Operaciones no CRUD en un servicio RESTful

¿Cuál es la forma “RESTANTE” de agregar operaciones que no son CRUD a un servicio RESTful? Digamos que tengo un servicio que permite el acceso de CRUD a registros como este:

GET /api/car/123 <- Returns information for the Car object with ID 123 POST /api/car <- Creates a new car (with properties in the request) PUT /api/car/123 <- Updates car 123 (with properties in the request) DELETE /api/car/123 <- Deletes car 123 POST /api/car/123/wheel/ <- Creates a wheel and associates it to car 123 

Si quiero cambiar el color del automóvil, simplemente POST /api/car/123 e incluir una variable POST para el nuevo color.

Pero digamos que quiero comprar un automóvil, y esa operación es más complicada que la simple actualización de la propiedad de “vehículo propiedad” de un registro de “usuario”. ¿Es RESTful simplemente hacer algo como POST /api/car/123/purchase , donde “purchase” es esencialmente un nombre de método? ¿O debería usar un verbo HTTP personalizado, como PURCHASE lugar de POST ?

¿O las operaciones que no son CRUD están completamente fuera del scope de REST?

Piense en comprar como una entidad comercial o un recurso en el diccionario RESTful. Dicho esto, hacer una compra en realidad está creando un nuevo recurso. Asi que:

 POST /api/purchase 

colocará un nuevo orden. Los detalles (usuario, automóvil, etc.) deben estar referenciados por id (o URI) dentro de los contenidos enviados a esta dirección.

No importa que ordenar un automóvil no sea simplemente un INSERT en la base de datos. En realidad, REST no se trata de exponer sus tablas de base de datos como operaciones CRUD. Desde el punto de vista lógico, está creando un pedido (compra), pero el lado del servidor puede realizar todos los pasos de procesamiento que desee.

Incluso puedes abusar del protocolo HTTP aún más. Use el encabezado Location para devolver un enlace al pedido creado recientemente, elija cuidadosamente los códigos de respuesta HTTP para informar a los usuarios sobre problemas (del lado del servidor o del cliente), etc.

La forma RESTful, según tengo entendido, es que no necesitas nuevos verbos HTTP, hay un sustantivo en alguna parte que significará lo que tienes que hacer.

Compra un auto? Bueno, no es eso

 POST /api/order 

Lo que realmente estás haciendo es crear un orden. Así que agregue otro recurso para ordenar y publicar y colocarlo allí durante el proceso de pedido.

Piense en términos de recursos en lugar de llamadas a métodos.

Para finalizar el pedido probablemente POST / api / order // complete o algo similar.

Considero que las API REST ayudan de muchas maneras más que solo proporcionar semántica. Por lo tanto, no puedo elegir el estilo RPC solo por algunas llamadas que parecen tener más sentido en el estilo de operación RPC. Ejemplo es la API de Google API para encontrar direcciones entre dos lugares. Se ve así: http://maps.googleapis.com/maps/api/directions/json?origin=Jakkur&destination=Hebbal

Podrían haberlo llamado “findDirections” (verbo) y tratarlo como una operación. Más bien hicieron “dirección” (sustantivo) como recurso y trataron encontrar direcciones como una consulta sobre el recurso de direcciones (aunque internamente no podría haber un recurso real llamado dirección y podría ser implementado por la lógica de negocios para encontrar direcciones basadas en params).