Pratica "migliore" per una risposta POST riposante


217

Quindi niente di nuovo qui sto solo cercando di ottenere alcuni chiarimenti e non riesco a trovarne nessuno in altri post.

Sto creando una nuova risorsa in modo irrequieto, ad esempio:

/books (POST)

con un corpo:

{
  title: 'The Lion, the Witch and the Wardrobe',
  author: 'C. S. Lewis'
}

So che dovrei restituire un 201 (creato) con un'intestazione Location della nuova risorsa:

Location: /books/12345

La domanda a cui non riesco a rispondere da solo è cosa dovrebbe restituire il server nel corpo.

Ho spesso fatto questo tipo di risposta:

{
  id: 12345,
  title: 'The Lion, the Witch and the Wardrobe',
  author: 'C. S. Lewis'
}

L'ho fatto per un paio di motivi:

  1. Ho scritto api per framework front-end come angularjs. Nel mio caso particolare sto usando risorse angolari e spesso ho bisogno solo dell'id per la risorsa per individuarlo. Se non restituissi l'id nel corpo della risposta, dovrei analizzarlo dall'intestazione Location.
  2. In un GET di tutti i libri di solito restituisco l'intero oggetto non solo l'ID. In questo senso il mio codice cliente non deve differenziare da dove ottenere l'id (intestazione o corpo della posizione).

Ora so di essere davvero nell'area grigia qui, ma la maggior parte delle persone sta dicendo che restituire l'intera risorsa è una pratica "cattiva". Ma cosa succede se il server modifica / aggiunge informazioni alla risorsa. Aggiunge sicuramente l'id, ma potrebbe anche aggiungere altre cose come un timestamp. Nel caso in cui non restituisca l'intera risorsa, è davvero meglio fare un POST, restituire l'id, quindi fare in modo che il client esegua un GET per ottenere la nuova risorsa.


Personalmente preferisco il corpo vuoto per le risposte POST. Il valore dell'intestazione RESTful Location non dovrebbe essere un URI (identificatore di risorsa univoco)? Quindi forse dovresti usarlo come ID e non analizzarlo per capire un ID interno del server. I consumatori IMO, RESTful API dovrebbero navigare utilizzando i collegamenti ipertestuali forniti e non creare percorsi, indovinando dove un determinato server individua le risorse ... E dopo tutto, il client non conosce già lo stato della risorsa che ha appena creato? ripeterlo rappresenta uno spreco di risorse di rete.
ch4mp,

1
Per Crea / Inserisci, Stato 201 - CREATO, Posizione intestazione → localhost: 8080 / impiegati / 1 (vedi: qui )
Hassan Tareq

Risposte:


129

Restituire l'intero oggetto su un aggiornamento non sembrerebbe molto rilevante, ma difficilmente riesco a capire perché restituire l'intero oggetto quando viene creato sarebbe una cattiva pratica in un normale caso d'uso. Ciò sarebbe utile almeno per ottenere facilmente l'ID e per ottenere i timestamp, se pertinenti. Questo è in realtà il comportamento predefinito ottenuto durante i ponteggi con Rails.

Non vedo davvero alcun vantaggio nel restituire solo l'ID e fare una richiesta GET dopo, per ottenere i dati che potresti avere con il tuo POST iniziale.

Comunque, purché la tua API sia coerente, penso che dovresti scegliere il modello che si adatta meglio alle tue esigenze. Non esiste un modo corretto per creare un'API REST, imo.


26
So che questo è vecchio, ma posso dare un argomento convincente per l'utilizzo di un GET dopo il tuo POST. Nelle specifiche http / 1.1 qualsiasi strumento storico può ignorare le impostazioni della cache restituite dalla risposta GET ... quindi se l'utente utilizza il pulsante Indietro nel browser per tornare a questa pagina dopo averlo aggiornato con il POST, può usare stantio dati memorizzati nella cache dal GET originale. Quindi, se riutilizzi GET, puoi aggiornare la cache e ottenere una migliore istantanea dell'aspetto della pagina quando sono partiti ...
Ombreggiato il

8
@Shaded Se l'API è progettata per essere utilizzata anche dalle app, l'argomento per fare due richieste non è valido. Lì, di solito si memorizzano nella cache i dati mantenendo in memoria oggetti di un tipo di modello, che in genere viene fatto con la risposta per le richieste POST. E per quanto riguarda i browser, la risposta su una richiesta POST non fa davvero male fino a quando esiste ancora un endpoint GET api.
Jeehut,

Sottoscrivo ciò che Daniel afferma qui. Anche se si controllano framework maturi come Spring Data, restituiscono sempre l'intero oggetto dopo averlo persistito. Penso che sia una buona pratica, poiché nel tuo client salverai un server di andata e ritorno per ottenere le stesse informazioni
frandevel

205

La restituzione del nuovo oggetto si adatta al principio REST di "Interfaccia uniforme - Manipolazione delle risorse tramite rappresentazioni". L'oggetto completo è la rappresentazione del nuovo stato dell'oggetto che è stato creato.

C'è un riferimento davvero eccellente per la progettazione dell'API, qui: Best practice per la progettazione di un'API RESTful pragmatica

Include una risposta alla tua domanda qui: Aggiornamenti e creazione dovrebbero restituire una rappresentazione delle risorse

Dice:

Per impedire a un consumatore di API di dover premere nuovamente l'API per una rappresentazione aggiornata, fare in modo che l'API restituisca la rappresentazione aggiornata (o creata) come parte della risposta.

Mi sembra ben pragmatico e si adatta al principio REST che ho menzionato sopra.


6
che ne dici di restituire l'intero set di oggetti rilevanti? in questo modo, il possibile ordinamento può essere eseguito sul lato server e facilita l'implementazione del front-end
phil294

2
Ma queste migliori pratiche non sono le migliori. L'autore afferma che HATEOAS, che è importante come gli altri principi, non deve essere utilizzato perché "non è pronto". HATEOAS non sarà mai "pronto", perché tutti i principi RESTful sono solo principi di progettazione architettonica, non implementazione specifica. Il riferimento citato riguarda la visione dell'autore sull'API RESTful, che non è affatto RESTful a causa della caduta di HATEOAS. Ecco perché questo non è il miglior riferimento :)
marcinn

1
@marcinn - noterai che la domanda originale aveva delle citazioni su "Best", immagino perché c'è molta opinione in questo settore. Il riferimento che ho indicato è qualcosa che ho trovato pratico. Se hai un riferimento migliore, condividilo. Sono sempre aperto a saperne di più.
Grahamesd,

@grahamesd Un'implementazione è una cosa diversa dal principio / modello di progettazione architettonica. Nessuno può aspettarsi che HATEOAS sarà pronto un giorno, ma c'è la possibilità che qualcuno crei un'implementazione accettabile da molti. Vinay ha anche scritto sulla mappatura dei metodi http su URL e operazioni specifiche (CRUD), ha affermato che il controllo delle versioni mediante prefisso URL è più pragmatico, ha scritto che filtrare in base ai parametri della query è una strada da percorrere ... va bene, ma tutto ciò ha poco da fare con l'architettura RESTful. Scrisse di una specie di contratto. Va bene per l'API HTTP, ma non chiamarlo RESTful.
marcinn,

@grahamesd Ecco alcuni post che spiegano questo: - medium.com/@andrea.chiarelli/… - restfulapi.net
marcinn
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.