Как да работя с договаряне на съдържание в уеб API

ASP.Net Web API е лека рамка, използвана за изграждане на бездържавни и RESTful HTTP услуги. RESTful услуги са леки, без гражданство, базирани на клиент-сървър, кешируеми услуги, които се основават на концепцията за ресурси. REST е архитектурен стил - набор от ограничения, използвани за внедряване на услуги без гражданство. Това е архитектурна парадигма, която се използва за създаване на повторно използваеми, мащабируеми услуги.

Представянето на ресурс във формата, за който се иска, е интересна тема, тъй като често може да искате да използвате вашите услуги от различни видове устройства. Договарянето на съдържание е една от най-важните концепции в уеб API. Макар и сравнително проста концепция, около тази тема има много заблуди и недоразумения. Когато проектирате и внедрявате RESTful услуги с помощта на Web API, често ще трябва да се занимавате с договаряне на съдържание.

Какво е договорено съдържание и защо е важно?

Договарянето на съдържание може да бъде дефинирано като процес на проверка на структурата на входяща HTTP заявка за определяне на най-доброто представяне на ресурс измежду множество налични представяния на един и същ ресурс. По същество договарянето на съдържание е концепция, която позволява на един и същ URL адрес да обслужва едно и също съдържание в различни формати. Можете да се възползвате от договарянето на съдържание, за да изберете предпочитания тип медия.

В Web API договарянето на съдържание се извършва от средата на изпълнение (от страна на сървъра), за да се определи форматиращият носител тип, който да се използва въз основа на връщане на отговора за входяща заявка от страна на клиента.

Договарянето на съдържание е съсредоточено върху форматирането на Media type и Media type. Докато първият се отнася до стойността на заглавката "тип съдържание" в HTTP заявка и HTTP отговор, последният се използва за преобразуване на .NET типове в съответстващи HTTP данни и обратно. Обърнете внимание, че форматирането на медиен тип в Web API е представено от абстрактен клас, наречен MediaTypeFormatter.

Рамката на Web API се предлага със следните форматиращи устройства по подразбиране.

  • System.Net.Http.Formatting.JsonMediaTypeFormatter
  • System.Net.Http.Formatting.XmlMediaTypeFormatter
  • System.Net.Http.Formatting.FormUrlEncodedMediaTypeFormatter
  • System.Web.Http.ModelBinding.JQueryMvcFormUrlEncodedFormatter

За да персонализирате договарянето на съдържание в уеб API, основната точка за разширяемост, от която би трябвало да се възползвате, е картографирането на типа медия. Обърнете внимание, че Web API предлага по подразбиране следните съпоставяния на носители.

  • QueryStringMapping
  • UriPathExtensionMapping
  • RequestHeaderMapping
  • MediaRangeMapping

За да създадете персонализирано картографиране на тип медия, ще трябва да създадете клас, който разширява MediaTypeMapping, както е показано в кодовия фрагмент по-долу.

public class MediaTypeMapping : MediaTypeMapping

{

   protected override double OnTryMatchMediaType(HttpResponseMessage response)

     {

                //Write your custom code here

     }

}

Следният кодов фрагмент илюстрира как можете да извлечете имената на всички поддържани форматиращи устройства в уеб API чрез итерация на колекцията HttpConfiguration.Formatters.

   [HttpGet]

       public List GetAllFormatters()

       {

           List lstFormaters = new List();

           foreach (var formatter in this.Configuration.Formatters)

           {

               lstFormaters.Add(formatter.GetType().Name);

           }

           return lstFormaters;

       }

Нека сега проучим как можем да работим с договаряне на съдържание, за да изберем форматиращия, който искаме, и да извлечем съдържанието във формата, от който се нуждаем. Помислете за следния клас обект.

public class CustomerDTO

   {

       public Int32 Id

       { get; set; }

       public string FirstName

       { get; set; }

       public string LastName

       { get; set; }

       public string Address

      { get; set; }

   }

След това приемете, че имате метод, който попълва данни в списък от тип CustomerDTO и ги връща.

private List GetCustomerData()

       {

           List lstCustomers = new List();

           CustomerDTO customer = new CustomerDTO();

           customer.Id = 1;

           customer.FirstName = "Joydip";

           customer.LastName = "Kanjilal";

           customer.Address = "Hyderabad, India";

           lstCustomers.Add(customer);

           return lstCustomers;

       }

Следващият метод на уеб API показва как можете да върнете HttpResponseMessage като отговор от вашия метод на уеб API на базата на механизма за договаряне на съдържанието по подразбиране.

[HttpGet]

       public HttpResponseMessage GetCustomers()

       {

           List lstCustomers = GetCustomerData();

           IContentNegotiator negotiator = Configuration.Services.GetContentNegotiator();

           ContentNegotiationResult result = negotiator.Negotiate(typeof(CustomerDTO), Request, Configuration.Formatters);

           return new HttpResponseMessage()

           {

               Content = new ObjectContent (lstCustomers, result.Formatter, result.MediaType.MediaType)

         };

       }

Ако трябва да използвате специфичен форматиращ механизъм, наличен в колекцията за форматиращи машини, може да искате да пренапишете същия метод, както е показано в кодовия фрагмент по-долу.

[HttpGet]

       public HttpResponseMessage GetCustomers()

       {

           List lstCustomers = GetCustomerData();

           return new HttpResponseMessage()

           {

               Content = new ObjectContent (lstCustomers, Configuration.Formatters[1])

           };

      }

Добре; но как тогава да създадете свой собствен форматиране? Е, за да създадете персонализирано форматиране на медиен тип, трябва да създадете клас, който разширява абстрактния клас MediaTypeFormatter. След това трябва да напишете своя персонализиран код в класа, който сте създали, за да замените методите на абстрактния базов клас MediaTypeFormatter.

public class CustomMediaTypeFormatter : MediaTypeFormatter

   {

       public override bool CanReadType(Type type)

       {

           throw new NotImplementedException();

       }

       public override bool CanWriteType(Type type)

       {

           throw new NotImplementedException();

       }

   }

След като вашият персонализиран форматиращ модул е ​​на място, можете лесно да го добавите към колекцията на форматиращите:

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