【问题标题】:Web API DELETE - The parameters dictionary contains a null entry for parameter 'id'Web API DELETE - 参数字典包含参数“id”的空条目
【发布时间】:2018-02-13 17:14:32
【问题描述】:

我正在尝试使用 ASP.NET Web API DELETE 从数据库中删除记录。

这里是 jQuery AJAX 调用:

var row = $(dom).closest("tr");
var text = row.find(".tId").text();
var tId = +(text);

//HTTP DELETE method
$.ajax({
    url: 'api/transaction/delete',
    type: 'DELETE',
    data: {
        'id': tId
    },
    success: function (result) {
        //Success logic
        //Refresh table?
        console.log("Successfully deleted transaction " + tId);
    },
    error: function () {
        console.log("Error deleting transaction");
    }
});

这是控制器代码:

    [HttpDelete]
    [Route("api/transaction/delete/{id}")]
    public HttpResponseMessage Delete(int id)
    {
        if (DataLayer.DataLayer.DeleteTransaction(id))
        {
            return Request.CreateResponse(HttpStatusCode.OK);
        }
        else
        {
            return null;
        }
    }

还有来自Global.asax.cs的Http路由

 RouteTable.Routes.MapHttpRoute(
            name: "DefaultApi",
            routeTemplate: "api/{controller}/{id}",
            defaults: new { id = System.Web.Http.RouteParameter.Optional }
        );

在 Fiddler 中查看请求,返回的错误为 The parameters dictionary contains a null entry for parameter 'id' of non-nullable type 'System.Int32' for method 'System.String Get(Int32)' in 'SemanticUI_Playground.Controllers.TransactionController'. An optional parameter must be a reference type, a nullable type, or be declared as an optional parameter.

但奇怪的是——也在 Fiddler 中——我可以看到请求有 id=1045

我显然没有做正确的事情;我的猜测是路由。如果我将 AJAX 请求 URL 更改为 api/transaction 而不是 api/transaction/delete 我会得到一个不同的错误(DELETE is not supported 或类似的效果)。

id参数全部去掉就意味着TransactionController中的断点遇到了,但是显然没用!

我知道这有点笨拙(这个项目只是一个自学网络开发的个人项目),对于我明显缺乏理解,请接受我的歉意!

【问题讨论】:

  • 为什么要将正在执行的操作包含在开始的路由中?如果你想成为 RESTful,那么 URL 不应该提到“删除”——只有 HTTP 动词应该。
  • 如果您将删除请求发送到 '/api/transaction/delete/' + tId 而不是将数据附加到正文会发生什么?如果将 [FromBody] 属性放在删除方法 (public HttpResponseMessage Delete([FromBody]int id)) 的 int id 参数上并按原样发送请求会发生什么?
  • 有很多很多关于这个错误的问题,你有没有试过搜索。例如,this onethis oneand many more
  • 您的路由指定 ID 应该在 URL 中而不是正文中。将您的$.ajax 调用的网址更改为url: 'api/transaction/delete/' + tId
  • Adn 是的,您的路线应该是api/transaction/{id}。事实上,您甚至不必用 RouteAttribute 指定它,因为它是默认路由(假设您的控制器名为 TransactionController)。通过在多个地方添加路由,将动词放在 URL 中,您更难检测到实际错误

标签: c# asp.net asp.net-web-api


【解决方案1】:

添加不同类型的请求的好处是您不需要有多个 URL 来执行操作;您通过请求类型(DELETE、GET、POST 等)调用它们。在您给出的示例中,我将删除您使用 [Route("api/transaction/delete/{id}")] 声明的附加路由并使用以下方法调用它:

$.ajax({
    url: '/api/transaction/' + tId,
    type: 'DELETE',
    success: function (result) {
        //Success logic
        //Refresh table?
        console.log("Successfully deleted transaction " + tId);
    },
    error: function () {
        console.log("Error deleting transaction");
    }
});

或者同样保留代码路由并将请求发送到'/api/transaction/delete/' + tId

我发现在调用MapHttpRoute 之前,您还需要在Global.asax.cs 中使用RouteTable.Routes.MapHttpAttributeRoutes 注册属性路由。看看这个for a bit of guidance on that (ordering of the registration code is important!)

【讨论】:

    猜你喜欢
    • 2017-05-12
    • 2013-12-15
    • 1970-01-01
    • 1970-01-01
    • 2016-10-14
    • 2018-01-21
    • 1970-01-01
    相关资源
    最近更新 更多