Vai al contenuto

L’architettura REST

REpresentational State Transfer (REST) è un tipo di architettura software per i sistemi di ipertesto distribuiti come il World Wide Web. I termini “representational state transfer” e “REST” furono introdotti nel 2000 nella tesi di dottorato di Roy Fielding, uno dei principali autori delle specifiche dell’Hypertext Transfer Protocol (HTTP), termine ampiamente usato nella comunità di Internet. fonte Wikipedia

In parole povere, possiamo dire che REST è uno stile di architettura per la progettazione di applicazioni in rete. L’idea è che, invece di usare i meccanismi complessi dei Web Services come CORBA, RPC o SOAP per il collegamento tra host, viene utilizzato il protocollo HTTP per gestire richieste ed effettuare chiamate tra due punti. In effetti lo stesso World Wide Web, che si basa su HTTP, può essere visto come un’immensa architettura basata su REST.

Le applicazioni basate su REST, si definiscono RESTful e utilizzano le richieste HTTP per inviare i dati (creazione e/o aggiornamento), effettuare query, modificare e cancellare i dati. In definitiva, REST utilizza HTTP per tutte e quattro le operazioni CRUD (Create / Read / Update / Delete).

REST e Web Service, quali differenze?

Proprio come un Web Services, un servizio REST è:

  • Indipendente dalla piattaforma
  • Indipendente dalla lingua
  • Basati su standard (HTTP in primis)
  • Può essere facilmente utilizzato in presenza di firewall

REST non offre metodi per gestire sicurezza, crittografia, gestione delle sessioni, garanzie di QoS, proprio come un Web Services ma possono facilmente essere incluse nell’header HTTP:

  • Per motivi di sicurezza, sono spesso utilizzati token nome utente / password.
  • Per la crittografia, REST può essere incluso nell’header HTTPS (secure sockets).

Una buona progettazione REST non contempla cookies: la “ST” di “REST” sta per “State Transfer”, e in effetti, una richiesta REST è del tutto autonoma e indipendente dalle altre, cioè, ogni richiesta porta con sé (durante la comunicazione client/server) tutte le informazioni che il server ha bisogno per completarla. Una richiesta non deve richiedere al server il recupero di un contesto o stato dell’applicazione. Un client REST devo includere nelle intestazioni o nel corpo HTTP tutti i parametri, contesto e dati necessari al server per generare una risposta.

La semplicità di REST

Supponiamo di dover sviluppare una rubrica online che legga i dettagli di uno specifico contatto. Con un Web Services, avremmo bisogno di costruire una richiesta SOAP specificando l’ID dell’utente:

<?xml version="1.0"?>
<soap:Envelope
xmlns:soap="http://www.w3.org/2001/12/soap-envelope"
soap:encodingStyle="http://www.w3.org/2001/12/soap-encoding">
 <soap:body pb="http://www.acme.com/phonebook">
  <pb:GetUserDetails>
   <pb:UserID>12345</pb:UserID>
  </pb:GetUserDetails>
 </soap:Body>
</soap:Envelope>

Questa richiesta SOAP deve essere poi inviata al server tramite una richiesta HTTP POST. Il server elabora e produce una risposta probabilmente in formato XML, che tuttavia verrà incorporata all’interno di un’altra “busta” SOAP.

E con REST? La query per interrogare il server probabilmente potrebbe essere simile a questa:

http://www.acme.com/phonebook/UserDetails/12345

Attenzione: questo non è il corpo di nessuna richiesta, è soltanto un URL che viene inviato al server utilizzando una semplice richiesta GET. Il server elabora e produce dei risultati grezzi, inviati tramite HTTP. Questi dati verranno poi manipolati e utilizzati come si crede.

Si noti che questo non è il corpo della richiesta – è solo un URL. Questo URL viene inviato al server utilizzando una richiesta GET semplice, e la risposta HTTP è il risultato di dati grezzi – non inclusa all’interno di nulla, solo i dati necessari in un modo è possibile utilizzare direttamente. Da questo esempio traiamo già alcuni spunti di riflessione:

  1. E’ facile capire perché i Web Services utilizzino spesso le librerie di supporto per la creazione di richieste SOAP e per analizzare le risposte inviate dal server.
  2. Con REST invece, è sufficiente una connessione di rete ed è possibile testare tutte le API direttamente utilizzando il browser, attraverso gli URL.
  3. Nonostante ciò, esistono librerie REST per semplificare le cose (ne parleremo più avanti)

REST vs SOAP

Una bella analogia di paragone per REST vs SOAP è l’invio di una lettera: con SOAP, si utilizza una busta; con REST, una cartolina. Le cartoline sono più facili da maneggiare, sprecano meno carta (quindi, consumano meno larghezza di banda), e hanno in genere brevi contenuti. (Naturalmente, le richieste non hanno limiti in lunghezza, se usano POST anziché GET).

REST è altrettanto sicuro come SOAP. In particolare, una richiesta REST può essere effettuata su Secure Sockets (utilizzando il protocollo HTTPS), e il contenuto può essere crittografato utilizzando qualsiasi meccanismo. Senza crittografia, REST e SOAP sono entrambi insicuri.

Richieste REST

Per richieste più complesse, REST può facilmente gestire più parametri. Nella maggior parte dei casi, basta utilizzare i parametri passati tramite l’URL.

http://www.acme.com/phonebook/UserDetails?firstName=John&lastName=Doe

Come regola generale, le richieste GET dovrebbero essere query per interrogare il database in sola lettura; non dovrebbero cambiare lo stato del server e dei dati. Per la creazione, l’aggiornamento e la cancellazione dei dati, le richieste sono di tipo post POST, anche se quest’ultimo può essere utilizzato anche per query di la sola lettura, quando sono richiesti parametri complessi (di lunghezza maggiore o binari).

Le richieste REST raramente utilizzano XML. Come mostrato sopra, nella maggior parte dei casi, i parametri di richiesta sono semplici, vengono passati tramite URL e non vi è alcuna necessità di overhead XML. In ogni caso, sia che utilizzate XML che testo semplice, bisogna sempre controllare la validità dei dati in ingresso.

Risposte REST

Una risposta REST è solitamente in formato XML, anche se potrebbe essere utilizzato il formato CSV o JSON. Infatti, a differenza di SOAP, REST non è legato indissolubilmente a XML, ma viene data la scelta al programmatore. Ovviamente, ciascun formato ha i suoi vantaggi e svantaggi. XML è facile da espandere ed è type-safe; CSV è più compatto; JSON è banale da analizzare nei client JavaScript.

Tranne che per specifici casi, i formati accettati sono XML, JSON e CSV. Altri formati, come ad esempio, l’HTML non viene accettato da REST in quanto si tratta di formati destinati al consumo umano e difficilmente interpretabili dai client. L’eccezione è quando il servizio REST deve restituire un documento leggibile (human-readable); altra eccezione è l’interno WWW, se visto come un’applicazione RESTful, scopriamo che le comunicazioni avvengono principalmente in HTML.

API REST

Di seguito, un elenco non esaustivo di fornitori di servizi che utilizzano REST. Da notare che alcuni di essi supportano anche WSDL (Web Services), in modo che lo sviluppatore sia messo nelle condizioni di poter scegliere quale utilizzare; nella maggior parte dei casi, quando entrambe le alternative sono disponibili, le chiamate REST sono più facili da creare e i risultati sono più facili da analizzare e da usare.
TO DO

  • L’API di Google Glass, noto come “Mirror API”
  • Twitter ha delle API REST (è ancora l’API principale utilizzata dagli sviluppatori di applicazioni di Twitter)
  • Flickr
  • Amazon.com offrire diversi servizi REST, ad esempio, per la loro soluzione di storage S3
  • Atom è un’alternativa RESTful a RSS
  • Tesla Model S utilizza delle API tra le interfacce delle auto con le applicazioni Android / iOS

REST e Ajax

In AJAX, le richieste vengono inviate al server tramite l’oggetto XMLHttpRequest. La risposta viene utilizzata dal codice JavaScript per modificare dinamicamente la pagina corrente. Nella maggior parte dei casi, le applicazioni AJAX seguono i principi di progettazione REST. Ogni XMLHttpRequest può essere vista come una richiesta di servizio REST, inviata utilizzando GET. La risposta è spesso in JSON, un formato molto popolare in REST. Per rendere l’applicazione AJAX veramente RESTful, si dovranno seguire i principi di progettazione REST (che discuteremo in seguito).

Quali sono i componenti di un’architettura REST?

  • Risorse (fonti di informazioni), identificate tramite URL logici. Per utilizzare le risorse, le componenti di una rete (componenti client e server) comunicano attraverso una interfaccia standard (ad es. HTTP) e si scambiano rappresentazioni di queste risorse (il documento che trasmette le informazioni). Si deduce che
    • Gli URL logici implicano che le risorse sono universalmente indirizzabili da altre parti del sistema.
    • Le risorse sono l’elemento chiave di un progetto RESTful, al contrario di “metodi” o “servizi” utilizzati nella RPC e SOAP Web Services, rispettivamente. Non esistono chiamate RPC del tipo "getProductName" o "getProductPrice"; piuttosto, i dati di un prodotto sono visti come una risorsa la quale dovrebbe contenere tutte le informazioni richieste (o link ad esso).
  • Una rete di risorse, il che significa che una singola risorsa non dovrebbe essere infinitamente grande e contenere troppi o tutti i dettagli. Ove necessario, una risorsa dovrebbe contenere link a ulteriori informazioni – proprio come nelle pagine web.
  • Il sistema REST ha una banale architettura client-server, ma un componente del server può essere il componente di un altro client.
  • Le interazioni tra client e server devono essere senza stato. Cioè, ciascuna richiesta non ha alcuna relazione con le richieste precedenti e successive. Ogni nuova richiesta deve portare con sé tutte le informazioni necessarie per completare e non deve affidarsi a precedenti interazioni con lo stesso client. Anche se REST preveda la comunicazione stateless, non vuol dire che un’applicazione non deve avere stato. La responsabilità della gestione dello stato dell’applicazione non deve essere conferita al server, ma rientra nei compiti del client.
  • Le risorse dovrebbero essere cachable quando possibile (con una scadenza data / ora). Il protocollo deve consentire al server di specificare quali risorse possono essere memorizzate nella cache e per quanto tempo.
    • Poiché HTTP è universalmente utilizzato come protocollo REST, le intestazioni cache-control HTTP vengono utilizzate per questo scopo.
    • I clienti devono rispettare le specifiche della cache del server per ogni risorsa.
  • I server proxy possono essere utilizzati come parte dell’architettura, per migliorare le prestazioni e la scalabilità. Qualsiasi proxy HTTP standard può essere utilizzato.

Si noti che un’applicazione può utilizzare i servizi REST (come client) senza essere se stessa un’architettura REST.

Alcune linee guida per la progettazione in REST

  1. Non utilizzare URL “fisici”. Un URL fisico punta a “qualcosa” di fisico – ad esempio, un file XML: “http://www.acme.com/inventory/product003.xml”. Un URL logico non implica un file fisico, cioè non usa riferimenti d’implementazione, né indica un tipo di contenuto (MIME) : “http://www.acme.com/inventory/product/003”.
    • Anche con l’estensione .xml il contenuto potrebbe essere generato dinamicamente. Ma dovrebbe essere “umanamente visibile” che l’URL è logico e non fisico.
  2. Non sovraccaricare le query di interrogazione dati. Se necessario, fornire un meccanismo di paging. Ad esempio, una richiesta GET per un elenco dei prodotti” dovrebbe restituire i primi n prodotti (ad esempio, i prima 10), con link successivo / precedente.
  3. Anche se la risposta REST può essere qualsiasi cosa, assicurarsi che sia ben documentata e di non modificare il formato di output (per evitare problemi di lettura / parsering con i client).
    • Ricordate, anche se l’output è “human-readable”, i vostri client non sono umani.
    • Se l’output è in formato XML, assicuratevi di documentare la struttura con uno schema o un DTD.
  4. Piuttosto che lasciare ai clienti l’onere di dover “definire” l’URL per delle azioni aggiuntive (scheda dettagli di un record, ad esempio), meglio includere gli URL con la risposta REST stessa. Ad esempio, se l’output di una lista dei prodotti restituisce un ID per prodotto, lasciare che sia il client a costruire l’URL http://www.acme.com/product/PRODUCT_ID per visualizzare ulteriori dettagli, potrebbe essere considerato cattivo design. Piuttosto, la risposta REST dovrebbe includere l’URL pre-costruito di ogni elemento: http://www.acme.com/product/001263, etc. Vero è che l’output diventa più pesante ma si evitano modifiche al codice dei client ogni qualvolta è necessario effettuare delle modifiche agli URL (cambio del dominio ad esempio).
  5. Le richieste GET non dovrebbe mai provocare un cambiamento di stato nel sistema. Tutto ciò che cambia lo stato del server dovrebbe essere inviato tramite una richiesta POST (o altri comandi HTTP, ad esempio CANC).