angular依赖注入_Angular依赖注入简介

angular依赖注入

by Neeraj Dana

由Neeraj Dana

In this article, we will see how the dependency injection of Angular works internally. Suppose we have a component named appcomponent which has a basic and simple structure as follows:

在本文中,我们将看到Angular的依赖项注入在内部如何工作。 假设我们有一个名为appcomponent的组件,它具有如下基本且简单的结构:

import { Component, OnInit } from "@angular/core";@Component({  selector: "my-root",  templateUrl: "app.component.html",  styleUrls: ["app.component.css"]})export class AppComponent implements OnInit {  ngOnInit(): void {      }}

And we have a service class named GreetingService with a function in it sayHello which has a name as a parameter and returns the name with “Hello” in front of it.

我们有一个名为GreetingService的服务类,其中带有一个函数sayHello ,该函数具有一个名称作为参数,并在其前面返回名称为“ Hello”的名称。

export class GreetingService{  sayHello(name){    return `Hello ${name}` ;  }}

There are two ways to use the service class in the component: first, we can manually create an instance of the service in the component (this is the wrong way and is never recommended).

在组件中使用服务类的方式有两种:首先,我们可以在组件中手动创建服务的实例(这是错误的方式,从不推荐)。

And the other way is to let Angular create the instance of our service and pass that instance to our component internally. This is the common and recommended way to do it.

另一种方法是让Angular创建服务实例并将该实例内部传递给我们的组件。 这是常用的推荐方法。

将我们的服务注入Angular依赖注入系统 (Injecting our service in the Angular dependency injection system)

Import {Component} from '@angular/core';Import {GreetingService} from '. /greetingService';
@Component({  selector: 'my-app',  templateUrl: './app.component.html',  styleUrls: [ './app.component.css' ]})export class AppComponent  {
constructor(private greetingService : GreetingService){   console.log(this.greetingService.sayHello());  }}

Now if you run this project, you will get the error “No provider for GreetingService!”

现在,如果您运行此项目,您将收到错误“ No GreetingService没有提供者!”。

So, basically Angular is complaining that it did not find any provider for creating an instance of the greeting service or it does not know how to create an instance. In order to let the framework know how the instance should be created, we have to pass a provider object to the providers property in the component decorator shown below:

因此,基本上Angular抱怨它没有找到任何创建问候服务实例的提供程序,或者它不知道如何创建实例。 为了让框架知道如何创建实例,我们必须将提供程序对象传递给组件装饰器中的providers属性,如下所示:

import { Component } from '@angular/core';import {GreetingService} from './greetingService';
@Component({  selector: 'my-app',  templateUrl: './app.component.html',  styleUrls: [ './app.component.css' ],  providers:[{      }]})export class AppComponent  {
constructor(private greetingService : GreetingService){   console.log(this.greetingService.sayHello());  }  }

In this provider object, we have many properties so let us understand them one by one.

在此提供程序对象中,我们有许多属性,因此让我们一一理解它们。

定制工厂 (Custom Factory)

use factory: this will tell the framework which factory will be used while creating the object of the service. In our case, we don’t have any factory so let’s create one.

使用工厂:这将告诉框架在创建服务对象时将使用哪个工厂。 在我们的案例中,我们没有任何工厂,因此让我们创建一个工厂。

The factory will be a function which will be responsible for creating and returning the object of the service.

工厂将是一个负责创建和返回服务对象的功能。

export function greetingFactory(){   return  new GreetingService()};
Or more short way
export const greetingFactory= () =>  new GreetingService ();

自定义注入令牌 (Custom Injection Token)

The next thing is to create a property whose value will be an Injection Token instance. Using this property, the framework will uniquely identify our service and will inject the right instance of the service.

接下来的事情是创建一个属性,其值将是“注入令牌”实例。 使用此属性,框架将唯一地标识我们的服务,并将注入正确的服务实例。

var greetingTokken = new InjectionToken<GreetingService>("GREET_TOKEN");

So in the above snippet, we are creating an instance of the InjectionToken class and it is generic. In our case, the GreetingService instance will be injected when someone asks for the injection with name greetingToken.

因此,在上面的代码段中,我们正在创建InjectionToken类的实例,并且它是通用的。 在我们的示例中,当有人要求使用名称greetingToken进行注入时,将注入GreetingService实例。

So far now our code will look like this:

到目前为止,我们的代码将如下所示:

import { Component ,InjectionToken} from '@angular/core';import {GreetingService} from './greetingService';
export const greetingTokken = new InjectionToken<GreetingService>("GREET_TOKEN");export const greetingFactory=()=>  new GreetingService();@Component({  selector: 'my-app',  templateUrl: './app.component.html',  styleUrls: [ './app.component.css' ],  providers:[{    provide  : greetingTokken,    useFactory : greetingFactory,     }]})export class AppComponent  {
constructor(private greetingService : GreetingService){   console.log(this.greetingService.sayHello());  }  name = 'Angular';}

But then also we will have the same error:

但是然后我们也会有同样的错误:

This is because in the constructor, where we are asking for the instance of our service, we have to tell it the unique string of our injection token that is greetingToken.

这是因为在构造函数中,我们在其中请求服务实例时,必须告诉它注入令牌的唯一字符串,即greetingToken

So let’s update our code:

因此,让我们更新代码:

export class AppComponent  {
constructor(@Inject(greetingTokken) private greetingService : GreetingService){   console.log(this.greetingService.sayHello('Neeraj'));  }  name = 'Angular';}

and now we will have the result that allows us to successfully pass a service from Angular dependency injection.

现在,我们将获得的结果使我们能够成功地通过Angular依赖项注入传递服务。

Now let us assume you have some nested dependencies like this:

现在让我们假设您有一些嵌套的依赖项,如下所示:

import{DomSanitizer} from '@angular/platform-browser';
export class GreetingService{  constructor (private domSanitizer:DomSanitizer){      }  sayHello(name){    return `Hello ${name}`  }}

So, in this case, we have to pass one more property to the provider’s object (that is deps) which is the array of all the dependencies:

因此,在这种情况下,我们必须再传递一个属性到提供者的对象(即deps),该对象是所有依赖项的数组:

@Component({  selector: 'my-app',  templateUrl: './app.component.html',  styleUrls: [ './app.component.css' ],  providers:[{    provide  : greetingTokken,    useFactory : greetingFactory,    deps:[DomSanitizer]     }]})export class AppComponent  {
constructor(@Inject(greetingTokken) private greetingService : GreetingService  ){   console.log(this.greetingService.sayHello('Neeraj'));  }  name = 'Angular';}

Up until now, whatever we have done has only been for learning purposes. It is not recommended to create manual providers until there is a need.

到目前为止,我们所做的一切仅是出于学习目的。 不建议在需要之前创建手动提供程序。

So this is all the hard work done by Angular behind the scenes for us. We don’t have to do all this for registering our service. We can actually reduce the code, and instead of passing the factory and token manually, we can ask the framework to do this for us in that case.

因此,这就是Angular在后台为我们完成的所有艰苦工作。 我们不必为注册我们的服务而做所有这一切。 实际上,我们可以减少代码,而不是手动传递工厂和令牌,在这种情况下,我们可以要求框架为我们这样做。

The provide property, which is the injection token, will be the name of the service and Angular will internally create an injection token and factory for us.

提供属性(即注入令牌)将是服务的名称,Angular将在内部为我们创建注入令牌和工厂。

We have to pass one more property (use-class) which tells the framework which class we need to use:

我们必须再传递一个属性(使用类),该属性告诉框架我们需要使用哪个类:

import { Component ,InjectionToken,Inject} from '@angular/core';
import {GreetingService} from './greetingService';
@Component({  selector: 'my-app',  templateUrl: './app.component.html',  styleUrls: [ './app.component.css' ],  providers:[{    provide  : GreetingService,    useClass :GreetingService     }]})export class AppComponent  {
constructor( private greetingService : GreetingService  ){   console.log(this.greetingService.sayHello('Neeraj'));  }  name = 'Angular';}

So now our code looks much cleaner and we can further reduce it by just passing the name of the service. Then Angular under the hood will create the provide object, the factory, and the injection token for us and make the instance available to us when needed.

因此,现在我们的代码看起来更简洁了,我们可以通过传递服务名称来进一步减少代码。 然后,Angular在幕后将为我们创建提供对象,工厂和注入令牌,并在需要时使实例可用。

import { Component } from '@angular/core';
import {GreetingService} from './greetingService';
@Component({  selector: 'my-app',  templateUrl: './app.component.html',  styleUrls: [ './app.component.css' ],  providers:[GreetingService]})export class AppComponent  {
constructor( private greetingService : GreetingService  ){   console.log(this.greetingService.sayHello('Neeraj'));  }  name = 'Angular';}

So in the end, our code looks very familiar. Now in the future, whenever you create a service, you know exactly what steps are involved to get that instance available.

因此,最后,我们的代码看起来非常熟悉。 将来,无论何时创建服务,您都确切知道要使该实例可用需要执行哪些步骤。

If you like this article follow me to get more of this kind of stuff.

如果您喜欢本文,请跟随我获得更多此类内容。

Visit Smartcodehub

前往Smartcodehub

翻译自: https://www.freecodecamp.org/news/angular-dependency-injection-in-detail-8b6822d6457c/

angular依赖注入

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/392429.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

leetcode 85. 最大矩形(dp)

给定一个仅包含 0 和 1 、大小为 rows x cols 的二维二进制矩阵&#xff0c;找出只包含 1 的最大矩形&#xff0c;并返回其面积。 示例 1&#xff1a; 输入&#xff1a;matrix [[“1”,“0”,“1”,“0”,“0”],[“1”,“0”,“1”,“1”,“1”],[“1”,“1”,“1”,“1”,“…

如何查看系统版本

1. winR,输入cmd&#xff0c;确定&#xff0c;打开命令窗口&#xff0c;输入msinfo32&#xff0c;注意要在英文状态下输入&#xff0c;回车。然后在弹出的窗口中就可以看到系统的具体版本号了。 2.winR,输入cmd&#xff0c;确定&#xff0c;打开命令窗口&#xff0c;输入ver&am…

java activemq jmx_通过JMX 获取Activemq 队列信息

首先在 activemq.xml 中新增以下属性在broker 节点新增属性 useJmx"true"在managementContext 节点配置断开与访问服务iP配置成功后启动下面来看测试代码/*** Title: ActivemqTest.java* Package activemq* Description: TODO(用一句话描述该文件做什么)* author LYL…

风能matlab仿真_发现潜力:使用计算机视觉对可再生风能发电场的主要区域进行分类(第1部分)

风能matlab仿真Github Repo: https://github.com/codeamt/WindFarmSpotterGithub回购&#xff1a; https : //github.com/codeamt/WindFarmSpotter This is a series:这是一个系列&#xff1a; Part 1: A Brief Introduction on Leveraging Edge Devices and Embedded AI to …

【Leetcode_easy】821. Shortest Distance to a Character

problem 821. Shortest Distance to a Character 参考 1. Leetcode_easy_821. Shortest Distance to a Character; 完转载于:https://www.cnblogs.com/happyamyhope/p/11214805.html

tdd测试驱动开发课程介绍_测试驱动开发的实用介绍

tdd测试驱动开发课程介绍by Luca Piccinelli通过卢卡皮奇内利 测试驱动开发很难&#xff01; 这是不为人知的事实。 (Test Driven Development is hard! This is the untold truth about it.) These days you read a ton of articles about all the advantages of doing Test …

软件安装(JDK+MySQL+TOMCAT)

一&#xff0c;JDK安装 1&#xff0c;查看当前Linux系统是否已经安装了JDK 输入 rpm -qa | grep java 如果有&#xff1a; 卸载两个openJDK&#xff0c;输入rpm -e --nodeps 要卸载的软件 2&#xff0c;上传JDK到Linux 3&#xff0c;安装jdk运行需要的插件yum install gl…

leetcode 205. 同构字符串(hash)

给定两个字符串 s 和 t&#xff0c;判断它们是否是同构的。 如果 s 中的字符可以被替换得到 t &#xff0c;那么这两个字符串是同构的。 所有出现的字符都必须用另一个字符替换&#xff0c;同时保留字符的顺序。两个字符不能映射到同一个字符上&#xff0c;但字符可以映射自己…

Java core 包_feilong-core 让Java开发更简便的工具包

## 背景在JAVA开发过程中,经常看到小伙伴直接从网上copy一长段代码来使用,又或者写的代码很长很长很长...**痛点在于:*** 难以阅读* 难以维护* sonar扫描结果债务长* codereview 被小伙伴鄙视* ....feilong-core focus on J2SE,是[feilong platform](https://github.com/venusd…

TensorFlow 2.X中的动手NLP深度学习模型准备

简介&#xff1a;为什么我写这篇文章 (Intro: why I wrote this post) Many state-of-the-art results in NLP problems are achieved by using DL (deep learning), and probably you want to use deep learning style to solve NLP problems as well. While there are a lot …

静态代码块

静态代码块 静态代码块&#xff1a;定义在成员位置&#xff0c;使用static修饰的代码块{ }。位置&#xff1a;类中方法外。执行&#xff1a;随着类的加载而执行且执行一次&#xff0c;优先于main方法和构造方法的执行。格式&#xff1a;作用&#xff1a; 给类变量进行初始化赋值…

异步api_如何设计无服务器异步API

异步apiby Garrett Vargas通过Garrett Vargas 如何设计无服务器异步API (How To Design a Serverless Async API) I recently ran a workshop to teach developers how to create an Alexa skill. The workshop material centered around a project to return car rental sear…

C# 序列化与反序列化json

与合作伙伴讨论问题&#xff0c;说到的c与c#数据的转换调用&#xff0c;正好就说到了序列化与反序列化&#xff0c;同样也可用于不同语言间的调用&#xff0c;做了基础示例&#xff0c;作以下整理&#xff1a; 1 using System.Data;2 using System.Drawing;3 using System.Linq…

学java 的要点_零基础学Java,掌握Java的基础要点

对于程序员群体来说&#xff0c;了解一定的技巧会对学习专业技能更有帮助&#xff0c;也更有助于在自己的职业发展中处于有利地位&#xff0c;无限互联Java培训专家今天就为大家总结Java程序员入门时需要掌握的基础要点&#xff1a;掌握静态方法和属性静态方法和属性用于描述某…

实验人员考评指标_了解实验指标

实验人员考评指标In the first part of my series on experimental design Thinking About Experimental Design, we covered the foundations of an experiment: the goals, the conditions, and the metrics. In this post, we will move away from the initial experimental…

leetcode 188. 买卖股票的最佳时机 IV(dp)

给定一个整数数组 prices &#xff0c;它的第 i 个元素 prices[i] 是一支给定的股票在第 i 天的价格。 设计一个算法来计算你所能获取的最大利润。你最多可以完成 k 笔交易。 注意&#xff1a;你不能同时参与多笔交易&#xff08;你必须在再次购买前出售掉之前的股票&#xf…

kotlin编写后台_在Kotlin编写图书馆的提示

kotlin编写后台by Adam Arold亚当阿罗德(Adam Arold) 在Kotlin编写图书馆的提示 (Tips for Writing a Library in Kotlin) Writing a library in Kotlin seems easy but it can get tricky if you want to support multiple platforms. In this article we’ll explore ways f…

1.Swift教程翻译系列——关于Swift

英文版PDF下载地址http://download.csdn.net/detail/tsingheng/7480427 我本来是做JAVA的。可是有一颗折腾的心&#xff0c;苹果公布Swift以后就下载了苹果的开发文档。啃了几天。朦朦胧胧的看了个几乎相同&#xff0c;想静下心看能不能整个翻译出来。我英语一般般&#xff0c;…

核心技术java基础_JAVA核心技术I---JAVA基础知识(集合set)

一&#xff1a;集合了解(一)确定性&#xff0c;互异性&#xff0c;无序性确定性&#xff1a;对任意对象都能判定其是否属于某一个集合互异性&#xff1a;集合内每个元素都是无差异的&#xff0c;注意是内容差异无序性&#xff1a;集合内的顺序无关(二)集合接口HashSet&#xff…

nba数据库统计_NBA板块的价值-从统计学上讲

nba数据库统计The idea is not to block every shot. The idea is to make your opponent believe that you might block every shot. — Bill Russel这个想法不是要阻止每一个镜头。 这个想法是让你的对手相信你可能会阻挡每一个投篮。 —比尔罗素 The block in basketball ha…