ionic2

Using Services

Remarks#

One very important thing about using shared services, is that they must be included in the providers array of the top-most component where they must be shared.

Why is that? Well, Let’s suppose that we include the MyService reference in the providers array from each Component. Something like:

@Component({
  templateUrl:"page1.html",
  providers: [MyService]
})

And

@Component({
  templateUrl:"page2.html",
  providers: [MyService]
})

That way a new instance of the service will be created for each component so the instance where one page will save the data, will be different from the instance used to get the data. So that won’t work.

In order to make the entire app use the same instance (making the service work as a singleton service) we can add its reference in the App Component like this:

@Component({
  template: '<ion-nav [root]="rootPage"></ion-nav>',
  providers: [MyService]
})

You could also add the MyService reference in the ionicBootstrap(MyApp, [MyService]); but according Angular2 style guides

Do provide services to the Angular 2 injector at the top-most component where they will be shared.

Why? The Angular 2 injector is hierarchical.

Why? When providing the service to a top level component, that instance is shared and available to all child components of that top level component.

Why? This is ideal when a service is sharing methods or state.

Why? This is not ideal when two different components need different instances of a service. In this scenario it would be better to provide the service at the component level that needs the new and separate instance.

And

It will work. It’s just not a best practice. The bootstrap provider option is intended for configuring and overriding Angular’s own preregistered services, such as its routing support.

… the App Component would be the best choice.

Share information between different pages

One of the easiest examples of using shared services is when we want to store some data from a given page of our application, and then get that data again but from another page.

One option could be to send that data as a parameter (for instance, if one page calls the other one) but if we want to use that data from a completely different part of the application, that seems to be not the best way to do it. That’s when shared services comes to play.

In this example, we’re going to use a simple service called MyService which only has two simple methods: saveMessage() to store a string and getMessage() to get it again. This code is part of this working plunker where you can see it in action.

import {Injectable} from '@angular/core';

@Injectable()
export class MyService { 
  
  private message: string;
  
  constructor(){ }
  
  public saveMessage(theMessage: string): void {
    this.message = theMessage;
  }
  
  public getMessage(): string {
    return this.message;
  }
}

Then, when we want to store a new message, we can just use the saveMessage(theMessageWeWantToSave); method from the MyService instance (called just service).

import { Component } from "@angular/core";
import { MyService } from 'service.ts';

@Component({
  templateUrl:"page1.html"
})
export class Page1 {
  
  message: string;
  
  // ... 
   
  public saveSecretMessage(): void {
    this.service.saveMessage(this.message);
  }      
}

In the same way, when we want to get that data we can use the getMessage() method from the service instance like this:

import { Component } from "@angular/core";
import { MyService } from 'service.ts';

@Component({
  templateUrl:"page2.html"
})
export class Page2 {
  
  enteredMessage: string;
  
  constructor(private service: MyService) {
    this.enteredMessage = this.service.getMessage();
  }
    
  // ...
}

Please remember to check the Remarks section to see where should the reference for the MyService service be included and why.


This modified text is an extract of the original Stack Overflow Documentation created by the contributors and released under CC BY-SA 3.0 This website is not affiliated with Stack Overflow