Costruzione URI per API REST e uso di verbi come risorsa?

3

Ho due domande.

1) Ho un problema di comprensione della costruzione URL corretta per un'API REST. Ad esempio,

https://api.context.io/lite/users/id/email_accounts/label/folders/folder/messages/message_id

Qui puoi vedere che la cartella si trova sotto le cartelle, e message_id è sotto i messaggi. È necessario mostrare la risorsa o la raccolta principale. Sarà sbagliato avere un URL come questo?

https://api.context.io/lite/userid/folderid/message_id

Qui, userid, folderid e message_id potrebbero indicare come numeri interi o qualche altro valore. Ovviamente con i valori l'URL non ha senso, ma ha importanza nella transazione m2m? Qual è il modo migliore per costruire l'URL?

2) Va bene avere "verbi" nell'URL? Ho visto i seguenti URL con verbi come "move", "send" nell'URL. È corretto? Se è sbagliato, dovremmo fare tutto come "ricerca" usando solo i parametri?

POST https://outlook.office365.com/api/v1.0/me/messages/{message_id}/move
POST https://www.googleapis.com/gmail/v1/users/userId/messages/send

Per favore condividi i tuoi pensieri. Ho letto molti articoli su questi. Eppure sembra più una scelta personale piuttosto che uno standard del settore. Cosa consiglierebbe il dottor Fielding?

Grazie in anticipo.

    
posta Nalaka Hewapathirana 15.06.2015 - 17:54
fonte

1 risposta

4

1) In genere è meglio essere espliciti sulla visualizzazione delle risorse a riposo. Pertanto, ha senso seguire il paradigma collection/:id/sub-collection/:id con la tua API.

2) È considerato un anti-modello nel mondo REST di utilizzare qualsiasi cosa diversa dai nomi per le tue raccolte nei tuoi URI. Questo perché le migliori pratiche REST si aspettano che la tua "verbiage" giunga sotto forma di verbi HTTP, e non qualcosa che hai deciso di dichiarare da solo. Questo non è un vincolo REST in alcun modo, ma è considerato la migliore implementazione possibile e consente agli sviluppatori di mantenere le cose coerenti.

I verbi HTTP GET POST PUT e DELETE sono adatti per qualsiasi esigenza del programma. Spesso, se ritieni di aver "bisogno di più verbi" per implementare con successo una funzione, significa davvero che devi espandere il tuo pensiero sulla risorsa su cui viene effettuata tale chiamata.

Ad esempio: se volessi accedere a un utente, il mio primo pensiero potrebbe essere quello di mettere quell'azione sulla classe User tramite un metodo User#login . Sarebbe piuttosto strano, però, giusto? Stiamo usando un verbo e ora sappiamo che è un anti-pattern REST.

Invece, se avessimo creato una classe Session associata? Ora possiamo tranquillamente chiamare Session#create su una nuova istanza del modello (che è associata a User ) e rimanere RESTful come al diavolo!

Spero davvero che questo aiuti. Ricorda: in caso di dubbio, tieni presente che, indipendentemente da ciò che stai facendo, la community ha trovato un modo per mantenere le cose RESTful, in quanto ci sono alcune applicazioni GRANDI OL là fuori che aderiscono strettamente alle regole di REST.

Aggiorna

Perché non usare un metodo di classe? Non ho visto il tuo codice, ma presumo che tu stia usando qualcosa come i binari per la tua API.

Potresti fare quanto segue:

///items/index.html.erb
<% form_tag items_path, method: :get do %>
<p>
  <%= text_field_tag :search, params[:search] %>
  <%= submit_tag "Search", name: nil %>
</p>
<% end %>

///items_controller.rb
def index
  @items = Item.search(params[:search])
end

///models/item.rb
def self.search(search)
  if search
    find(:all, conditions: ['name LIKE ?', "%#{search}%"])
  else
    find(:all)
  end
end

Questa è ovviamente una descrizione degli oggetti abbastanza vaga, ma penso che ti verrà un'idea. In questo modo, utilizzi sempre un verbo HTTP GET e lo fai in modo riposante. L'altra opzione, sì, è usare i parametri di query. Questo ti aiuta a evitare di farlo.

    
risposta data 15.06.2015 - 20:46
fonte

Leggi altre domande sui tag