Как пройти через метод подписки в Angular 5

Я пытаюсь пройти через метод подписки. Однако порядок, в котором данные помещаются в этот массив this.fieldsList, не согласован. Что может быть причиной?

import { Component, OnInit } from '@angular/core';
import {ActivatedRoute} from '@angular/router';
import { DragulaService } from 'ng2-dragula';
import {MatTableDataSource, MatDialog, MatDialogRef, MAT_DIALOG_DATA} from '@angular/material';
import { DataService } from '../../data.service';
import { ManufacturerAddTabComponent } from './manufacturer-add-tab/manufacturer-add-tab.component';
import { ManufacturerEditTabComponent } from './manufacturer-edit-tab/manufacturer-edit-tab.component';
import { ManufacturerDeleteTabComponent } from './manufacturer-delete-tab/manufacturer-delete-tab.component';
import { ManufacturerOrderTabsComponent } from './manufacturer-order-tabs/manufacturer-order-tabs.component';
import { ManufacturerAddFieldComponent } from './manufacturer-fields/manufacturer-add-field/manufacturer-add-field.component';
import { ManufacturerEditFieldComponent } from './manufacturer-fields/manufacturer-edit-field/manufacturer-edit-field.component';
import { ManufacturerDeleteFieldComponent } from './manufacturer-fields/manufacturer-delete-field/manufacturer-delete-field.component';

@Component({
  selector: 'app-manufacturer-tabs',
  templateUrl: './manufacturer-tabs.component.html',
  styleUrls: ['./manufacturer-tabs.component.css']
})
export class TabsComponent implements OnInit {

  manufacturerId;
  tabId;
  tabsList;
  fieldsList = [];
  rearrangedFields;

  constructor(private _dataService: DataService, public dialog: MatDialog, private route:ActivatedRoute, private dragulaService: DragulaService) {
    dragulaService.dropModel.subscribe((value) => {
      this.onDropModel(value);
    });
  }

  ngOnInit() {
    this.route.params.subscribe(res => this.manufacturerId = res.id);
    this.listTabs();
  }

  addTab(){
    let dialogRef = this.dialog.open(ManufacturerAddTabComponent, {
      width: '400px',
      data: { id: this.manufacturerId }
    });
    dialogRef.afterClosed().subscribe(result => {
      this.listTabs();
    });
  }

  editTab(tabId){
    let dialogRef = this.dialog.open(ManufacturerEditTabComponent, {
      width: '400px',
      data: { id: this.manufacturerId, tabId: tabId }
    });
    dialogRef.afterClosed().subscribe(result => {
      this.listTabs();
    });
  }

  deleteTab(tabId){
    let dialogRef = this.dialog.open(ManufacturerDeleteTabComponent, {
      width: '400px',
      data: { tabId: tabId }
    });
    dialogRef.afterClosed().subscribe(result => {
      this.listTabs();
    });
  }

  listTabs(){
    this.fieldsList = [];
    this._dataService.getManufacturerTabs(this.manufacturerId)
      .subscribe((response) => {
        this.tabsList = response;
        console.info(this.tabsList);
        for (let i=0; i<this.tabsList.length; i++){
          this.listFields(this.tabsList[i].id);
        }
      })
  }

  listFields(tabId){
    this._dataService.getManufacturerFields(tabId)
      .subscribe((response) => {
        this.fieldsList.push(response);
        console.info(this.fieldsList);
      })
  }

  orderTabs(){
    let dialogRef = this.dialog.open(ManufacturerOrderTabsComponent, {
      width: '400px',
      data: this.tabsList
    });
    dialogRef.afterClosed().subscribe(result => {
      this.listTabs();
    });
  }

  addField(tabId){
    let dialogRef = this.dialog.open(ManufacturerAddFieldComponent, {
      width: '400px',
      data: { id: tabId }
    });
    dialogRef.afterClosed().subscribe(result => {
      this.listTabs();
    });
  }

  editField(fieldId){
    let dialogRef = this.dialog.open(ManufacturerEditFieldComponent, {
      width: '400px',
      data: { id: fieldId }
    });
    dialogRef.afterClosed().subscribe(result => {
      this.listTabs();
    });
  }

  deleteField(fieldId){
    let dialogRef = this.dialog.open(ManufacturerDeleteFieldComponent, {
      width: '400px',
      data: { id: fieldId }
    });
    dialogRef.afterClosed().subscribe(result => {
      this.listTabs();
    });
  }

  onDropModel(args) {
      this.rearrangedFields = args[2].children;
      this.orderFields();
  }

  orderFields(){
    for(let i=0; i<this.rearrangedFields.length; i++){
      console.info(this.rearrangedFields[i].id + ' ' + (i+1));
      this._dataService.updateManufacturerFieldsOrder(this.rearrangedFields[i].id, i+1)
      .subscribe((response) => {
        console.info(response);
        this.listTabs();
      })
    }
  }
}

Можете показать, где называется listTabs?

Sébastien S. 02.05.2018 15:25

Я обновил код.

Rahul Dagli 02.05.2018 15:30

добавил свой ответ, попробуй ...

Pranay Rana 02.05.2018 15:40

это сработало для вас?

Pranay Rana 03.05.2018 07:29
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Angular и React для вашего проекта веб-разработки?
Angular и React для вашего проекта веб-разработки?
Когда дело доходит до веб-разработки, выбор правильного front-end фреймворка имеет решающее значение. Angular и React - два самых популярных...
Эпизод 23/17: Twitter Space о будущем Angular, Tiny Conf
Эпизод 23/17: Twitter Space о будущем Angular, Tiny Conf
Мы провели Twitter Space, обсудив несколько проблем, связанных с последними дополнениями в Angular. Также прошла Angular Tiny Conf с 25 докладами.
Угловой продивер
Угловой продивер
Оригинал этой статьи на турецком языке. ChatGPT используется только для перевода на английский язык.
Мое недавнее углубление в Angular
Мое недавнее углубление в Angular
Недавно я провел некоторое время, изучая фреймворк Angular, и я хотел поделиться своим опытом со всеми вами. Как человек, который любит глубоко...
Освоение Observables и Subjects в Rxjs:
Освоение Observables и Subjects в Rxjs:
Давайте начнем с основ и постепенно перейдем к более продвинутым концепциям в RxJS в Angular
1
4
3 932
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Ответ принят как подходящий

вы делаете это неправильно, если у вас есть несколько запросов, тогда используйте mergeMap, прямо сейчас проблема с вашим кодом заключается в том, что вы выполняете асинхронный вызов для каждого идентификатора, и каждый из них занимает разное время для завершения (поэтому, если вы хотите организовать его, вам следует поместите данные в один массив и отсортируйте их, решение ниже сделает это также для вас)

В первом методе listTabs() введите код, как показано ниже

   const ids = [];
   for (let i=0; i<this.tabsList.length; i++){
      ids.push(this.tabsList[i].id);
    }
   this._dataService.getManufacturerFields(ids)
   .subscribe(item => {
    this.items.push(item);
    /*
      sort items by original IDs order 
      because responses might arrived in unordered fashion
      due to network conditions
    */
    this.items.sort((a: Item, b: Item) => {
       const aIndex = ids.findIndex(id => id === a.id);
       const bIndex = ids.findIndex(id => id === b.id);
       return aIndex - bIndex;
    })
  });

в вашем методе обслуживания вы можете закодировать, как показано ниже

getManufacturerFields(ids: number[]): Observable<any> {
  return from(ids).pipe(
    mergeMap(id => <Observable<any>> this.httpClient.get(`item/${id}`))
  );
}

теперь, если вы хотите упорядочить по идентификатору, вам следует сделать


вы также можете использовать метод forkJoin, который дает вам вывод для отправки запроса, но проблема с этим методом заключается в том, что он ожидает, пока все запросы будут конкурировать.

getManufacturerFields(ids: number[]): Observable<any> {
  return <Observable<any>> forkJoin(
    ids.map((id) => {
      return <Observable<Post>> this.httpClient.get(`item/${id}`);
    })
  ).pipe(concatAll());
}

вот статья может вам помочь: https://blog.angularindepth.com/practical-rxjs-in-the-wild-requests-with-concatmap-vs-mergemap-vs-forkjoin-11e5b2efe293

Это происходит потому, что цикл является синхронным, а получение - асинхронным. Таким образом, цикл не ждет, пока метод listFields завершит итерацию.

Другие вопросы по теме