2016-10-24 3 views
1

Прошу прощения, если это основной вопрос с базовым ответом. Я довольно новичок в Angular2 в частности и в разработке в целом, и я застрял.* ngIf проблема синхронизации с firebase

У меня есть сервис, который тянет список из Firebase:

listItems: FirebaseListObservable<any[]>; 
constructor(public af: AngularFire) { 
    this.listItems = af.database.list('items'); 
} 
getFood() { 
    return this.listItems; 
} 

Мой компонент:

list: Observable<any[]>; 
delBtnActive: boolean = false; 
constructor(private dataService: DataSService) { 
    this.list = dataService.getFood(); 
} 

ngOnInit(): void { 
    this.lookForDel(); 
} 

lookForDel() { 
    var found = false; 
    this.list.forEach(items => { 
     items.forEach(item => { 
      if (item.del) {found = true}; 
     }) 
    }); 
    this.delBtnActive = found; 
} 

И, наконец, мой шаблон, который использует delBtnActive булевы:

<button *ngIf="delBtnActive">Confirm Delete</button> 

Все работает здесь, за исключением того, что когда этот маршрут сначала инициализируется, кнопка не отображается на-scr когда он должен быть там. Переключение с этого маршрута на другой, а затем обратно приводит к правильному отображению кнопки. Любое обновление данных о Firebase приведет к правильной работе кнопки.

EDIT: Обратите внимание, что на основе ведомости консоли метод lookForDel() вызывается OnInit. I считает, что ошибка связана с тем, что ngIf происходит до того, как данные загружаются, когда маршрут сначала инициализируется.

Любая помощь по этому поводу или советы в целом были бы очень оценены!

ответ

0

Вместо того чтобы слушать для испускаемых значений с помощью forEach, можно составить наблюдаемый, излучающую логический - указывая, должна ли кнопка быть активной - каждый раз, когда список излучается из вашего Firebase наблюдаемого:

delBtnActive: Observable<boolean>; 

lookForDel() { 
    this.delBtnActive = this.listItems.map((items) => Boolean(items.find(item => item.del)); 
} 

В ваш шаблон, вы бы затем использовать async трубку:

<button *ngIf="delBtnActive | async">Confirm Delete</button> 

Относительно того, почему текущая реализация иногда работает, а иногда нет, единственное объяснение, которое я могу видеть, что иногда й e forEach происходит синхронно, а иногда нет. (С RxJS такая вещь может произойти.)

+0

Извините, все еще привыкнуть к комментариям функциональности. Обратите внимание, что время * только * код, который я использовал выше, НЕ работает при начальной загрузке - он отлично работает каждый раз. Я думаю, что канал Observable w/async - это путь, но я пока не смог заставить его работать правильно. Если вы знаете хороший учебник по правильной настройке, я был бы признателен. – brovery

+0

Может быть [это] (http://briantroncone.com/?p=623) один? Если вы хотите добавить несколько [debug logging] (http://staltz.com/how-to-debug-rxjs-code.html), вы можете поместить оператор 'do' после' map' и записать значение в консоль - проверить, что асинхронный канал подписывается на 'delBtnActive', и что это то, что вы ожидаете. – cartant

Смежные вопросы