I have already consulted other questions regarding this issue but I have not pulled a spider out of the hole. I have to use distinct on an array of objects, with the code that I propose to you the distinct does not work and I have no errors in the console. How can I make it work?
carRecent
export class CarRecent {
id:number;
carId:number;
userId:number;
imageURL:string;
}
carsService
getRecentCars(userId){
let params = new HttpParams().set('userId', userId);
let options = {headers:this.headers, params:params};
return this.http.get<CarRecent[]>(this.host + 'getRecentCars', options);
}
recentCar.component.ts
export class RecentCarsComponent implements OnInit {
url:string = 'assets/';
recentCars = new BehaviorSubject<CarRecent[]>(null);
subscriptionRecentCars;
constructor( public carsService:CarsService, public authService:AuthenticationService ) { }
ngOnInit(): void {
this.loadRecentCars();
}
loadRecentCars(){
this.subscriptionRecentCars = this.carsService.getRecentCars(this.authService.currentUserValue.id)
.pipe(
tap( cars => console.log(cars) ),
distinct( (car:any) => car.carId )
)
.subscribe({
next:cars => {
this.recentCars.next(cars);
}
})
}
}
RxJS operators are often confused with array functions, but they operate on the whole value returned by the observable - they aren't specific to arrays.
In your case you want to return a distinct array of objects based on some key. You want to transform the array returned by the observable to another value - a subset of the array. When transforming data in the pipe, use the map
operator.
Once you're inside the map
operator, you can reduce the array to return distinct values.
ngOnInit() {
this.carsService.getRecentCars(this.authService.currentUserValue.id)
.pipe(
tap(cars => console.log(cars)),
map(cars => {
const uniques = new Set();
return cars.reduce((arr, current) => {
if (!uniques.has(current.carId)) {
arr.push(current);
uniques.add(current.carId);
}
return arr;
}, []);
})
).subscribe({
next:cars => {
this.recentCars.next(cars);
}
});
}
I have used a Set
to avoid redundant array iterations.