Получить данные текущего пользователя в angularfire2 с помощью Ionic

Я ищу, как использовать службы для получения данных пользователя

пользователи.services.ts

import { AngularFire, AuthProviders, AuthMethods, FirebaseListObservable}     


export class Users {
   uid :string = '8fbEOShqIigfA4u84cyvJcLkv5u1';

    constructor(public af: AngularFire) {}

    getUserObservable(){
        return this.af.database.object('/users/' + this.uid);
    }
}

А вот и мой home.ts

import { Users } from '../../services/users.service';

@Component({
  selector: 'page-home',
  templateUrl: 'home.html'
})
export class HomePage {
  user: any;
  isAuthenticated: boolean = true;

  constructor(private userService: Users) {}

  ngOnInit(){
    this.userService.getUserObservable().subscribe((userObject) => {
      this.user = userObject;
      console.log("result : ", this.user);
    });
  }

}

В консоли получаю:

result :  Object {imgLink: "blabla.jpg", money: 0, score: 0, uid: "8fbEOShqIigfA4u84cyvJcLkv5u1", username: "Luis Willnat"…}

Но в ионном представлении:

Cannot read property 'money' of undefined

Думаю, это из-за чего-то асинхронного (в чем я недостаточно хорошо разбираюсь), но не знаю из-за чего..

Большое спасибо за Вашу помощь :)


person luiswill    schedule 27.02.2017    source источник
comment
Что ж, вам действительно нужно выполнить извлечение данных, теперь вы возвращаете только this.user, что, вероятно, не определено. getUser в вашем сервисе должен выполнить запрос и вернуть пользователя компоненту.   -  person AJT82    schedule 28.02.2017
comment
Да, я увидел это через 5 минут после публикации. Я посмотрю в следующий час и обновлю вопрос, если это необходимо, спасибо :)!   -  person luiswill    schedule 28.02.2017
comment
Хорошо, что ты разобрался! Удачного кодирования! :)   -  person AJT82    schedule 28.02.2017
comment
@AJT_82. Сервис не может вернуть пользователя, так как не знает, когда он будет доступен (из-за асинхронного вызова). Сервис может возвращать только наблюдаемую оболочку пользователя.   -  person AngularChef    schedule 28.02.2017
comment
@AngularFrance Да, конечно, я знаю, кажется, я действительно не обращал на это внимания: P Не заметил там подписку ... (кажется, я представил, что это map) Но спасибо, что указали на это! :)   -  person AJT82    schedule 28.02.2017


Ответы (1)


Вам нужно настроить свой код по-другому. Как правило, когда служба оборачивает асинхронные вызовы — любой асинхронный вызов, а не только Firebase — его методы должны возвращать наблюдаемые объекты, а НЕ значения, выдаваемые наблюдаемыми объектами.

Даже если вы хотите, неудобно (или невозможно) пытаться возвращать значения, завернутые в наблюдаемый объект, поскольку они доступны только тогда, когда наблюдаемый объект излучает, и вы не можете контролировать, когда это произойдет.

В соответствии с этими рекомендациями ваш код становится:

@Injectable()
export class UserService {
  constructor(public af: AngularFire) {}
  getUser() {
    // Return the observable. DO NOT subscribe here.
    return this.af.auth;
    // Hint: you could also transform the value before returning it:
    // return this.af.auth.map(authData => new User({name: authData.name}));
  }
}

Затем в вашем компоненте или где вам нужно, вы подписываетесь на получение пользователя:

ngOnInit() {
  this.userService.getUser()
    .subscribe(user => this.user = user);
}
person AngularChef    schedule 27.02.2017
comment
Большое вам спасибо в первую очередь! Я кое-чему научился у тебя! Возможно, я обновлю свой код в этом вопросе, потому что я решил эту проблему, но я думаю, что у меня все еще есть одна небольшая проблема, вероятно, из-за aysnc.. - person luiswill; 28.02.2017
comment
Пожалуйста. Проблема, которая у вас все еще есть, действительно связана с асинхронностью. В своем шаблоне вы, вероятно, пытаетесь отобразить свойства пользователя, такие как {{ user.money }}, но user изначально не определено. Вам нужно защитить ошибку, записывая user? каждый раз, когда вы интерполируете свойство пользователя (например, {{ user?.money }}). АЛЬТЕРНАТИВНО вы можете обернуть все интерполяции {{ user.prop }} в ОДИН большой <div *ngIf="user">...</div>. Если вы считаете, что ответ вас удовлетворил, отметьте его как принятый, спасибо. :) - person AngularChef; 28.02.2017
comment
Woow merci beaucoup, c'est la plus belle selected qui m'arrive aujourd'hui :D Большое спасибо, вы действительно помогли мне, я ценю это! :) - person luiswill; 28.02.2017