2012-05-14 20 views
5

Supongo que he leído mucho sobre el control de versiones de una API relajante, y decidí no versionar el servicio a través de la uri, pero usando mediatypes (formato y esquema en el encabezado request accept):Implementando el versionado de una API RESTful con WCF o ASP.Net Web Api

¿Cuál sería la mejor manera de implementar un servicio wcf o un servicio web api para atender solicitudes que definan el recurso solicitado en el uri, el formato (por ejemplo, application/json) y el esquema/versión (por ejemplo, jugador-v2) en el encabezado de aceptar?

WCF me permite enrutar en función del uri, pero no en función de los encabezados. Entonces no puedo rutear apropiadamente.

Web Api me permite definir formatos de medios personalizados, enrutamiento para el formato solicitado, pero no el esquema (por ejemplo, tipo de retorno PlayerV1 o PlayerV2).

me gustaría implementar un servicio (ya sea con WCF o Web API) que, para esta solicitud (Pseudo código):

api.myservice.com/players/123 Accept format=application/json; schema=player-v1 

devuelve una entidad PlayerV1, en formato JSON

y para esta solicitud:

api.myservice.com/players/123 Accept format=application/json; schema=player-v2 

devuelve una entidad PlayerV2, en formato json.

¿Algún consejo sobre cómo implementar esto?

EDIT: Para aclarar por qué quiero usar la negociación de contenido para tratar las versiones, consulte aquí: REST API Design: Put the “Type” in “Content-Type”.

Respuesta

2

Lo que traes aquí no me parece como control de versiones pero es más una negociación de contenido. El encabezado Aceptar expresa los deseos del cliente sobre el formato del recurso. El servidor debe otorgar los deseos o devolver 406. Por lo tanto, si necesitamos más de un concepto de Contrato (aunque la API web unline RPC no define uno), el recurso es más sólido.

Las mejores prácticas para el control de versiones aún no se han discutido plenamente pero más entusiastas creen REST utilizando la versión en la URL es el camino a seguir (por ejemplo http://server/api/1.0.3/...). Esto también tiene más sentido para mí, ya que en su enfoque el servidor de negociación de contenido debe mantener la compatibilidad con versiones anteriores y solo puedo imaginar que el código en el servidor será cada vez más complejo. Con el uso del enfoque de URL, puede hacer una pausa limpia: los clientes antiguos pueden usar con gusto antes, mientras que los nuevos clientes pueden disfrutar de los beneficios de la nueva API.


ACTUALIZACIÓN

OK, ahora la cuestión ha cambiado a "Aplicación de negociación de contenido en un AP REST".

Tipo 1: Controlador ajeno

Básicamente, si la negociación de contenido implica sólo el formato del recurso, la aplicación o el uso de la derecha tipo de medio formateador es suficiente. Por ejemplo, si la negociación de contenido implica devolver JSON o XML. En estos casos, el controlador está ajeno a para las negociaciones de contenido.

Tipo 2: Controlador conscientes

controlador necesita estar al tanto de la negociación petición. En este caso, los parámetros de la solicitud deben extraerse de la solicitud y pasarse como parámetro. Por ejemplo, imaginemos esta acción en un controlador:

public Player Get(string schemaVersion) 
{ 
    ... 
} 

En este caso, me gustaría utilizar proveedores de valor de estilo clásico MVC (Ver Brad Wilson's post on ValueProviders - este es el MVC, pero proveedor de valor de Web API es similar):

public Player Get([ValueProvider(typeof(RequestHeadersSchemaValueProviderFactory))]string schemaVersion) 
{ 
    ... 
} 
+2

No comencemos un debate sobre qué camino es mejor (versión en URI o no) ya que ese no es el punto aquí. Podría reformular la pregunta: "Implementar la negociación de contenido en una API RESTful ...", el desafío de la implementación seguiría siendo el mismo, ¿no? – codeclash

+0

@cardinal que he actualizado. – Aliostad

+0

El proveedor de valor me da acceso al esquema solicitado, pero en cualquier caso el tipo de devolución en su ejemplo sería Player, mientras que en realidad tendría que devolver un Player o PlayerV2, ... dependiendo del esquema solicitado. ¿Me estoy perdiendo de algo? – codeclash