Форма POST ASP.NET Core призводить до відповіді HTTP 415 непідтримуваного типу медіа


173

Надсилання запиту POST HTTP ( Content-Type: application/x-www-form-urlencoded) на контролер нижче, призводить до відповіді HTTP 415 Непідтримуваний тип медіа .

public class MyController : Controller
{
    [HttpPost]
    public async Task<IActionResult> Submit([FromBody] MyModel model)
    {
        //...
    }
}

Формати заголовків повідомлення HTTP:

POST /submit HTTP/1.1
Host: example.com:1337
Connection: keep-alive
Content-Length: 219
Pragma: no-cache
Cache-Control: no-cache
Origin: https://example.com:1337
Upgrade-Insecure-Requests: 1
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36
Content-Type: application/x-www-form-urlencoded
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8
Referer: https://example.com:1337/submit
Accept-Encoding: gzip, deflate, br
Accept-Language: en-US,en;q=0.8,nl;q=0.6

Це використовувалося для роботи з ASP.NET MVC 5 на .NET 4.6.


вам не доведеться використовувати [FromForm] "Надіслати (модель MyModel)" також правильно отримати модель.
хасан

Відповіді:


298

Для форм використовуйте [FromForm]атрибут замість [FromBody]атрибута.

Наведений нижче контролер працює з ASP.NET Core 1.1:

public class MyController : Controller
{
    [HttpPost]
    public async Task<IActionResult> Submit([FromForm] MyModel model)
    {
        //...
    }
}

Примітка. [FromXxx]Потрібно, якщо ваш контролер помічений на [ApiController]. Для звичайних контролерів перегляду його можна опустити.


104

Ви можете використовувати, [FromBody]але вам потрібно встановити Content-Typeзаголовок вашого запиту application/json, тобто

Content-Type: application/json

1
Ось чому в питанні конкретно згадується форма POST, що містить тип вмісту application/x-www-form-urlencoded. Як і <form>на сторінці HTML.
Барт Веркойєн

Це було корисно для мене, оскільки я подав об’єкт, а не форму. Прийнята відповідь є найбільш правильною для ОП, яка вже використовувала правильний тип вмісту для [FromForm]. Все-таки я радий, що і цей був тут. :)
Кен Ліон

1
Це зовсім не відповідає на питання. Питання полягає в тому, як зробити органи підтримки сервера форми, а не як просто сказати всім своїм клієнтам, щоб вони перестали надсилати їх!
csauve

Зачекайте, чи це означає, що неможливо проковтнути вміст із тіла запиту, іншого, ніж application/json, як application/text? @BartVerkoeijen якісь ідеї?
SpiritBob

10

Спочатку потрібно вказати у заголовках Content-Type, наприклад, що це може бути application/json.

Якщо ви встановите application/jsonтип вмісту, вам потрібно надіслати json.

Так що в bodyваше прохання ви пошлете НЕ form-data, що не , x-www-for-urlencodedале rawJSON, наприклад ,{"Username": "user", "Password": "pass"}

Ви можете адаптувати приклад до різних типів вмісту, включаючи те, що потрібно надіслати.

Ви можете використовувати такий інструмент, як "Листоноша" або завиток, щоб грати з цим.


6

На додаток до хороших відповідей, Вам не доведеться використовувати [FromForm]для отримання даних форми в контролер. Рамка автоматично перетворює дані форми у модель, як ви хочете. Ви можете реалізувати, як описано нижче.

[HttpPost]
public async Task<IActionResult> Submit(MyModel model)
{
    //...
}

3
Не те, що я бачу.
Франсуа

Я перевірив його, і він працював. Можливо, є ще одна проблема з вашим кодом
hasan

Це вирішило мою проблему. Я відхиляв об'єкт FormData з полями та файлами в ньому, [FromForm] або [FromBody] не працювали. Видалили їх і воно спрацювало. (Asp.Net MVC Core 2.1 ззаду, ванільний js спереду). Тут суть .
Даніель Сабо

Смішно, через кілька місяців після мого попереднього коментаря - сьогодні у мене була така ж проблема в проекті AspNetCore 2.2 Web Api, і мені довелося використовувати [FromFrom], щоб він працював у контролері WebAPI (див. Відповідь @ Барта).
Даніель Сабо

1
Для мене був [FromQuery]параметр, але я не вказав Content-Type як application/json- додавши, що в моєму запиті я також зробив цю роботу з параметром [FromQuery].
Майк

5

Це мій випадок: це запуск середовища: Контролер AspNet Core 2.1:

public class MyController
{
    // ...

    [HttpPost]
    public ViewResult Search([FromForm]MySearchModel searchModel)
    {
        // ...
        return View("Index", viewmodel);
    }
}

Вид:

<form method="post" asp-controller="MyController" asp-action="Search">
    <input name="MySearchModelProperty" id="MySearchModelProperty" />
    <input type="submit" value="Search" />
</form>

2

проблема може через MVC MW. Ви повинні встановити formatterType у параметрах MVC:

services.AddMvc(options =>
            {
                options.UseCustomStringModelBinder();
                options.AllowEmptyInputInBodyModelBinding = true;
                foreach (var formatter in options.InputFormatters)
                {
                    if (formatter.GetType() == typeof(SystemTextJsonInputFormatter))
                        ((SystemTextJsonInputFormatter)formatter).SupportedMediaTypes.Add(
                            Microsoft.Net.Http.Headers.MediaTypeHeaderValue.Parse("text/plain"));
                }
            }).AddJsonOptions(options =>
            {
                options.JsonSerializerOptions.PropertyNameCaseInsensitive = true;
            });

Де параметри.UseCustomStringModelBinder () доступний ?? Я не знайшов документації про це ніде.
Fabricio Araujo

0

"HTTP 415 непідтримуваний відповідь типу медіа" походить від Content-Type в заголовку вашого запиту. наприклад у javascript від axios:

Axios({
            method: 'post',
            headers: { 'Content-Type': 'application/json'},
            url: '/',
            data: data,  // an object u want to send
          }).then(function (response) {
            console.log(response);
          });
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.