Angular,独立组件之间通信的最佳方式是什么?

时间:2017-12-11 08:35:45

标签: angular components rxjs5 behaviorsubject

我的Angular 4应用程序中有两个组件,比如listComponent& searchComponent没有任何关系。我想在searchComponent中调用一个函数,同时从searchComponent中选择一个搜索条件。 考虑到性能,哪种方法最好,最有效?

或者:

1)我可以将输出事件传递给root并使用数据服务进行数据更改,即切换组件显示并从公共服务获取数据。在这里,我每次都要调用ngAfterViewChecked()或ngOnChange()并使用一些标志来了解从searchComponent中选择的新搜索。

2)在数据服务中使用rxjs / behavioralSubject并从searchComponent设置它并在listComponent中订阅它。

4 个答案:

答案 0 :(得分:1)

如果两个组件之间存在父/子连接,则应使用@Input和@Output。

所以我假设列表组件将搜索条件作为输入,搜索组件在选择项目后发出输出事件。

通过这种方式,您可以在ngOnChanges()上更新列表组件,如果您不想通知列表组件,除非它的输入已更改,请使用ChangeDetectionStrategy.OnPush。

您提到的第二种方法是在单独的服务中使用rxjs / behavioralSubject,您可以从搜索组件中推送搜索条件并在列表组件上订阅该主题。

如果有更多搜索逻辑,您可以获得在Angular上使用服务的好处,并创建处理所有搜索逻辑的搜索服务,包括通知组件。

答案 1 :(得分:1)

几种解决方案:

1 - 使用服务。它应该包含要发出事件的主题,或者至少包含用于存储您在两个组件中设置的数据的数据。

2 - 使用父组件的输出/输入。

3 - 将ViewChild组件与Outputs一起使用。一旦父组件收到输出,它就会通过视图子绑定调用子组件中的metyhod。

答案 2 :(得分:0)

我通常使用主题服务

import {Injectable} from '@angular/core';
import {Observable, Subject} from "rxjs";

/**
 * Event Types
 */
export const MyAppEventTypes =
  {
    EventType1: 'EventType1'
//...
  };
/**
 * Events
 */
export class MyAppEvent
{
  type: string;
  data: any;
}

/**
 * Service in charge of broadcasting messages
 */
@Injectable()
export class MessageService
{
  /**
   * Subject to trigger events
   * @type {Subject<MyAppEvent>}
   */
  private myAppEventSubject: Subject<MyAppEvent> = new Subject<MyAppEvent>();

  /**
   * The observable for events
   * @type {"../../Observable".Observable<MyAppEvent>}
   */
  public readonly myAppEvent$: Observable<MyAppEvent> = this.myAppEventSubject.asObservable();


  /**
   * Broadcasts a message
   * @param name
   * @param data
   */
  broadcast(name: string, data)
  {
    this.myAppEventSubject.next(
      {
        type: name,
        data: data
      });
  }
}

然后,在注入服务

之后需要广播消息的类中
 this.messageService.broadcast(MyAppEventTypes.EventType1, {data: 'test'});

在注入服务后需要接收消息的类中

this.messageService.myAppEvent$.subscribe(ev => {
      if (ev.type == MyAppEventTypes.EventType1)
      {
        this.data = ev.data;
      }
    });

答案 3 :(得分:0)

我认为最好的解决方案是使用ngrx。我使用这几次,它理想地适合这样的问题。