Angular 5 - 以同步顺序发出2 GET请求,然后在DataTable中显示数据

时间:2018-05-16 13:56:50

标签: angular

Angular 5: 在一个组件中,我将数据存储在2个数组中,然后显示在DataTable中。

但是如何得到数据需要一些严格的命令:

  1. 在REST控制器上发出GET请求,来自它的数据应存储在第一个数组中。

  2. 使用步骤1中第一个数组的数据在REST控制器上获取请求,来自它的数据应存储在第二个数组中。

  3. 来自1.和2.的数据应显示在DataTable中,有些列保存来自第一个数组的对象的数据,有些列保存来自第二个数组的对象的数据。

  4. 如何实现这一目标? 首先必须执行1.如果完成,则必须执行步骤2.如果完成了第2步,则两个数组中的数据都将显示在DataTable中。

    谢谢!

3 个答案:

答案 0 :(得分:0)

您可以使用带有结果选择器的switchMap RxJS运算符以特定顺序执行这些调用。 switchMap确保先前的observable在开始下一个observable之前完成。结果选择器允许您使用来自第一次和第二次调用的结果的值创建数据结构。此外,您可以使用map RxJS运算符来操作结果,以执行sort,concat或者在observable发出之前需要的任何其他内容。如果你不需要第一个数组,你可以简单地省略switchMap的结果选择器参数,只需使用{{1}在本例的method2()中创建你需要/想要的最终结构/数据}}

虽然此示例显示此操作在map()中执行,但这可以在基本时刻执行,例如使用ngOnInit。将本地属性设置为(click)或空数组null可与[]一起使用,以有条件地呈现数据表元素,直到调用成功完成。使用空数组,您可以检查长度是否大于零。

这种结构还允许您在每个调用中单独进行转换和错误处理,保持清洁和分离。

下面的示例显示了一个简单的服务,其中发出*ngIf个各种数组的Observables正在Component中使用switchMap利用subscribe执行方法/调用switchMap使用对象解析语句从import { Observable } from 'rxjs'; import { map } from 'rxjs/operators'; Injectable() export class SomeService { constructor(private http: HttpClient) {} method1(): Observable<SomeModel[]> { return this.http.get<SomeModel[]>('some/url); } method2(someInput: SomeModel[]): Observable<SomeOtherModel[]> { return this.http.get<SomeModel[]>('some/url).pipe( // you can use the map() operator to do something with the result such as sort, concat, etc before being emitted map(result => result.sort()) ); } } 结果选择器中创建的对象中获取值。此示例使用RxJS 5.5 +。

<强>服务

import { switchMap } from 'rxjs/operators';

@Component({
    template: `
        <button (click)="someMethod()" type="button"></button>
        <div *ngIf="data"><!-- data table --></div>
    `
})
export class SomeComponent {
    // null as to be falsy for the *ngIf
    data: SomeModel[] = null;

    constructor(private someService: SomeServie) {}

    someMethod(): void {
        this.someService.method1().pipe(
            switchMap(
                resultArray1 => this.someService.method2(resultArray1),
                (result1, result2) => ({result1, result2}) // you can omit this if you just want to use the 2nd result array
            )
        )
        .subscribe(results => {
            console.log(results);
            const { result1, result2 } = results;                
            // prepare final data in some way you need  
            const data = [...result1, ...result2];                
            this.data = data;
        });

    }
}

<强>组件:

{{1}}

希望这有帮助!

答案 1 :(得分:0)

这是做你要求的简单方法。

import { Component } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { Observable } from 'rxjs/Observable';

@Component({
  selector: 'app-root',
  templateUrl: 'app/app.component.html'
})
export class AppComponent {
  constructor(private http: HttpClient) { }

  ngOnInit() {
    this.http.get('url1').subscribe(data1 => {

     // process data1 and make call for second type of data

     this.http.get('url2').subscribe(data2 => {
       // process data2
      });

   });
  }
}

答案 2 :(得分:0)

我现在无法采用Staroselsky解决方案,因为我的Angular代码是由JHipster生成的,其中大部分仍然是我所知,但我会尽快尝试。

现在我使用与Sarker类似的解决方案,在GET部分的第二个subscribe请求中添加一个标记(“process data2”),将标记设置为true为表示最终加载了数据。我仍然不确定这个解决方案是否是首选解决方案。

我在TurboTable的*ngIf中使用的那个标志(在它是DataTable之前)。

但我发现了一个奇怪的行为,我在Angular 5 - TurboTable HTML rendering, reload

上发布了这个行为
相关问题