Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Unsupported Media Types when POST to web api

Here is the client :

using (var client = new HttpClient())
{

    client.BaseAddress = new Uri("http://localhost/MP.Business.Implementation.FaceAPI/");
    client.DefaultRequestHeaders
            .Accept
            .Add(new MediaTypeWithQualityHeaderValue("application/octet-stream"));
    using (var request = new HttpRequestMessage(HttpMethod.Post, client.BaseAddress + "api/Recognition/Recognize"))
    {
        request.Content = new ByteArrayContent(pic);
        request.Content.Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream");

        await client.PostAsync(request.RequestUri, request.Content);

    }
}   

and the server :

[System.Web.Http.HttpPost]
public string Recognize(byte[] img)
{
    //do someth with the byte []

}  

I am getting error:

415 Unsupported Media Type

all the time - The request entity's media type 'application/octet-stream' is not supported for this resource. What can i do about it? I've found some answered threads here , but it didnt help.

like image 761
Chris Tanev Avatar asked Oct 17 '22 12:10

Chris Tanev


1 Answers

While byte[] would be a great way to represent application/octet-stream data, this is not the case by default in Web API.

My workaround is in ASP.NET Core 1.1 - the details may be different in other variants.

In your controller method, remove the img parameter. Instead, refer to the Request.Body, which is a Stream. e.g. to save to a file:

using (var stream = new FileStream(someLocalPath, FileMode.Create))
{
    Request.Body.CopyTo(stream);
}

The situation is similar for returning binary data from a GET controller method. If you make the return type byte[] then it is formatted with base64! This makes it significantly larger. Modern browsers are perfectly capable of handling raw binary data so this is no longer a sensible default.

Fortunately there is a Response.Body https://github.com/danielearwicker/ByteArrayFormatters:

Response.ContentType = "application/octet-stream";
Response.Body.Write(myArray, 0, myArray.Length);

Make the return type of your controller method void.

UPDATE

I've created a nuget package that enables direct use of byte[] in controller methods. See: https://github.com/danielearwicker/ByteArrayFormatters

like image 53
Daniel Earwicker Avatar answered Oct 22 '22 19:10

Daniel Earwicker