2016-05-29 8 views

risposta

10

Fabbriche, servizi, costanti e valori sono tutti andati in Angular2. Angular2 è radicalmente e fondamentalmente diverso dal classico Angular. In Angular2, i concetti di base sono

  • componenti
  • iniezione di dipendenza
  • vincolante

L'idea di servizi, fabbriche, fornitori e costanti è stata criticata in angolare 1. E 'stato difficile scegli tra uno. Rimozione li semplifica un po 'le cose.

Nel angolare originale, si dovrebbe definire un servizio come modo

app.service('BookService', ['$http', '$q', BookService]); 
function BookService($http, $q){ 
    var self = this; 
    var cachedBooks; 
    self.getBooks = function(){ 
    if (cachedBooks) { 
     return $q.when(cachedBooks); 
    } 
    return $http.get('/books').then(function(response){ 
     cachedBooks = response.data.books; 
     return cachedBooks; 
    }) 
    } 
} 

Angular2 sfrutta in modo significativo la sintassi ES6 per rendere il codice più leggibile e più facile da capire.

Una nuova parola chiave in ES6 è class, che può essere considerata come un servizio.

Le classi ES6 sono uno zucchero semplice rispetto al modello OO basato su prototipo. Avere un'unica comoda forma dichiarativa rende più facili da usare gli schemi di classe e incoraggia l'interoperabilità. Le classi supportano l'ereditarietà basata su prototipi, super chiamate, istanze e metodi e costruttori statici.

Ecco come lo stesso codice potrebbe essere in Angular2

import {HttpService, Promise} from '../Angular/Angular2'; 
export class BookService{ 
    $http, $q, cachedBooks; 
    constructor($http: HttpService, $q: Promise) { 
     this.$http = $http; 
     this.$q = $q 
    } 
    getBooks() { 
    if (this.cachedBooks) { 
     return this.$q.when(this.cachedBooks); 
    } 
    return this.$http.get('/books').then(function(data) { 
     this.cachedBooks = data.books; 
     return this.cachedBooks; 
    }) 
    } 
} 
+11

perché dovresti dire ** servizi ** sono andati in Angular 2? È ancora una grande sezione come concetto generale nel tutorial ufficiale: https://angular.io/docs/ts/latest/tutorial/toh-pt4.html – paradite

+0

Puoi mostrare nella risposta come creare un oggetto condiviso? – zoonman

+0

In seguito a @zoonman, le factory di classe sono anche necessarie per nascondere le dipendenze DI delle classi come mostrato qui: https://angular.io/docs/ts/latest/guide/dependency-injection.html#!#factory-provider – Herc

14

risposta di @pluto Hamilton è apprezzato e in aggiunta a ciò ci sono alcuni punti da notare.

Per fabbriche, servizi e così via, in Angular2 abbiamo il servizio (o servizio condiviso). dobbiamo fare il nostro servizio Injectable per poterlo usare.

NOTA: questo codice appartiene alla versione beta e non RC.

import {Component, Injectable,Input,Output,EventEmitter} from 'angular2/core' 
import {Router} from 'angular2/router'; 
import {Http} from 'angular2/http'; 

export interface ImyInterface { 
    show:boolean; 
} 

@Injectable()  <---------------------------- Very Important 
export class sharedService { <----------------- Service Name 
    showhide:ImyInterface={show:true}; 

    constructor(http:Http;router:Router) 
    { 
    this.http=http; 
    }  
    change(){ 
     this.showhide.show=!this.showhide.show; 
    } 
} 

Se voglio usare ovunque nella mia app, allora devo iniettare questo servizio in funzione di bootstrap come questo,

bootstrap(App, [HTTP_PROVIDERS,sharedService <--------Name Injection 
     ROUTER_PROVIDERS,bind(APP_BASE_HREF).toValue(location.pathname) 
]); 

In questo modo si crea singola istanza del vostro servizio. Se non vuoi andare con una singola istanza, quello che puoi fare è: puoi usare i metadati Providers:[sharedService] nel tuo decoratore @component.

Quindi, utilizzare nel vostro uno dei componenti di questo tipo,

export class TheContent { 
    constructor(private ss: sharedService) { <--------Injection dependency of your newly created service 
    console.log("content started"); 
    } 
    showhide() { 
    this.ss.change(); <----- usage 
    } 
} 

Check working example here

+1

'bind (...). ToXxx (...)' è una sintassi deprecata. Usa invece 'provide (..., {useXxx: ...})' –

+0

Grazie per l'aggiornamento. Non me ne accorgo mentre scrivo questa roba. – micronyks

+0

Questa dovrebbe essere la risposta accettata – Mahesh

5

Non so che cosa fare esattamente fabbriche in Angular1 ma in Angular2 c'è useFactory:

{ 
    provide: SomeClass, 
    useFactory: (dep1, dep2) => (x) => new SomeClassImpl(x, dep1, dep2), 
    deps: [Dep1, Dep2] 
} 

per fornire la propria logica di costruzione dell'istanza se l'impostazione predefinita non corrisponde alle proprie esigenze.

È inoltre possibile iniettare una fabbrica per creare nuove istanze da soli:

/* deprecated or removed depending on the Angular version you are using */ 
provide(SomeClass, { 
    useFactory: (dep1, dep2) => { 
     (x) => new SomeClassImpl(x, dep1, dep2), 
    }, 
    deps: [Dep1, Dep2] 
}) 
constructor(@Inject(SomeClass) someClassFactory: any) { 
    let newSomeClass = someClassFactory(1); 
} 

argomento x deve avere assegnazione del tipo, altrimenti angolare non sa come trattare con essa.

class SomeClassImpl { 
    constructor(x: number, dep1: Dep1, dep2: Dep2){} 
} 
+0

se la proprietà deps è nello stesso scope di useFactory? – smirnov

+0

Hai ragione, grazie mille per averlo indicato :) –

+0

Per quanto mi ricordo, ho risposto a una domanda simile con un Plunker. Sarebbe stata una buona idea anche qui: - /. Grazie ancora per la correzione. –

0

Se avete bisogno di una nuova istanza di un servizio in qualche componente è necessario fornire in tale componente come questo:

@Component({ 
    selector: 'hero-list', 
    templateUrl: './hero-list.component.html', 
    providers: [ HeroService ] 
}) 

Questo genererà una nuova istanza della HereService come fa una fabbrica .

Problemi correlati