Reputation:
I have a service which has an observable which is subscribed to. The payload is passed onto a subject in the service. However, when I subscribe to the subject in my component, nothing is happening. I should see the console.log
in the .subscribe
method in the ngOnInit
in the component.
I had this same setup working with a previous version which subscribed to an observable resulting from a http.get operation. I want to know why its not working with this version.
The service:
@Injectable()
export class TileService {
availableTiles$ = new Subject<any>();
// The view is expecing an array, else: Error trying to diff '[object Object]'. Only arrays and iterables are allowed
source: {}[] = [
{title: 'Title A'},
{title: 'Title B'}
];
simpleObservable = new Observable((observer) => {
observer.next(this.source);
observer.complete();
});
constructor() { }
getTiles(): void {
this.simpleObservable.subscribe(x => this.availableTilesStream(x));
}
availableTilesStream(data) {
console.log(data); // Logs an array of the two objects from the source array
this.availableTiles$.next(data); // Nothing seems to happen here.
}
}
The component.ts:
@Component({
selector: 'app-available-tiles',
templateUrl: './available-tiles.component.html',
styleUrls: ['./available-tiles.component.css']
})
export class AvailableTilesComponent implements OnInit {
tiles: {}[];
constructor(private tileService: TileService) { }
ngOnInit() {
this.tileService.getTiles();
this.tileService.availableTiles$.subscribe(x => {
console.log('Log from availableTiles$.subscribe in ngOnInit: ', x);
this.tiles = x;
});
}
}
Upvotes: 3
Views: 9250
Reputation: 932
Like Ringo said, the component most likely subscribes after data has been passed (via .next()) to the availableTiles$ Subject.
Seeing as you're using Subject, late subscribers won't receive a value until .next() has been called on the source Subject again.
One solution is to use BehaviorSubject. This means that any subscriber (including late ones) will immediately receive a value.
@Injectable()
export class TileService {
availableTiles$ = new BehaviorSubject<any>([]); // must be initialised with a value
Upvotes: 17