Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/angular/26.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Angular2:在组件之间更新和共享数据_Angular_Typescript_Rxjs - Fatal编程技术网

Angular2:在组件之间更新和共享数据

Angular2:在组件之间更新和共享数据,angular,typescript,rxjs,Angular,Typescript,Rxjs,我正试着做一些像这样的东西: 寻找一种方法,使服务在必要时向订阅的组件提供最新数据。例如:Component3将更改写入API>Component1,Component2必须获取最新数据 目前,这两个组件都订阅了服务返回的一个可观察对象,如果两个组件都被呈现,则会导致2个API请求。这感觉不对。据我所知,这些组件应该提供数据,而不是自行请求数据。需要明确的是:此服务返回的数据始终在Component1中使用,而Component2是可选呈现的 以下是我到目前为止所做工作的一些片段和一些描述:

我正试着做一些像这样的东西:

寻找一种方法,使服务在必要时向订阅的组件提供最新数据。例如:Component3将更改写入API>Component1,Component2必须获取最新数据

目前,这两个组件都订阅了服务返回的一个可观察对象,如果两个组件都被呈现,则会导致2个API请求。这感觉不对。据我所知,这些组件应该提供数据,而不是自行请求数据。需要明确的是:此服务返回的数据始终在Component1中使用,而Component2是可选呈现的

以下是我到目前为止所做工作的一些片段和一些描述:

服务通过HTTP从API获取数据Component1Component2订阅了服务返回的可观察项

从“@angular/core”导入{Injectable};
从“@angular/Http”导入{Http};
导入'rxjs/add/operator/map';
@可注射()
导出类组服务{
构造函数(私有http:http){}
getGroups(){
返回此值。_http.get('/assets/groups.json'))
.map((res)=>{
返回res.json();
});
}
}
对于您的用例来说,使用可能是最方便的选择。在服务中注册
BehaviorSubject
,并在任何组件请求新数据时需要更新的所有组件中订阅它

这是服务的外观:

@Injectable()
export class GroupService {

    groupsSource: BehaviorSubject<any> = new BehaviorSubject(null);

    constructor(private _http: Http) { }

    getGroups(): void {
        this._http.get('/assets/groups.json')
            .map((res) => res.json())
            .subscribe((groups) => this.groupsSource.next(groups)); // Update all components subscribed to the BehaviorSubjet
    }
}
组件2,自动更新:

export class Component2 implements OnInit {

    groups: any;

    constructor(private _groupService: GroupService) { }

    ngOnInit() {
        this._groupService.groupsSource.subscribe((groups) => {
            this.groups = groups;
        });
    }
}
使用
BehaviorSubject
可以获得它所持有的最新值,而无需订阅:

export class Component3 implements OnInit{

    groups: any;

    constructor(private _groupService: GroupService) { }

    ngOnInit() {
        this.groups = this._groupService.groupsSource.getValue();
    }
}

与seidme的方法略有不同,我个人更喜欢:

GroupService
中设置数据流,并在组件中使用该数据流

服务:

import { Injectable } from "@angular/core";
import { Http } from "@angular/http";
import { BehaviorSubject } from 'rxjs/BehaviorSubject';
import { Observable } from 'rxjs/Observable';

import 'rxjs/add/operator/map';

@Injectable()
export class GroupService {
    private groupSource = new BehaviorSubject<any>({});
    public group$: Observable = this.groupSource.asObservable();

    constructor(private _http: Http) {}

    getGroups() {
        this._http.get('/assets/groups.json')
            .map((res) => {
                return res.json();
            })
            .subscribe((groups) => this.groupSource.next(groups));
    }
}
然后在模板中,使用
async
管道:
{{{groups | async}}
。它将为您订阅(并处理)可观察到的内容

现在,无论何时从任何组件调用
GroupService.getGroups()
,所有其他组件都将自动更新


另外,使用OnInit比在构造函数中做一些事情更可取,请参见。

这正是我所需要的。谢谢
import { Injectable } from "@angular/core";
import { Http } from "@angular/http";
import { BehaviorSubject } from 'rxjs/BehaviorSubject';
import { Observable } from 'rxjs/Observable';

import 'rxjs/add/operator/map';

@Injectable()
export class GroupService {
    private groupSource = new BehaviorSubject<any>({});
    public group$: Observable = this.groupSource.asObservable();

    constructor(private _http: Http) {}

    getGroups() {
        this._http.get('/assets/groups.json')
            .map((res) => {
                return res.json();
            })
            .subscribe((groups) => this.groupSource.next(groups));
    }
}
import { Component, OnInit } from '@angular/core';
import { router } from '../../app.router';
import { GroupService } from '../../services/group.service';
import { Group } from '../../interfaces/group.interface';
import { Observable } from 'rxjs/Observable';

@Component({
    selector: 'app-sidebar',
    templateUrl: './sidebar.component.html',
    styleUrls: ['./sidebar.component.scss'],
})

export class SidebarComponent implements OnInit {
    router;
    groups: Observable;

    constructor(private _groupService: GroupService){
        this.router = router;
    }

    ngOnInit {
        this.groups = this._groupService.group$;
    }
}