Formátování dat odpovědí ve webovém ASP.NET Core API

Rick Anderson a Steve Smith

ASP.NET Core MVC podporuje formátování dat odpovědí. Data odpovědi lze formátovat pomocí konkrétních formátů nebo v reakci na požadovaný formát klienta.

Zobrazení nebo stažení ukázkového kódu (stažení)

Výsledky akce specifické pro formát

Některé typy výsledků akce jsou specifické pro konkrétní formát, například a JsonResult ContentResult . Akce mohou vracet výsledky, které jsou formátovány v určitém formátu bez ohledu na předvolby klienta. Například vrácení vrátí JsonResult data ve formátu JSON. Vrácení nebo ContentResult řetězec vrátí řetězcová data formátovaná jako prostý text.

Akce není nutná k vrácení žádného konkrétního typu. ASP.NET Core podporuje libovolnou návratovou hodnotu objektu. Výsledky z akcí, které vracejí objekty, které nejsou IActionResult typy, jsou serializovány pomocí příslušné IOutputFormatter implementace. Další informace naleznete v tématu Návratové typy akce kontroleru ve ASP.NET Core API.

Integrovaná pomocná metoda vrací Ok data ve formátu JSON: [!code-csharp]

Ukázkový soubor ke stažení vrátí seznam autorů. Použití vývojářských nástrojů prohlížeče F12 nebo nástroje Postman s předchozím kódem:

  • Zobrazí se hlavička odpovědi obsahující content-type: application/json; charset=utf-8 .
  • Zobrazí se hlavičky požadavku. Například Accept hlavička. Hlavičku Accept ignoruje předchozí kód.

Pokud chcete vrátit data ve formátu prostého textu, ContentResult použijte a Content pomocná pomocníka:

// GET api/authors/about
[HttpGet("About")]
public ContentResult About()
{
    return Content("An API listing authors of docs.asp.net.");
}

V předchozím kódu je Content-Type vrácena text/plain hodnota . Vrácení řetězce doručuje Content-Type text/plain :

// GET api/authors/version
[HttpGet("version")]
public string Version()
{
    return "Version 1.0.0";
}

Pro akce s více návratových typy vraťte IActionResult . Například vrácení různých stavových kódů HTTP na základě výsledku provedených operací.

Vyjednávání obsahu

Vyjednávání obsahu nastane, když klient zadá hlavičku Accept. Výchozí formát, který používá ASP.NET Core je JSON. Vyjednávání obsahu je:

  • Implementovali jsme ObjectResult .
  • Integrované do výsledků akce specifické pro stavový kód vrácených z pomocých metod. Pomocná metoda výsledků akce je založená na ObjectResult metodě .

Při vrácení typu modelu je návratový typ ObjectResult .

Následující metoda akce používá Ok pomocné metody NotFound a :

// GET: api/authors/search?namelike=th
[HttpGet("Search")]
public IActionResult Search(string namelike)
{
    var result = _authors.GetByNameSubstring(namelike);
    if (!result.Any())
    {
        return NotFound(namelike);
    }
    return Ok(result);
}

Ve výchozím nastavení ASP.NET Core application/json typy text/json médií , a text/plain . Nástroje, jako je Fiddler nebo Postman, mohou nastavit Accept hlavičku požadavku a určit formát vrácení. Pokud Accept hlavička obsahuje typ, který server podporuje, vrátí se tento typ. Další část ukazuje, jak přidat další formátovací funkce.

Akce kontroleru mohou vracet objekty POCOs (prosté staré objekty CLR). Po vrácení objektu POCO modul runtime automaticky vytvoří objekt , ObjectResult který objekt zabalí. Klient získá formátovaný serializovaný objekt. Pokud je vrácený objekt null , 204 No Content vrátí se odpověď.

Vrácení typu objektu:

// GET api/authors/RickAndMSFT
[HttpGet("{alias}")]
public Author Get(string alias)
{
    return _authors.GetByAlias(alias);
}

V předchozím kódu vrátí žádost o platný alias autora odpověď s daty 200 OK autora. Požadavek na neplatný alias vrátí 204 No Content odpověď.

Hlavička Accept

Vyjednávání obsahu probíhá, když Accept se v požadavku zobrazí hlavička. Pokud požadavek obsahuje hlavičku accept, ASP.NET Core:

  • Vytvoří výčet typů médií v hlavičce accept v pořadí podle priority.
  • Pokusí se najít formátovací modul, který může vytvořit odpověď v jednom ze zadaných formátů.

Pokud není nalezen žádný formátovací modul, který může splňovat požadavek klienta, ASP.NET Core:

  • Vrátí 406 Not Acceptable hodnotu , pokud je MvcOptions.ReturnHttpNotAcceptable nastavená na , nebo true -
  • Pokusí se najít první formátovací modul, který může vytvořit odpověď.

Pokud není pro požadovaný formát nakonfigurován žádný formátovací modul, použije se první formátovací modul, který může formátovat objekt. Pokud se Accept v požadavku nezobrazí žádná hlavička:

  • První formátovací modul, který může zpracovat objekt se používá k serializaci odpovědi.
  • Nehodí se žádné vyjednávání. Server určuje, jaký formát se má vrátit.

Pokud hlavička Accept obsahuje */* , hlavička se ignoruje, pokud RespectBrowserAcceptHeader není u nastavená hodnota MvcOptions true.

Prohlížeče a vyjednávání obsahu

Na rozdíl od typických klientů rozhraní API dodávají webové Accept prohlížeče hlavičky. Webový prohlížeč určuje mnoho formátů, včetně zástupných znaků. Když rozhraní ve výchozím nastavení zjistí, že požadavek pochází z prohlížeče:

  • Hlavička Accept se ignoruje.
  • Pokud není nakonfigurované jinak, vrátí se obsah ve formátu JSON.

To poskytuje konzistentnější prostředí napříč prohlížeči při používání rozhraní API.

Pokud chcete nakonfigurovat aplikaci tak, aby přijímaly hlavičky prohlížeče, nastavte RespectBrowserAcceptHeader na true :

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllers(options =>
    {
        options.RespectBrowserAcceptHeader = true; // false by default
    });
}
public void ConfigureServices(IServiceCollection services)
{
    services.AddMvc(options =>
    {
        options.RespectBrowserAcceptHeader = true; // false by default
    });

    services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
}

Konfigurace formatterů

Aplikace, které potřebují podporovat další formáty, mohou přidat NuGet balíčky a nakonfigurovat podporu. Pro vstup a výstup existují samostatné formátovací metody. Vstupní formátovací metody se používají v modelové vazbě. K formátování odpovědí se používají formátovací soubory výstupu. Informace o vytvoření vlastního formátovacího modulu najdete v tématu Vlastní formátovací modul.

Přidání podpory formátu XML

Formátovací metody XML implementované XmlSerializer pomocí se konfiguruje voláním AddXmlSerializerFormatters :

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllers()
        .AddXmlSerializerFormatters();
}

Předchozí kód serializuje výsledky pomocí XmlSerializer .

Při použití předchozího kódu vrátí metody kontroleru odpovídající formát na základě hlavičky Accept požadavku.

Konfigurace System.Text.Json formátovací funkce založené na nástroji

Funkce pro System.Text.Json formátovací prvky založené na systému je možné nakonfigurovat pomocí Microsoft.AspNetCore.Mvc.JsonOptions.JsonSerializerOptions . Výchozí formátování je camelCase. Následující zvýrazněný kód nastaví formát JazykaCase podle jazykaCase:

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllers()
            .AddJsonOptions(options => 
               options.JsonSerializerOptions.PropertyNamingPolicy = null);
}

Následující metoda akce volá ControllerBase.Problem k vytvoření ProblemDetails odpovědi:

[HttpGet("error")]
public IActionResult GetError()
{
    return Problem("Something went wrong!");
}

Pomocí předchozího kódu:

  • https://localhost:5001/WeatherForecast/temperature vrací jazyk PascalCase.
  • https://localhost:5001/WeatherForecast/error vrátí camelCase. Chybová odpověď je vždy camelCase, i když aplikace nastaví formát na FormátCase. ProblemDetails následuje DOKUMENT RFC 7807,který určuje malá písmena.

Následující kód nastaví položkuCase jazykaCase a přidá vlastní převaděč:

services.AddControllers().AddJsonOptions(options =>
{
    // Use the default property (Pascal) casing.
    options.JsonSerializerOptions.PropertyNamingPolicy = null;

    // Configure a custom converter.
    options.JsonSerializerOptions.Converters.Add(new MyCustomJsonConverter());
});

Možnosti serializace výstupu pro každou akci lze nakonfigurovat pomocí JsonResult . Příklad:

public IActionResult Get()
{
    return Json(model, new JsonSerializerOptions
    {
        WriteIndented = true,
    });
}

Přidání podpory formátu JSON založeného na PříponěSoft.Json

Před ASP.NET Core 3.0 se výchozí použité formátovací funkce JSON implementovali pomocí Newtonsoft.Json balíčku . Ve ASP.NET Core verze 3.0 nebo novější jsou výchozí formátovací funkce JSON založené na System.Text.Json . Podpora pro formátovací a funkce založené na systému je dostupná instalací Newtonsoft.Json balíčku NuGet a jeho konfigurací v Microsoft.AspNetCore.Mvc.NewtonsoftJson Startup.ConfigureServices .

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllers()
        .AddNewtonsoftJson();
}

V předchozím kódu volání nakonfiguruje následující funkce webového rozhraní AddNewtonsoftJson API, MVC a Pages pro použití Razor Newtonsoft.Json :

Některé funkce nemusí se formátovacími funkcemi založenými na typu dobře fungovat a vyžadují odkaz na formátery System.Text.Json Newtonsoft.Json založené na . Pokud aplikace používá Newtonsoft.Json následující formátovací funkce:

  • Používá Newtonsoft.Json atributy. Příkladem je [JsonProperty] nebo [JsonIgnore].
  • Upraví nastavení serializace.
  • Spoléhá na funkce, které Newtonsoft.Json poskytuje.
  • Nakonfiguruje Microsoft.AspNetCore.Mvc.JsonResult.SerializerSettings . Před ASP.NET Core 3.0 přijímá instanci , která JsonResult.SerializerSettings JsonSerializerSettings je specifická pro Newtonsoft.Json .

Funkce pro Newtonsoft.Json formátovací zařízení založená na systému je možné nakonfigurovat pomocí Microsoft.AspNetCore.Mvc.MvcNewtonsoftJsonOptions.SerializerSettings :

services.AddControllers().AddNewtonsoftJson(options =>
{
    // Use the default property (Pascal) casing
    options.SerializerSettings.ContractResolver = new DefaultContractResolver();

    // Configure a custom converter
    options.SerializerSettings.Converters.Add(new MyCustomJsonConverter());
});

Možnosti serializace výstupu pro každou akci lze nakonfigurovat pomocí JsonResult . Příklad:

public IActionResult Get()
{
    return Json(model, new JsonSerializerSettings
    {
        Formatting = Formatting.Indented,
    });
}

Přidání podpory formátu XML

Formátování XML vyžaduje Microsoft.AspNetCore.Mvc.Formatters.Xml NuGet kódu.

Formátovací metody XML implementované XmlSerializer pomocí se konfiguruje voláním AddXmlSerializerFormatters :

public void ConfigureServices(IServiceCollection services)
{
    services.AddMvc()
        .SetCompatibilityVersion(CompatibilityVersion.Version_2_1)
        .AddXmlSerializerFormatters();
}

Předchozí kód serializuje výsledky pomocí XmlSerializer .

Při použití předchozího kódu by metody kontroleru měly vrátit odpovídající formát na základě hlavičky Accept požadavku.

Určení formátu

Pokud chcete omezit formáty odpovědí, použijte [Produces] filtr. Podobně jako u většinyfiltrů je [Produces] možné akci, kontroler nebo globální rozsah použít:

[ApiController]
[Route("[controller]")]
[Produces("application/json")]
public class WeatherForecastController : ControllerBase
{

Předchozí [Produces] filtr:

  • Vynutí, aby všechny akce v kontroleru vrátily odpovědi ve formátu JSON.
  • Pokud jsou nakonfigurované jiné formátovací funkce a klient určuje jiný formát, vrátí se JSON.

Další informace najdete v tématu Filtry.

Formátování zvláštních případů

Některé speciální případy jsou implementovány pomocí předdefinované formátovací funkce. Návratové typy string jsou ve výchozím nastavení formátovány jako text/plain (text/html, pokud je to požadováno prostřednictvím Accept hlavičky). Toto chování je možné odstranit StringOutputFormatter odebráním . V metodě se odebraly ConfigureServices formátovací metody. Akce, které mají objekt modelu, vrací při vrácení 204 No Content návratový typ null . Toto chování je možné odstranit HttpNoContentOutputFormatter odebráním . Následující kód odebere a StringOutputFormatter HttpNoContentOutputFormatter .

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllers(options =>
    {
        // requires using Microsoft.AspNetCore.Mvc.Formatters;
        options.OutputFormatters.RemoveType<StringOutputFormatter>();
        options.OutputFormatters.RemoveType<HttpNoContentOutputFormatter>();
    });
}
public void ConfigureServices(IServiceCollection services)
{
    services.AddMvc(options =>
    {
        // requires using Microsoft.AspNetCore.Mvc.Formatters;
        options.OutputFormatters.RemoveType<StringOutputFormatter>();
        options.OutputFormatters.RemoveType<HttpNoContentOutputFormatter>();
    });

    services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
}

Bez StringOutputFormatter rozhraní vracejí integrované formátovací formátovací formáty JSON string typy. Pokud je integrovaný formátovací modul JSON odebrán a k dispozici formátovací modul XML, formátovací modul XML string vrátí typy. V opačném string případě návratové typy vrátí 406 Not Acceptable .

Bez HttpNoContentOutputFormatter objektu jsou objekty null formátovány pomocí nakonfigurovaného formátovacího modulu. Příklad:

  • Formátovací modul JSON vrátí odpověď s textem null .
  • Formátovací modul XML vrátí prázdný element XML s nastaveným xsi:nil="true" atributem.

Mapování adres URL ve formátu odpovědi

Klienti mohou žádat o konkrétní formát jako součást adresy URL, například:

  • V řetězci dotazu nebo části cesty.
  • Pomocí přípony souboru specifického pro formát, například .xml nebo .json.

Mapování z cesty požadavku by se mělo zadat na trase, kterou rozhraní API používá. Příklad:

[Route("api/[controller]")]
[ApiController]
[FormatFilter]
public class ProductsController : ControllerBase
{
    [HttpGet("{id}.{format?}")]
    public Product Get(int id)
    {

Předchozí trasa umožňuje zadat požadovaný formát jako volitelnou příponu souboru. Atribut kontroluje existenci hodnoty formátu v objektu a mapuje formát odpovědi na příslušný formátovací modul [FormatFilter] RouteData při vytvoření odpovědi.

Trasa Formátovací modul
/api/products/5 Výchozí formátovací modul pro výstup
/api/products/5.json Formátovací modul JSON (pokud je nakonfigurovaný)
/api/products/5.xml Formátovací modul XML (pokud je nakonfigurovaný)