Est-il correct de transmettre le "courant" $scope
à un service AngularJS?
Je suis dans la situation où j'ai un service $ sachant qu'il est consommé par un seul contrôleur, et j'aimerais avoir une référence à la portée du contrôleur dans les méthodes $ service elles-mêmes.
Est-ce philosophiquement correct?
Ou je ferais mieux de diffuser des événements sur $ rootScope et de faire en sorte que mon contrôleur les écoute?
$scope
propriétés et appeler en$scope.$apply
cas de besoin.$scope
... comment le contrôleur accède-t-il directement aux données du service et les transmet à la vue sans faire cela?Réponses:
Pour informer le contrôleur lorsqu'un événement asynchrone se produit, utilisez les promesses angulaires .
Pour provoquer le
$apply
, vous n'avez pas besoin de la portée, vous pouvez appeler$rootScope.$apply
, car il n'y a aucune différence en l'appelant dans une portée spécifique ou à la racine.En ce qui concerne la lecture des variables, il serait préférable que vous receviez des paramètres. Mais vous pouvez également le lire à partir d'une portée en tant que paramètre d'objet, mais j'irais avec un paramètre, ce qui rendrait votre interface de service beaucoup plus claire.
la source
$scope
via un appel à un service utilisant uneexecuteSql()
fonction asynchrone . En regardant dans 3 options (1) utiliser un rappel sur la fonction async, puis appeler$scope.$apply
... cela fonctionne, mais c'est moche (2) passer$scope
à la fonction asynchrone, puis appelertheScope.$apply()
... cela fonctionne aussi (3) utiliser une promesse. ..pas encore essayé. Pourquoi une promesse est-elle le meilleur moyen? Merci!Je dirais que si votre fonctionnalité est spécifique à un seul contrôleur, vous n'avez pas besoin d'un service.
Les tâches des contrôleurs sont de manipuler le modèle spécifique alors qu'un service doit traiter des tâches globales. Je préfère m'en tenir à ce paradigme au lieu de mélanger les choses.
C'est ce que disent les documents
Un service
Manette
PS: En dehors de cela, si vous avez besoin de digérer, vous pouvez également injecter le $ rootScope dans votre service.
la source
$apply
ou$digest
sur le $ rootScope a tout à fait un sens pour moi.Oui. Vous pouvez transmettre la portée $ au service lorsque vous l'initialisez. Dans le constructeur de service, vous pouvez attribuer la portée à quelque chose comme ceci._scope puis référencer la portée dans le service!
la source
$scope
fois que ce contrôleur donné injecte le service - afin de ne pas avoir à appeler une méthode sur le service et à lui passer manuellement$scope
.new MyFunction()
). La question portait sur un service, où l'appelnew
n'est pas une option.Personnellement, je pense que passer
$scope
à un service est une mauvaise idée , car cela crée une sorte de référence circulaire: le contrôleur dépend du service et le service dépend de l'étendue du contrôleur.En plus d'être déroutants en termes de relations, des choses comme celle-ci finissent par gêner le ramasse-miettes.
Mon approche préférée consiste à placer un objet de domaine dans la portée du contrôleur et à le transmettre au service. De cette façon, le service fonctionne indépendamment du fait qu'il soit utilisé dans un contrôleur ou peut-être dans un autre service à l'avenir.
Par exemple, si le service est censé pousser et extraire des éléments d'un tableau
errors
, mon code sera:Le service interagit alors avec le contrôleur en fonctionnant sur
errors
. Bien sûr, je dois faire attention à ne jamais effacer toute la référence du tableau, mais en fin de compte, c'est une préoccupation générale de JS.Je ne voudrais jamais utiliser la diffusion
$apply
et / ou des choses similaires, car à mon avis, les bonnes pratiques OO l'emporteront toujours sur la magie angulaire.la source
$scope.errors = []; $scope.myService = new MyService($scope.errors);
errors
vit indépendamment de$scope
. C'est tout l'intérêt de cette réponse. Veuillez vérifier le lien que j'ai fourni dans le texte. À votre santé.$scope.errors
pointe versvar errors
, et les erreurs variables me semblent redondantes, car ce n'est qu'un autre pointeur. Une situation similaire je peux penser et qu'il est manifestement est redondant ce morceau de code:const errors = errors2 = errors3 = []; $scope.errors = errors;
. Êtes-vous d'accord avec le fait qu'avec seulement le morceau de code que vous avez fourni, cela semblevar errors = []
redondant?errors
vit indépendamment de$scope
. Vous devez comprendre ce qu'est un objet de domaine, ainsi que ce qu'est unevar
affectation. Si le lien que j'ai fourni n'est pas suffisant, il existe de nombreux autres documents disponibles.MyService(errors)
. Dans ma compréhension, le service devrait générer un tableau de journalisation basé sur le paramètre (c'est-à-dire dans ce cas un pointeur). Pour moi, c'est un mauvais schéma, car les services sont des singletons anguleux. Si l'implémentation du service est bien programmée, elle doit générer le tableau dans une variable interne (pour rester un singleton). Par conséquent, il n'a aucun sens d'initialiser la variable en dehors du service.