WebApi Put "The parameter dictionary contains a null entry for the parameter ..."

public class ContactsController : ApiController { private static readonly List<Contact> _contacts = new List<Contact>(); public Contact PutContacts(int id, Contact contact) { if (_contacts.Any(c => c.Id == contact.Id) == false) { throw new HttpResponseException(HttpStatusCode.NotFound); } contact.LastModified = DateTime.Now; return contact; } } 

http put header:

 PUT /api/contacts/3 HTTP/1.1 User-Agent: Fiddler Content-Type: application/json Host: localhost:8080 

body:

 {"Id":3,"Name":"mmm","Phone":"000 000 0000","Email":" mmm@gmail.com ","LastModified":"2012-03-08T23:42:13.8681395+08:00"} 

Answer:

 HTTP/1.1 400 Bad Request "The parameters dictionary contains a null entry for parameter 'id' of non-nullable type 'System.Int32' for method 'SelfHost.Contact PutContacts(Int32, SelfHost.Contact)' in 'SelfHost.ContactsController'. An optional parameter must be a reference type, a nullable type, or be declared as an optional parameter." 

Why? thanks.

PS:

 config.Routes.MapHttpRoute( name: "DefaultApi", routeTemplate: "api/{controller}/{id}", defaults: new { id = RouteParameter.Optional } ); 
+6
source share
3 answers

I cannot reproduce the problem you are describing.

Model:

 public class Contact { public int Id { get; set; } public string Name { get; set; } public string Phone { get; set; } public string Email { get; set; } public DateTime LastModified { get; set; } } 

Controller:

 public class ContactsController : ApiController { public Contact Put(int id, Contact contact) { return contact; } } 

Client:

 class Program { static void Main() { using (var client = new WebClient()) { client.Headers[HttpRequestHeader.ContentType] = "application/json"; var data = Encoding.UTF8.GetBytes(@"{""Id"":3,""Name"":""mmm"",""Phone"":""000 000 0000"",""Email"":"" mmm@gmail.com "",""LastModified"":""2012-03-08T23:42:13.8681395+08:00""}"); var result = client.UploadData("http://localhost:1405/api/contacts/4", "PUT", data); Console.WriteLine(Encoding.UTF8.GetString(result)); } } } 

When I start the client, the following request is sent:

 PUT /api/contacts/4 HTTP/1.1 Content-Type: application/json Host: localhost:1405 Content-Length: 119 Expect: 100-continue Connection: Keep-Alive {"Id":3,"Name":"mmm","Phone":"000 000 0000","Email":" mmm@gmail.com ","LastModified":"2012-03-08T23:42:13.8681395+08:00"} 

and I get the correct result from the server. Therefore, I assume that the request you are showing is not the actual request that is sent to the server.

+1
source

I have the same problem. The request parameter "id" is null and the contact object is populated. I think this is a problem with model binding. If you set a breakpoint in the controller, look at this expression:

 this.ControllerContext.RouteData.Values["id"] 

You will see that the value is indicated in the route data; it is simply not installed on the model. I have an ActionFilter, and if I also added a breakpoint, I can see that the actionContext of the ActionArgument has a key for it, but has a null value.

Im still exploring ...

+2
source

craigtadlock, thanks for your help and sent a bug to Microsoft. I had the same problem with PUT. None of them worked. As a workaround, I hacked POST to handle PUT. If the object that I am sending to the server already has an identifier, the POST code treats it as a PUT with this identifier. Pseudocode:

 public HttpResponseMessage<MyClass> PostMyClass(MyClass myObject) { if( myObject.ID != 0 ){ //do PUT code }else{ //do POST code } } 
0
source

Source: https://habr.com/ru/post/910264/


All Articles