1
votes

I've tested this quite a bit and can't understand why below doesn't work. The problem is that after the @Input variable arrives and the user object is retrieved from the service, the ngIf in the template only outputs: "some random text" and none of the user object values. If I switch the ngIf line out with <div *ngIf="userList">{{userList.firstName}} {{userList.lastName}} it works fine (the userList array has firstName and lastName elements too). For some reason it seems can't do it with the promise function getUser. I have tested the promise response with console.log and it is definitely retrieving the data object from the service. I know the tutorial does this type of thing this with routing, but I'm curious what I'm doing wrong here so I can understand what's happening.

import { Component, Input } from '@angular/core';
import { User } from './ViewModels/UserVM';
import { UserList } from './userList';
import { UserService } from './user.service';

@Component({
    moduleId: module.id,
    selector: 'user-form',
    template: `
    <div *ngIf="user">{{user.firstName}} {{user.lastName}} some random text</div>
  `
})

export class UserFormComponent {
    errorMessage: string;
    user: User;
    _selectedUser: UserList;
    @Input()
    set selectedUser(selectedUser: UserList) {
        if (selectedUser) {
            this._selectedUser = selectedUser;
            this.getUser(selectedUser.id);
        }
    }
    get selectedUser() { return this._selectedUser; }


    constructor(private userService: UserService) { }

    getUser(id: number) {
        this.userService.getUser(id).toPromise()
            .then(user => this.user = user)
            .catch(err => this.errorMessage = err);
    }

}

-----UPDATE-----

Turns out I forgot that the User object is not completely flat and firstname and lastname are actually in user.Person.firstName, etc.

3
You should be implemented OnInit and get user in ngOnInit() method.Ha Hoang
I actually tried ngOnInit and it had issues with the variables not being set yet. That's why I tried the setter/getterCrob
You have to make sure the user existed before using *ngIf. So you can check Promise for this.Ha Hoang
What is the exact problem you are facing?Nikhil Shah
"For results I only end up with the "some random text" part of the div. " It should have the values from the user object as well.Crob

3 Answers

1
votes

As you are playing with a promise/callback, you are not sure when data arrives,

So probably you should use ?. operator and don't use ngIf.

<div>{{user?.firstName}} {{user?.lastName}} some random text</div>
1
votes

This was a stupid error on my part. The User object is not flat. It was User.Person.firstName etc.

0
votes

I found that initializing the data where you declare the variable will solve the issue. If you need more control over when your observable changes you may want to look into ChangeDetectorRef and use that to force changes after your promise returns

import (ChangeDetectorRef)

constructor(private ref: ChangeDetectorRef

this.ref.detectChanges();

This will detectChanges for the entire component however, although change detection costs are extremely minute with Angular 2