La nostra applicazione deve accedere ai dati presenti nel database. Per questo motivo abbiamo creato l'infrastruttura PHP necessaria. Ora dobbiamo chiamare le pagine PHP da Angular, ritirare i dati e usarli nel nostro component.
Per ritirare i dati creeremo e useremo un service, cioè una classe che ci permetterà di condividere le stesse funzionalità fra tutti i component che ne avranno bisogno senza inutili duplicazioni di codice. In pratica si tratta di un modo per astrarre e condividere funzionalità in modo che la nostra applicazione sia organizzata gerarchicamente.
La creazione del service avverrà tramite la CLI dove andremo a digitare:
ng generate service prodotti
L'esecuzione di questo comando ci permetterà di creare nella root del progetto il file prodotti.service.ts
sul quale andremo a lavorare. La prima cosa che notiamo aprendo il file è il decoratore Injectable
che indica che il service potrebbe avere delle dipendenze iniettate, al momento naturalmente non ce ne sono. Per il resto abbiamo solo la definizione della classe.
Dal momento che vogliamo ritirare dei dati, avremo bisogno del servizio http di Angular. Esso non è presente nel core della libreria e va importato, eseguiremo questa operazione nel modulo principale dell'applicazione. Quindi andiamo ad aggiungere al file app.module.ts
l'importazione:
import { HttpModule } from '@angular/http';
Per poter usare il modulo lo aggiungeremo alla lista degli imports:
imports: [
BrowserModule, HttpModule, routing
],
Importato il modulo possiamo importare anche gli oggetti necessari nel service:
import { Http, Response, RequestOptions } from '@angular/http';
import { Observable } from 'rxjs/Observable';
import 'rxjs/add/operator/map';
Il primo è il servizio http che ci permetterà di inoltrare la richiesta asincrona al Web server, tramite la response potremo gestire i dati di ritorno. Qualche spiegazione in più merita invece Observable
che viene definito nella libreria rxjs
a sua volta importata con gli operatori che ci permetteranno di mappare i dati JSON di ritorno.
Per gestire le richieste asincrone Angular utilizza gli Observable al posto delle Promises, un Observable è fondamentalmente un flusso di dati asincrono sul quale noi possiamo lavorare con gli opportuni operatori, come quello che abbiamo importato. I vantaggi legati all'uso di Observable rispetto alle Promises sono diversi: per esempio observable
può essere usato per i Web socket dato che non richiede la fine di un flusso di dati per elaborare la risposta.
Inoltre, mentre le Promises sono legate ad un unico evento, ora possiamo gestire più eventi anche combinando i dati fra di loro o cancellando delle richieste non soddisfatte. In ultimo, se lo desideriamo, possiamo convertire un Observable in una Promise.
Prima di aggiungere un metodo al nostro service, creiamo la classe Prodotti
perché la nostra chiamata restituirà un array di oggetti prodotti.
Il file Prodotto.ts
conterrà la definizione dell'oggetto, questo è uno dei passaggi che segna maggiormente la distanza dalla programmazione JavaScript classica:
export class Prodotto {
constructor(
public id: number,
public nome: string,
public prezzo: number,
public descrizione: string,
public categoria_id: number,
public categoria_nome: string
){}
}
Importiamo la classe nel nostro service:
import { Prodotto } from './prodotto';
Tornando al service, il prossimo passaggio sarà quello di passare l'oggetto Http
che abbiamo importato al costruttore:
constructor(private _http : Http){ }
Aggiungiamo ora un metodo al service che definirà che la risposta sarà un Observable composto da un array di Prodotti:
readProducts(): Observable<Prodotto[]>{
return this._http
.get("http://localhost/phprest/api/v1/prodotti/",)
.map(res => res.json());
}
</Prodotto[]>
Useremo il metodo get
per inoltrare la richiesta all'URL passato come parametro e la risposta sarà elaborata con l'operatore map
importato da rxjs
.
Definito il nostro metodo il prossimo passaggio sarà quello di richiamarlo dal component e preparare la visualizzazione dei dati ottenuti.