具有多个数据的Angular 5共享服务

时间:2018-04-05 15:24:49

标签: angular typescript angular5

在互联网上,我找到了如何与服务共享数据的示例:

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

@Injectable()
export class DataService {

  private subject = new Subject<any>();

  sendData(phone: any) {
    this.subject.next(phone);
  }

  clearData() {
    this.subject.next();
  }

  getData(): Observable<any> {
    return this.subject.asObservable();
  }

}

然后我们订阅了更改

subscription: Subscription;

this.subscription = this.dataService.getData()
  .subscribe(data => {
     this.someData= data;
  });

好的,这很好用。但是,如果我想分享多个元素?为每个元素复制此代码似乎是不合理的,只更改名称。但我找不到任何抽象的解决方案。也许使用带有名称和数据本身的地图,但我无法理解如何在这种情况下订阅更改以及应该如何看待服务。

2 个答案:

答案 0 :(得分:7)

要实现此目的,您可以将所有相关值放入(行为)主题中此对象的包装器对象中。每个订阅者更改其感兴趣的个人价值的内容,然后写回整个包装。

e.g。

假设您将定义的所有模型放入models.ts中。这是包装器。

export class MyWrapper {
   constructor(
      public value1?: string,
      public value2?: number,
      public value3?: boolean
   ){}
}

然后将此包装器模型导入您的服务和所有订阅者

import { Injectable } from '@angular/core';
import {Subject} from 'rxjs/Subject';
import {Observable} from 'rxjs/Observable';
import { MyWrapper } from '../models/models';

@Injectable()
export class DataService {

  private subject = new Subject<MyWrapper>();

  sendData(wrapper: MyWrapper) {
    this.subject.next(wrapper);
  }

  clearData() {
    this.subject.next();
  }

  getData(): Observable<MyWrapper> {
    return this.subject.asObservable();
  }

}

在其中一个订阅者中,无论是服务,指令还是组件,您都可以操纵该值。只是一个例子!如何来回处理包装器有很多不同的方法。

import { MyWrapper } from '../models/models';

private localWrapper: MyWrapper;

constructor(
 private dataService: DataService
){}

ngOnInit(): void {
   this.dataService.getData().subscribe(wrapper => {
      this.localWrapper = wrapper;
   });
}

// The wrapper in your service gets replaced and all subscribers
// get a fresh version of all contained values. This way you
// could exchange hundreds of values with only one set of methods
// and a single (Behavior)Subject.
private saveValue1(value: string): void {
   localWrapper.value1 = value;

   this.dataService.sendData(localWrapper);
}

答案 1 :(得分:1)

我认为您要搜索的解决方案与ngrx库类似。在这种情况下你想要做的是创建一个具有不同数据层(电话,地址,名称等)的对象并将其放入BehaviorSubject中。然后,每个订阅者都可以通过使用rxjs.的pluck运算符来提取必要的信息层。要改变某些数据层,你必须通过应用扩展运算符来改变不可变数据的变化,只改变你需要的层,而其他层保持不变。

相关问题