Est-il possible d'injecter de l'interface avec angular2?
je me demande si il ya une bonne façon d'injecter des interfaces dans Angular2? (cf. ci-dessous)
Je pense que c'est lié à l' @Injectable() décorateur sur l'interface, mais il semble que ce n'est pas autorisé.
Ce qui concerne.
Quand CoursesServiceInterface est mis en œuvre comme une interface, le Tapuscrit compilateur se plaint "CoursesServiceInterface ne peut pas trouver de nom":
import {CoursesServiceInterface} from './CoursesService.interface';
import {CoursesService} from './CoursesService.service';
import {CoursesServiceMock} from './CoursesServiceMock.service';
bootstrap(AppComponent, [
ROUTER_PROVIDERS,
GlobalService,
provide(CoursesServiceInterface, { useClass: CoursesServiceMock })
]);
mais avec CoursesServiceInterface comme une interface:
import {Injectable} from 'angular2/core';
import {Course} from './Course.class';
//@Injectable()
export interface CoursesServiceInterface {
getAllCourses(): Promise<Course[]>;//{ return null; };
getCourse(id: number): Promise<Course>;//{ return null; };
remove(id: number): Promise<{}>;//{ return null; };
}
Lorsque le service est d'une classe, le Tapuscrit compilateur ne se plaint pas plus:
import {Injectable} from 'angular2/core';
import {Course} from './Course.class';
@Injectable()
export class CoursesServiceInterface {
getAllCourses() : Promise<Course[]> { return null; };
getCourse(id: number) :Promise<Course> { return null; };
remove (id: number) : Promise<{}> { return null; };
}
Vous devez vous connecter pour publier un commentaire.
Non, les interfaces ne sont pas pris en charge pour les DI. Avec Tapuscrit interfaces ne sont pas disponibles au moment de l'exécution de plus, seulement de manière statique et ne peut donc pas être utilisé comme DI jetons.
Alternativement, vous pouvez utiliser les chaînes de caractères comme des clés ou des
InjectionToken
et de l'injecter comme
Voir aussi https://angular.io/api/core/InjectionToken
La raison pour laquelle vous ne pouvez pas utiliser des interfaces est parce que l'interface est un Tapuscrit au moment de la conception de l'artefact. JavaScript n'est pas avoir des interfaces. Le Tapuscrit de l'interface disparaît de l'JavaScript généré. Il n'y a pas d'interface type d'informations à gauche Angulaire de trouver au moment de l'exécution.
Solution 1:
La solution la plus facile est de définir une classe abstraite qui implémente l'interface. Souvent, vous avez besoin d'une classe abstraite de toute façon.
Interface:
Classe Abstraite:
De La Classe De Béton:
Maintenant, vous pouvez définir votre fournisseur comme d'habitude:
Solution 2:
La documentation officielle de l'Angulaire suggérons d'utiliser la InjectionToken, semblable à OpaqueToken. Voici l'Exemple:
Votre interface et classe:
Définir votre Jeton:
Registre de la dépendance du fournisseur à l'aide de la InjectionToken objet, de l'e.g dans votre application.le module.ts:
Que vous pouvez injecter de l'objet de configuration dans n'importe quel constructeur qui en a besoin, avec l'aide d'un @Inject décorateur:
providers
à quelque chose commeproviders: [{ provide: APP_CONFIG, useClass: AppConfigMockClass }]
Utilisation OpaqueToken, les interfaces ne sont pas pris en charge par DI, dans la mesure où le Javascript lui-même n'avez pas les interfaces. Une façon de le faire dans Angulaire 2 est par l'utilisation de OpaqueToken.
https://angular.io/docs/ts/latest/guide/dependency-injection.html
J'espère que cela peut vous aider.
InjectionToken
que le remplacementMon expérience (en venant de java développement backend) en dev frontend est la suivante.
Si nous parlons de "l'interface" j'ai la forte attente d'un principe essentiel de l'aide de l'interface est assurée par des langues qui "offre" de l'interface.
Qui est: "code à l'encontre de l'interface pas à l'encontre de mise en œuvre".
Ce qui semble ne pas être assuré par le tapuscrit/angular2. (qu'ils ne devraient pas utiliser le mot interface encore, peut-être).
Ce qui était mon cas (attention: je suis en train d'apprendre angular2 donc ma solution de contournement peut sembler moche pour les utilisateurs avancés):
Composante A1 a un enfant de composant B.
Composant B doit savoir de la mère et de l'appeler une méthode sur un parent.
Si le composant B reçoit le parent via DependencyInjection dans son constructeur.
Tout va bien.
Que les choses se compliquent.
Une autre composante A2 peut être à l'origine de la composition. B.
Idéalement, je devrais l'injecter dans B une interface (pas de mise en œuvre) qui est mis en œuvre par A1 et A2, ce qui serait naturellement dans le monde java).
Que B serait de travailler avec cette interface. Si nécessaire, Un transtypage de A2 par exemple, serait de faire de B au courant si l'instance qu'il a est vraiment A2 ou pas.
Je parle de la plaine de composants/classes, et non les services (je vois que la plupart des solutions se réfère aux services).
J'ai essayé d'utiliser @Host(), @Injectable(), OpaqueToken, les Fournisseurs, mais il y avait toujours une erreur. Quand à la fin il semblait travail: en réalité, l'objet injecté dans le Composant B est un objet vide, pas le parent - peut-être que j'ai mal aux fournisseurs et un nouvel objet vide a été créé au lieu d'injecter de l'objet parent.
Ce que j'ai fait à la fin: je n'ai pas utiliser l'interface.
J'ai créé une plaine de la classe de base pour A1 et A2 - appelons-le Rabaisser.
Composant B serait de conserver une référence à cette classe de base. Référence pourrait être défini dans le constructeur comme ceci:
Oui, c'est une étrange solution de contournement, pas sympa (en venant de java mondiale de la pensée, je suis d'accord) mais j'ai juste manqué de temps et a été déçu de la 'interface' chose.
Mis à jour
Je reconsidère la question précédente (c'est une mauvaise conception, de laid ... c'était à mes débuts angulaire)
Maintenant Angulaire de la documentation description claire sur ce problème précis: trouver le parent d'un composant.
Ne pouvez pas utiliser l'interface comme interface ne peut pas être injecté.
"À la recherche pour les composants qui implémentent une interface serait mieux. Ce n'est pas possible parce que la Machine interfaces disparaître de la transpiled JavaScript, qui ne prend pas en charge les interfaces. Il n'y a pas d'artefact de les chercher."
Ne pouvez pas utiliser de la classe de base de parents possibles ni ... (ce qui est la cause de racine de ma avec les précédents désespérée, mauvaise réponse)
Ce qui fonctionne? Technique: trouver un parent par sa classe de l'interface.
Principalement:
Enfant B un parent
Parent
(peut être A1Component ou A2Component)Et la chaque composant parent fournit un
Parent
(au niveau du composant !!!) à l'aide de la classe de l'interface: