Чтобы обновить компонент после выполнения операции POST - PullRequest
0 голосов
/ 21 марта 2019

У меня есть компонент с именем customers-list, где я отображаю всех своих клиентов из API:

клиенты-list.html

<div *ngFor="let customer of customers">
     <p>{{customer.name}</p>
</div>

клиенты-list.ts

import { Component Input} from '@angular/core';
import { ICustomer} from 'src/app/models/app.models';
import { CustomersService } from 'src/app/services/customers.service';

@Component({
  selector: 'drt-customers-list',
  templateUrl: './customers-list.component.html',
  styleUrls: ['./customers-list.component.scss'],
})
export class CustomerListComponent {
 public customers:  ICustomer[] ;

 constructor(public customersService: CustomersService,) {}

  public async ngOnInit(): Promise<void> {
    this.customers = await this.customersService.getCustomersList('');
  }

}

У меня есть еще один компонент с именем add-customer, в который я добавлю нового клиента, например:

public onaddCustomer(): void {
    this.someCustomer = this.addCustomerForm.value;
    this.customersService.addCustomer( this.someCustomer).subscribe(
      () => { // If POST is success
        this.successMessage();
      },
      (error) => { // If POST is failed
        this.failureMessage();
      }
    );

  }

Теперь POST операция происходит нормально, но customer-list не обновляется без обновления страницы.

Как я могу обновить компонент customers-list после успешной операции POST, не обновляя всю страницу?

файл услуг:

import { HttpClient } from '@angular/common/http';
import { Injectable } from '@angular/core';
import { ICustomer} from 'src/app/models/app.models';
import { Observable } from 'rxjs';

@Injectable({
  providedIn: 'root',
})

export class CustomersService {
 private  baseUrl : string = '....api URL....';

  public async getCustomersList(): Promise<ICustomer[]> {
    const apiUrl: string = `${this.baseUrl}/customers`;

    return this.http.get<ICustomer[]>(apiUrl).toPromise();
  }

public addCustomer(customer: ICustomer): Observable<object> {
  const apiUrl: string = `${this.baseUrl}/customers`;

  return this.http.post(apiUrl, customer);
}


}

Ответы [ 3 ]

1 голос
/ 22 марта 2019

Основная причина, по которой он не обновляется, потому что ngOnIniit выполняется только во время инициализации. Я предполагаю, что вы не используете какую-либо библиотеку управления состоянием (хранилище данных), поэтому лучшим решением будет использование Subject в CustomerService. Вот код, он может не скомпилироваться, я просто быстро написал его в блокноте для вас. Также вам нужно убедиться, что добавляемый метод действительно добавляет клиента, а метод getCustomer действительно получает нового добавленного клиента. Если оба работают, то мое решение будет работать.

CustomerListComponent

import { Component Input} from '@angular/core';
import { ICustomer} from 'src/app/models/app.models';
import { CustomersService } from 'src/app/services/customers.service';

@Component({
  selector: 'drt-customers-list',
  templateUrl: './customers-list.component.html',
  styleUrls: ['./customers-list.component.scss'],
})
export class CustomerListComponent {
 public customers:  ICustomer[] ;

 constructor(public customersService: CustomersService,) {}

  public async ngOnInit(): Promise<void> {
    this.initCustomerAddedSubscription();
  }

/**
 * This subscription will execute every single time whenever a customer is added successfully
 *
 */ 
  public initCustomerAddedSubscription() {
    this.customersService.customerAdded.subscribe((data: boolean) => {
        if(data) {
            this.customers = await this.customersService.getCustomersList('');
        }
    });  

  }

}

CustomersService

import { HttpClient } from '@angular/common/http';
import { Injectable } from '@angular/core';
import { ICustomer} from 'src/app/models/app.models';
import { Observable } from 'rxjs';

@Injectable({
  providedIn: 'root',
})

export class CustomersService {
 private  baseUrl : string = '....api URL....';
 // use this subject in onAddCustomer method
 public   customerAdded: Subject<boolean>;

 // constructor to initialize subject
 constructor() {
    this.customerAdded = new Subject<boolean>();
 }
 public async getCustomersList(): Promise<ICustomer[]> {
    const apiUrl: string = `${this.baseUrl}/customers`;

    return this.http.get<ICustomer[]>(apiUrl).toPromise();
  }

public addCustomer(customer: ICustomer): Observable<object> {
  const apiUrl: string = `${this.baseUrl}/customers`;

  return this.http.post(apiUrl, customer);
}


}

Метод onaddCustomer

public onaddCustomer(): void {
    this.someCustomer = this.addCustomerForm.value;
    this.customersService.addCustomer( this.someCustomer).subscribe(
      () => { // If POST is success
        // You can pass in the newly added customer as well if you want for any reason. boolean is fine for now.
        this.customersService.customerAdded.next(true);
        this.successMessage();
      },
      (error) => { // If POST is failed
        this.failureMessage();
      }
    );

  }
0 голосов
/ 21 марта 2019
constructor(public customersService: CustomersService, private cd: ChangeDetectorRef) {}
    public onaddCustomer(): void {
        this.someCustomer = this.addCustomerForm.value;
        this.customersService.addCustomer( this.someCustomer).subscribe(
          () => { // If POST is success
            this.customers = await this.customersService.getCustomersList('');
            console.log(this.customers) //are you getting updating list here without refreshing.
             this.cd.markForCheck();
          },
          (error) => { // If POST is failed
            this.failureMessage();
          }
        );

      }
0 голосов
/ 21 марта 2019

ngOnInit запускается только один раз.Вы присвоили переменную customer в ngOnInit.Таким образом, это обновление только на обновление.Вам необходимо присвоить значение this.customers каждый раз, когда запрос будет выполнен.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...