godblessstrawberry
godblessstrawberry

Reputation: 5088

Angular share data between service and two components

I need to get Post[] from http and then I display it on post-list component. I can delete some items on post-list template, and edit some items by navigating to another route where I use post-edit component. How do I share same Post[] array between them so the changes will be instantly displayed in the app? I assume I need to store Post[] in the service? what is the correct way to edit/update it from component? here I'm trying to save Post[] array inside service by tap() operator inside the service

  getAllPosts(): Observable<Post[]> {
    return this.http.get<Post[]>("https://jsonplaceholder.typicode.com/posts");
  }

  getAllUsersPosts(userId: number): Observable<Post[]> {
    return this.getAllPosts().pipe(
      map((posts: Post[]) => posts.filter((p: Post) => p.userId === userId)),
      tap(posts => {
        //storing to service
        this.userPosts = posts;
      })
    );
  }

to share the updated Post[] after delete method executed I'm trying to send stored array back to subscriber, but it doesnt help

  deletePost(id: number): Observable<any> {
    return this.http.delete(`https://jsonplaceholder.typicode.com/posts/${id}`).pipe(
      mapTo(res => {
        const index = this.userPosts.findIndex(p => p.id == id);
        // console.log(index);
        this.userPosts.splice(index, 1);
        return this.userPosts;
      })
    )
  }

what is the correct way to achieve this?

Upvotes: 0

Views: 99

Answers (3)

Ram
Ram

Reputation: 611

Create an Behaviour Subject Singleton variable in the service and make it as an observable. Then subscribe to that observable from any component by importing the service, create an instance and subscribe to that observable singleton.

private publisherVariable= new BehaviorSubject<string>('empty')
castVariable = this.publisherVariable.asObservable()
this.publisherVariable.next(DATA_YOU_WANT_TO_SEND)

Upvotes: 1

Vaibhav
Vaibhav

Reputation: 1509

Create a model and create it as a singleton ,use this singleton within your service so same reference gets passed on and updated .Just for an example

export class PostsModel {
    private static instance: PostsModel;
    public prop1: type = '';
    public prop2: type ='';
    static getInstance() {
        if (!PostsModel.instance) {
            PostsModel.instance = new PostsModel();
        }
        return PostsModel.instance;
    }

    static destroyInstance() {
        delete PostsModel.instance;
    }
}

Upvotes: 0

blazehub
blazehub

Reputation: 1960

The persistence of userPosts will depend on the injected scope of service.

Try provding service a module scope or root scope

@module({
  providers:[PostService]
})
export class PostModule{}

Or

@Injectable({
  provideIn:'root'
})
export class PostService{}

Avoid putting postservice as provider both in module and component.

@Componenent({
  providers:[PostService]
})
export class PostComponent{}

Upvotes: 0

Related Questions