У меня есть компонент, который печатает наблюдаемое значение (test $) в шаблон через асинхронный канал.
Свойство компонента необходимо инициализировать на основе входных данных компонента, поэтому я присваиваю его значение наблюдаемой, испускаемой службой (test $) в ngOnInit.Наблюдаемое, предоставляемое сервисом, присваивается комбинации субъектов при инициализации сервиса.Значение не печатается в шаблоне. Stackblitz
Если я определяю объединенные темы как BehaviorSubject, шаблон уведомляется о новом значении.
Я предполагаю, что это как-то связано с холодными / горячими наблюдаемыми.Насколько я понимаю, если вы подписываетесь на BehaviorSubject, вы всегда получите последнее значение, даже если вы подписались после того, как оно отправило значение, но с холодными наблюдаемыми (как субъект) вам необходимо подписаться до того, как значение будет отправлено, чтобы получить уведомление.
Так почему же шаблон не обновляется, если подписка происходит до того, как субъекты выдают значение?Я рассуждаю так: подписка происходит после того, как шаблон был отображен, что находится в ngOnInit.Субъекты не выдают свои значения до тех пор, пока не пройдут этот шаг.
Компонент
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: [ './app.component.css' ]
})
export class AppComponent {
@Input() initialValue: number;
result$: Observable<number>;
constructor(private service: TestService) {
}
ngOnInit() {
console.log('component init');
this.result$ = this.service.result$;
// Get data based on inputs
this.service.initTransformedValue(this.initialValue);
}
}
Сервис
@Injectable()
export class TestService {
result$: Observable<number>;
otherValue$: Observable<number>;
transformedValue$: Observable<number>;
constructor() {
console.log('service constructor');
this.init();
}
init(){
this.result$ = combineLatest(
this.transformedValue$,
this.otherValue$
).pipe(map(([first, second]) => {
console.log('have combined value');
return first + second;
})
);
}
initTransformedValue(initialValue) {
// Use timeout to simulate HTTP calls
setTimeout(() => {
console.log('service. emit transformedValue value');
this.transformedValue$ = of(initialValue * 2);
}, 1000);
setTimeout(() => {
console.log('service. emit otherValue value');
this.otherValue$ = of(initialValue * 4);
}, 1200);
}
}
Шаблон
<p>{{result$ | async}}</p>