Проводка форм-данных И файл в ASP.NET Web API

У меня есть этот метод ASP.NET Web API, и я хочу опубликовать объект и в то же время файл!

    public async Task<IHttpActionResult> Post(Facility facility)
    {
        if (!ModelState.IsValid)
            return BadRequest();

        // Check if the request contains multipart/form-data.
        if (!Request.Content.IsMimeMultipartContent())
        {
            throw new HttpResponseException(HttpStatusCode.UnsupportedMediaType);
        }

        string root = HttpContext.Current.Server.MapPath("~/App_Data");
        var provider = new MultipartFormDataStreamProvider(root);

            // Read the form data.
            await Request.Content.ReadAsMultipartAsync(provider);

            // This illustrates how to get the file names.
            foreach (MultipartFileData file in provider.FileData)
            {
                Trace.WriteLine(file.Headers.ContentDisposition.FileName);
                Trace.WriteLine("Server file path: " + file.LocalFileName);
            }
            // Logic
            // Login

        return Ok(facilityManager.Insert(facility));
    }

И я хочу назвать это, поэтому отправлю этот http-запрос с помощью скрипача:

Заголовок:

Content-Type: multipart/form-data; boundary=-------------------------acebdf13572468
User-Agent: Fiddler
Host: localhost:44301
Content-Length: 3279

Тело

---------------------------acebdf13572468
Content-Disposition: form-data; name="fieldNameHere"; filename="credits.txt"
Content-Type: text/plain

<@INCLUDE *C:\Program Files (x86)\Fiddler2\credits.txt*@>
---------------------------acebdf13572468
Content-Disposition: form-data; name="facility"
Content-Type: application/json
{
    "FacilityTypeId":"1"
}
---------------------------acebdf13572468--

Я получаю код ошибки 415 с текстом ответа:

{ "message": "Тип носителя данных типа" multipart/form-data "не поддерживается для этого ресурса.", "exceptionMessage": "No MediaTypeFormatter доступен для чтения объекта типа 'Facility' из содержимого с типом мультимедиа" multipart/form-data ".," exceptionType ":" System.Net.Http.UnsupportedMediaTypeException "," stackTrace ":" в System.Net.Http.HttpContentExtensions.ReadAsAsync [T] (содержимое HttpContent, тип type, IEnumerable 1 formatters, IFormatterLogger formatterLogger, CancellationToken cancellationToken)\r\n at System.Net.Http.HttpContentExtensions.ReadAsAsync(HttpContent content, Type type, IEnumerable 1 formatters, IFormatterLogger formatterLogger, CancellationToken cancelationToken)\r\n в System.Web.Http.ModelBinding.FormatterParameterBinding.ReadContentAsync(запрос HttpRequestMessage, тип типа, IEnumerable`1 formatters, IFormatterLogger formatterLogger, CancellationToken cancelationToken) " }

Я много раз искал, прежде чем спрашивать, но не смог найти решение. Thnaks за помощь.

EDIT:

Примечание. Если я удалю параметр "объект" и дам метод только для загрузки файла, он отлично работает, но я хочу опубликовать JSON и файл вместе.

Ответы

Ответ 1

"mulitpart/form-data", поэтому мы регистрируем UploadMultipartMediaTypeFormatter

public class UploadMultipartMediaTypeFormatter : MediaTypeFormatter
{
    UploadMultipartMediaTypeFormatter()
    {
        SupportedMediaTypes.Add(new MediaTypeHeaderValue("multipart/form-data"));
    }
}

* зарегистрируйтесь в global.asax или (см. код песочницы)

config.Formatters.Add(new UploadMultipartMediaTypeFormatter());

Теперь WebApi вызовет MediaTypeFormatter.ReadFromStreamAsync, и мы можем вызывать расширение HttpContent.ReadAsMultipartAsync.

Ответ 2

У меня была та же проблема. Решено MultipartDataMediaFormatter для ASP.NET WebApi. Как использовать:

  • Найти и установить из пакетов Nuget MultipartDataMediaFormatter.
  • Добавить текущий форматтер в коллекцию форматировщиков WebApi:

    • если WebApi размещен в IIS (при запуске приложения).:
      • GlobalConfiguration.Configuration.Formatters.Add(new FormMultipartEncodedMediaTypeFormatter());
    • если WebApi является самостоятельным:

      • new HttpSelfHostConfiguration(<url>).Formatters.Add(new FormMultipartEncodedMediaTypeFormatter());

После этого вы можете отправить objec вместе с файлом вместе в одной модели.

Примечание. В пакетах Nuget версия 1.1.0 не является последней. Они еще не обновлены. Возможно, можно установить последнюю версию вручную.