In addition to Weibo, there is also WeChat
Please pay attention
WeChat public account
Shulou
2025-04-05 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >
Share
Shulou(Shulou.com)06/02 Report--
This article shows you how to understand Angular services, the content is concise and easy to understand, can definitely brighten your eyes, through the detailed introduction of this article, I hope you can learn something.
Why do you need services?
Components should not get or save data directly, and they should not know whether or not they are displaying fake data. They should focus on displaying data and delegate the responsibility of data access to a service.
You will create a HeroService that all classes in the application can use to get a list of heroes. Instead of using new to create this service, rely on Angular's dependency injection mechanism to inject it into the constructor of HeroesComponent.
Services are a good way to share information between classes that "don't know each other". You will create a MessageService and inject it into two places:
In HeroService, it uses this service to send messages.
In MessagesComponent, it displays the messages in it.
Create HeroService
Create a service called hero using Angular CLI.
Ng generate service hero
This command generates the skeleton of the HeroService class in src/app/hero.service.ts. The code for the HeroService class is as follows:
Src/app/hero.service.ts (new service)
Import {Injectable} from'@ angular/core'; @ Injectable ({providedIn: 'root',}) export class HeroService {constructor () {}} @ Injectable () service
Notice that the new service imports the Injectable symbol of Angular and adds the @ Injectable () decorator to the service class. It marks this class as one of the participants in the dependency injection system. The HeroService class will provide an injectable service, and it can also have its own dependencies to be injected. It is not yet dependent, but it will be soon.
The @ Injectable () decorator accepts the service's metadata object, just as @ Component () does to the component class.
Get hero data
HeroService can get data from anywhere: a Web service, local storage (LocalStorage), or a simulated data source.
Removing the data access logic from the component means that you can change the current implementation at any time in the future without changing any components. These components do not need to know about the internal implementation of the service.
The implementation in this lesson will still provide a list of simulated heroes.
Import Hero and HEROES.
Import {Hero} from'. / hero';import {HEROES} from'. / mock-heroes'
Add a getHeroes method to return the list of simulated heroes.
GetHeroes (): Hero [] {return HEROES;} provides (provide) HeroService
Before you ask Angular to inject HeroService into HeroesComponent, you must provide this service to the dependency injection system. That's what you're gonna do later. You can do this by registering for a provider. The provider creates and delivers the service, which in this case instantiates the HeroService class to provide the service.
Now, you need to make sure that HeroService is registered as a provider of the service. You need to register it with an injector. The injector is an object that is responsible for selecting and injecting the provider as needed.
By default, the Angular CLI command ng generate service registers your service as a provider with the root injector by adding metadata to the @ Injectable decorator.
If you look at the @ Injectable () statement definition immediately before HeroService, you will find that the value of providedIn metadata is' root':
@ Injectable ({providedIn: 'root',}) @
Injectable
({providedIn: 'root',})
When you provide the service at the top level, Angular creates a single, shared instance of HeroService and injects it into any class that wants it. Registering the provider in @ Injectable metadata also allows Angular to optimize by removing services that are completely unused.
To learn more about the provider, see the provider section. To learn more about injectors, see the dependency injection guide.
Now HeroService is ready to be plugged into the HeroesComponent.
This is a transitional code example that will allow you to provide and use HeroService. The code at the moment is very different from the final code.
Modify HeroesComponent
Open the HeroesComponent class file.
Delete the import statement for HEROES, because you will never use it again. Import HeroService instead.
Src/app/heroes/heroes.component.ts (import HeroService)
Import {HeroService} from'.. / hero.service'
Change the definition of the heroes attribute to a simple declaration.
Heroes: Hero []; inject HeroService
Add a private heroService of type HeroService to the constructor.
Constructor (private heroService: HeroService) {}
This parameter does two things at the same time: 1. Declared a private heroService property, 2. Mark it as an injection point for HeroService.
When Angular creates a HeroesComponent, the dependency injection system sets this heroService parameter to the singleton object of HeroService.
Add getHeroes ()
Create a function to get these hero data from the service.
GetHeroes (): void {this.heroes = this.heroService.getHeroes ();} call it in ngOnInit
You can call getHeroes () in the constructor, but that's not best practice.
Keep the constructor simple and do only initialization operations, such as assigning the constructor's parameters to the property. The constructor should not do anything. It certainly should not call a function to make a HTTP request to a remote service, such as a real data service.
Instead, you choose to call getHeroes () in the ngOnInit lifecycle hook, which is then handed over to Angular, which invokes ngOnInit at some appropriate time after constructing an instance of HeroesComponent.
NgOnInit () {this.getHeroes ();} to view the running effect
Refresh the browser and the application is still running as usual. Displays a list of heroes and displays the hero details view when you click on the name of a hero.
Observable (Observable) data
The function signature of HeroService.getHeroes () is synchronized, and its implicit assumption is that HeroService can always get hero list data synchronously. HeroesComponent also assumes that the results of getHeroes () can be fetched synchronously.
This.heroes = this.heroService.getHeroes ()
This is almost impossible in real applications. You can do this now only because the service currently returns mock data. Soon, however, the application is about to get heroic data from a remote server, which is inherently asynchronous.
HeroService must wait for the server to respond, while getHeroes () cannot immediately return hero data, and the browser will not stop responding while the service is waiting.
HeroService.getHeroes () must have some form of asynchronous function signature.
It can use a callback function that returns either Promise (commitment) or Observable (observable object).
In this lesson, HeroService.getHeroes () will return Observable because it will eventually use Angular's HttpClient.get method to get hero data, while HttpClient.get () will return Observable.
Observable object version of HeroService
Observable is a key class in the RxJS library.
In a later HTTP tutorial, you will know that the method of Angular HttpClient will return the Observable of RxJS. In this lesson, you will use RxJS's of () function to simulate the return of data from the server.
Open the HeroService file and import Observable and of symbols from RxJS.
Src/app/hero.service.ts (Observable imports)
Import {Observable, of} from 'rxjs'
Change the getHeroes method to this:
GetHeroes (): Observable {return of (HEROES);}
Of (HEROES) returns an Observable, which emits a single value, which is an array of these simulated heroes.
In the HTTP tutorial, you will call HttpClient.get (), which also returns an Observable, and it also emits a single value from the array of heroes in the HTTP response body.
Subscribe in HeroesComponent
The HeroService.getHeroes method previously returned a Hero [], but now it returns Observable.
You must also look like this form in this service in HeroesComponent.
Find the getHeroes method and replace it with the following code (compared with the previous version):
Heroes.component.ts (Observable)
GetHeroes (): void {this.heroService.getHeroes () .subscribe (heroes = > this.heroes = heroes);}
Heroes.component.ts (Original)
GetHeroes (): void {this.heroes = this.heroService.getHeroes ();}
Observable.subscribe () is the key difference.
The previous version assigned an array of heroes to the component's heroes property. This assignment is synchronous, with the assumption that the server can immediately return an array of heroes or that the browser can freeze the interface while waiting for the server to respond.
This approach doesn't work when HeroService does make a request to a remote server.
The new version waits for Observable to issue this array of heroes, either immediately or in a few minutes. The subscribe function then passes the array of heroes to the callback function, which assigns the array of heroes to the component's heroes property.
With this asynchronous approach, HeroService works when it fetches hero data from a remote server.
Show messa
In this section, you will
Add a MessagesComponent that displays messages in the application at the bottom of the screen.
Create an injectable, full-application-level MessageService for sending messages to be displayed.
Inject MessageService into HeroService.
A message is displayed when HeroService successfully gets the hero data.
Create MessagesComponent
Create a MessagesComponent using CLI.
Ng generate component messages
CLI creates the component file in src/app/messages and declares the MessagesComponent in AppModule.
Modify the template of AppComponent to display the generated MessagesComponent:
/ src/app/app.component.html
{{title}}
You can see the default content from the MessagesComponent at the bottom of the page.
Create MessageService
Use CLI to create a MessageService in src/app.
Ng generate service message
Open MessageService and change its contents to look like this:
/ src/app/message.service.ts
Import {Injectable} from'@ angular/core'; @ Injectable ({providedIn: 'root',}) export class MessageService {messages: string [] = []; add (message: string) {this.messages.push (message);} clear () {this.messages = [];}}
The service exposes its messages cache, as well as two methods: the add () method adds a message to the cache, and the clear () method is used to clear the cache.
Inject it into HeroService
Reopen HeroService and import MessageService.
/ src/app/hero.service.ts (import MessageService)
Import {MessageService} from'. / message.service'
Modify the constructor to add a private messageService property parameter. Angular will inject a singleton of MessageService into this property when creating the HeroService.
Constructor (private messageService: MessageService) {}
This is a typical "service in service" scenario: you inject MessageService into HeroService, and HeroService is injected into HeroesComponent.
Send a message from HeroService
Modify the getHeroes method to send a message when the array of heroes is obtained.
GetHeroes (): Observable {/ / TODO: send the message _ after_ fetching the heroes this.messageService.add ('HeroService: fetched heroes'); return of (HEROES);} display messages from HeroService
MessagesComponent can display all messages, including the one sent when HeroService gets the hero data.
Open MessagesComponent and import MessageService.
/ src/app/messages/messages.component.ts (import MessageService)
Import {MessageService} from'.. / message.service'
Modify the constructor to add a messageService property of public. Angular will inject an instance of MessageService into this property when creating an instance of MessagesComponent.
Constructor (public messageService: MessageService) {}
This messageService property must be a public property because you will bind to it in the template.
Angular binds only to the public properties of the component.
Bind to MessageService
Change the template of the MessagesComponent generated by CLI to this:
Src/app/messages/messages.component.html
Messages clear {{message}}
This template is directly bound to the messageService property of the component.
* ngIf displays the message area only when there is a message.
* ngFor is used to display a list of messages in a series of elements.
Angular's event binding binds the button's click event to MessageService.clear ().
These messages look better when you add the contents of a page of the final code to messages.component.css.
Refresh the browser and the page displays a list of heroes. Scroll to the bottom and you will see a message from HeroService in the message area. Click the "empty" button and the message area is gone.
View the final code
Your application should become such an online example / download example. The code file mentioned on this page is as follows.
If you want to run the examples on this page directly in stackblitz, please click the link: https://stackblitz.com/github/cwiki-us-angular/cwiki-us-angular-tour-of-hero-services
The code mentioned on this page is as follows: https://github.com/cwiki-us-angular/cwiki-us-angular-tour-of-hero-services
The corresponding file list and code links are as follows:
File name
source code
Src/app/hero.service.ts https://github.com/cwiki-us-angular/cwiki-us-angular-tour-of-hero-services/blob/master/src/app/hero.service.tssrc/app/heroes/heroes.component.tshttps://github.com/cwiki-us-angular/cwiki-us-angular-tour-of-hero-services/blob/master/src/app/heroes/heroes.component.tssrc/app/messages/messages.component.tshttps://github.com/cwiki- Us-angular/cwiki-us-angular-tour-of-hero-services/blob/master/src/app/messages/messages.component.tssrc/app/messages/messages.component.html https://github.com/cwiki-us-angular/cwiki-us-angular-tour-of-hero-services/blob/master/src/app/messages/messages.component.htmlsrc/app/messages/messages.component.csshttps://github.com/cwiki-us-angular/cwiki-us-angular-tour-of-hero- Summary of services/blob/master/src/app/messages/messages.component.csssrc/app/app.module.ts https://github.com/cwiki-us-angular/cwiki-us-angular-tour-of-hero-services/blob/master/src/app/app.module.tssrc/app/app.component.htmlhttps://github.com/cwiki-us-angular/cwiki-us-angular-tour-of-hero-services/blob/master/src/app/app.component.html
You refactored the data access logic into the HeroService class.
You register HeroService as the provider of the service in the root injector so that it can be injected elsewhere.
You injected it into the component using the Angular dependency injection mechanism.
You provide an asynchronous function signature for the method of getting data in HeroService.
You found Observable and the RxJS library.
You use the of () method of RxJS to return an observable object (Observable) that simulates hero data.
The HeroService method is called in the component's ngOnInit lifecycle hook, not in the constructor.
You create a MessageService to implement loosely coupled communication between classes.
HeroService is injected into the component along with the service MessageService that is injected into it.
The above is how to understand Angular services. Have you learned any knowledge or skills? If you want to learn more skills or enrich your knowledge reserve, you are welcome to follow the industry information channel.
Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.
Views: 0
*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.
Continue with the installation of the previous hadoop.First, install zookooper1. Decompress zookoope
"Every 5-10 years, there's a rare product, a really special, very unusual product that's the most un
© 2024 shulou.com SLNews company. All rights reserved.