我已经阅读了大量描述相同错误消息的类似帖子,但它们似乎与我所遇到的不符。
我最近开始使用Web API并将我所有的MVC方法转换到我返回JSON等的位置,因此MVC将只渲染html,我将通过webapi控制器的ajax调用模型。
这是奇怪的事情,我可以从我的家庭apiController获取和POST(所以我可以登录/注册等),但我只能从我创建的区域中的API控制器获取。我得到了405(方法不允许),即使它的装饰和调用方式与其他控制器相同。我想路由是好的,否则它不会返回我的初始获取?
路由
public static void Register(HttpConfiguration config)
{
config.Routes.MapHttpRoute(
name: "DefaultAreaApi",
routeTemplate: "api/{area}/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional }
);
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional }
);
}
控制器
// Returns Model
[HttpGet]
public HttpResponseMessage SelectAgent()
// The requested resource does not support http method 'POST'.
[HttpPost]
public HttpResponseMessage SelectAgent(Guid id)
JQuery的
// Works fine
$.ajax({
type: 'POST',
url: '/api/Home/Login',
headers: options.headers,
contentType: "application/json; charset=utf-8",
dataType: 'JSON',
data: ko.toJSON(self.serverModel),
success: function (response) {
// Works fine
$.getJSON("/api/Account/Users/SelectAgent", function (model) { ....
// 405
$.ajax({
type: 'POST',
url: '/api/Account/Users/SelectAgent',
headers: options.headers,
contentType: "application/json; charset=utf-8",
dataType: 'JSON',
data: "{'id':'" + selectModel.agentId() + "'}",
success: function (response) {....
传递的数据似乎很好(或者至少是它曾经使用过的MVC控制器)。
我根本没有修改过Home API Controller,我不明白我怎么能发布到那个而不是我的其他控制器。哎呀。
任何正确方向的指针都会很棒。
答案 0 :(得分:12)
Web API仅查看基本数据类型的查询字符串参数。因此,当您发帖时,您的帖子只会查看/api/Account/Users/SelectAgent
的网址。在与函数匹配时,不会考虑提交的数据,因为您没有使用Guid
属性标记[FromBody]
。因此,正在返回“方法不允许”错误,因为它将您的POST请求发送到您的GET方法(没有参数)。
您可以在asp.net上了解详情:
如果参数是“简单”类型,Web API会尝试从URI中获取值。简单类型包括.NET基元类型(int,bool,double等),以及TimeSpan,DateTime,Guid,decimal和string,以及具有可以从字符串转换的类型转换器的任何类型。 (稍后将详细介绍类型转换器。)
要解决此问题,请尝试执行以下操作之一:
更改您要提交的网址,以便在电子邮件的查询字符串中包含id
url: '/api/Account/Users/SelectAgent?id=' + selectModel.agentId()
更改操作签名以阅读ID FromBody
:
public HttpResponseMessage SelectAgent([FromBody]Guid id)
答案 1 :(得分:3)
我知道这是一个老问题,但这个答案可能对某人有所帮助。更改Action签名以读取Id FromBody:对我来说不起作用,我想知道当你有一个包含许多字段/成员的复杂类型时,将参数传递给查询字符串是多么容易。
这个问题是由于传统和基于动词的路由都不能在同一个ApiController中使用。见this link。
您可以通过向POST操作方法添加空[Route]
属性来解决此问题。那是: -
[HttpPost]
[Route]
public HttpResponseMessage SelectAgent(Guid id)
答案 2 :(得分:1)
如果您的帖子和获取功能具有相同的名称,它将路由到Get功能。这就是为什么你得到这个答案。今天最简单的方法是
[HttpPost]
[Route("api/postagent", Name ="postagent")]
public HttpResponseMessage SelectAgent(Guid id)
只需为您的帖子功能定义路线,并在客户端为其发布 主持人+ / api / postagent例如。您可以通过此链接找到更多详细信息。
如果您通过generatin new controller创建一个api控制器,这将特别有用。预定义函数将具有get和post方法具有相同路径的结构。你需要重新定义其中一个或两个分开它们。