Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Singletons in Ionic 3, Angular 4

Tags:

I am defining service as class, something like this:

@Injectable() export class MyService {  ... } 

In other components or pages, I am importing that class with just import command.

import { MyService } from '../pages/services/myservice'; 

In constructor:

constructor(public _MyService: MyService) 

In my main app.module.ts I have added that class service as provider.

providers: [someOtherThings, MyService, someOtherThings] 

In Ionic 2, things are working as expected. Service is singleton.

But in Ionic 3, which uses angular 4, it looks like every component is creating new instance of that class.

Is there some new way of creating singleton services classes in angular 4?

like image 234
Dragan Malinovic Avatar asked Apr 13 '17 09:04

Dragan Malinovic


2 Answers

Im using ionic 3 with lazyload an angular 4 and not having the issues. To make it singleton make sure your app module provide the service. and remove providers on @Component that use the service.

App Module

@NgModule({   ...    providers: [     StatusBar,     SplashScreen,     { provide: ErrorHandler, useClass: IonicErrorHandler },     Singleton // the service or provider to be single ton   ] }) export class AppModule { } 

The Service

import { Injectable } from '@angular/core'; import 'rxjs/add/operator/map';  @Injectable() export class Singleton {    data = "init data";   constructor() {     console.log('Hello Singleton Provider');   }    set(data){     this.data = data;   }    log(){     console.log(this.data);      } } 

Tes Case the service on ionic page

First Page

import { Component } from '@angular/core'; import { IonicPage, NavController, NavParams } from 'ionic-angular'; import { Singleton } from '../../providers/singleton';  @IonicPage() @Component({   selector: 'page-first',   templateUrl: 'first.html' }) export class FirstPage {   constructor(public navCtrl: NavController, public navParams:    NavParams,private single:Singleton) {   }    ionViewDidLoad() {     console.log('ionViewDidLoad First');     this.single.log(); // log init data;     this.single.set("First singleton data");   }  } 

Second Page

import { Component } from '@angular/core'; import { IonicPage, NavController, NavParams } from 'ionic-angular'; import { Singleton } from '../../providers/singleton';  @IonicPage() @Component({   selector: 'page-second',   templateUrl: 'second.html' }) export class SecondPage {   constructor(public navCtrl: NavController, public navParams:    NavParams,private single:Singleton) {   }    ionViewDidLoad() {     console.log('ionViewDidLoad Second');     this.single.log(); // log First singleton data   }  } 

Third Page it create new instance if providers added on component

import { Component } from '@angular/core'; import { IonicPage, NavController, NavParams } from 'ionic-angular'; import { Singleton } from '../../providers/singleton';  @IonicPage() @Component({   selector: 'page-second',   templateUrl: 'second.html',   providers:[Singleton] // wrong because its create a new instance }) export class ThirdPage {   constructor(public navCtrl: NavController, public navParams:    NavParams,private single:Singleton) {   }    ionViewDidLoad() {     console.log('ionViewDidLoad ThirdPage');     this.single.log(); // log init data   }  } 

make sure to remove the providers on component to make it singleton.

like image 106
Ade Novan Avatar answered Sep 28 '22 23:09

Ade Novan


Try storing the Service's instance in your AppModule and get the instance (instead of instancing it) later in other components.

import {Injector} from '@angular/core';  export class AppModule {     // Allows for retrieving singletons using 'AppModule.injector.get(MyService)' later in the code      static injector: Injector;      constructor(injector: Injector) {         AppModule.injector = injector;     } } 

And to retrive the Service's instance use:

const myService = AppModule.injector.get(MyService); 

Check the documentation Here!

like image 27
SrAxi Avatar answered Sep 28 '22 22:09

SrAxi