0

I am using Angular2 and displaying a variable on the page. The page has a button that I click and a data service is invoked. Inside the dataservice call, I change the value of the variable and expect the change to be reflected on the page. However, I still see the old value. Only when I click on another link and then come back to this page, do I see the new value reflected. Any changes to the variable that I make outside a dataservice call is reflected immediately. Only the changes within the dataservice call is not reflected: Below is some code snippet:

HTML template:

<button type="button" class="btn (click)="clickNextButton()">
    <span>save</span>  
</button>

{{text}}

Typescript class

export class ConfigComponent implements OnInit {
    public text = '';

    ..
    ..
    private clickNextButton(): void {
        this.text = 'abc;
        this.dataService.getConfig()
            .then((config: IConfig): void => {
            console.log('printed');
            this.text = 'xyz';
            console.log('printed..');
        });
    }
}

So, I click on the button and the value changes to abc on the page but it does not change to xyz. console logs are printed fine, so I know for sure that the code is reached. Why the changes I make to the variable inside the dataservice call not getting reflected on the page? How do I fix this issue?

Update:

This issue occurs only when the component is included and used in another component, as:

 <prod-setup
     ....
 </prod-setup>   

When I change variable value in the dataService call of the main component, it changes and reflects fine on the view. Only when I change a variable in the Data Service call of the included component, it doesn't reflect on the UI. Any idea?

user1892775
  • 2,001
  • 6
  • 37
  • 58

3 Answers3

0

Maybe your async call is outside ngZone thus not triggering the UI update (Angular optimizes the app performance running async calls outside zone). You can put your code inside zone detection:

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

export class ConfigComponent implements OnInit {
    public text = '';
    public constructor(private ngZone: NgZone) { }

    ..
    ..
    private clickNextButton(): void {
        this.text = 'abc;
        this.ngZone.run(() => {
            this.dataService.getConfig()
                .then((config: IConfig): void => {
                console.log('printed');               
                this.text = 'xyz';                             
                console.log('printed..');
            });
        });
    }
}
Pedro Arantes
  • 5,113
  • 5
  • 25
  • 60
  • Doesn't fix the issue – user1892775 Dec 29 '17 at 04:53
  • All right. Try to change the call of angular zone run - I edited my answer and `this.ngZone.run` is encompassing `this.dataService.getConfig()` – Pedro Arantes Dec 29 '17 at 04:56
  • I added a section 'Update' under the original question. The issue seem more specific when I am changing a variable in an included component and not in the main component. Any idea why? – user1892775 Jan 08 '18 at 01:57
  • Are you providing the service only once? I mean, are you providing `dataService` only in some main module which contains the views, i.e. `app.module.ts`? – Pedro Arantes Jan 08 '18 at 09:51
  • yes, and infact this problem occurs even with code in setTimeout. Any variable set instantly is reflected on the UI. anything thats within a DataService call or setTimeout etc is not reflected (only when its an included component in the main component) – user1892775 Jan 08 '18 at 16:40
0

You can also use resolve() so the calling function gets notified and can perform any post processing.

private clickNextButton(): void {
        this.text = 'abc;
        this.dataService.getConfig()
            .then((config: IConfig): void => {
            console.log('printed');
            this.text = 'xyz';
            this.text = resolve();     

        });
    }

Another option would be to call another function that will set the value

     private clickNextButton(): void {
        this.text = 'abc;
        this.dataService.getConfig()
            .then((config: IConfig): void => {
            console.log('printed');
            this.text = 'xyz';
            this.text = resolve('xyz');
            this.setValue();     

        });
    }
    setValue(): void{
        this.text
    }
edkeveked
  • 17,989
  • 10
  • 55
  • 93
0

is this.text of the dataservice not out of scope? ie, try : private clickNextButton =(): void => { could also setup message service that returns a message to the component when updated.

angular 4 service cannot read property 'newService' of undefined

oudekaas
  • 325
  • 1
  • 6
  • 21