Неожиданное преобразование числа c в строку при создании объекта в машинописи - PullRequest
1 голос
/ 06 февраля 2020

Я пишу сервис на Angular. Объявите переменную в классе обслуживания:

private tariffCache: {id: number, observable: Observable<Tariff>}[] = [];

(внимание к идентификатору)

Заполните эту переменную в функции:

getTariff(id: number): Observable<Tariff> {
    if (!this.tariffCache || !this.tariffCache.find(x => x.id === id)) {
      const url = ${this.tariffsUrl}/${id};
      this.tariffCache.push({
        id,
        observable: this.http.get<Tariff>(url, this.httpOptions)
          .pipe(shareReplay(1))
      });
    }
    return this.tariffCache.find(x => x.id === id).observable;
  }

Что я ожидаю увидеть в переменной ' tarCache 'после ответа от сервера с id = 34?

{id: 34, observable: Observable}

Верно! Но на самом деле:

{id: "34", observable: Observable}

Ух ты? Почему 34 сейчас строка? Когда это преобразовать в строку ?! Но это еще не все! Я повторяю вызов этой функции с id = 34. 34 - это цифра c, иначе компилятор выдаст ошибку. Весь код в функции 'getTariff' работает! Функция 'find' отлично работает с оператором сравнения "===". Массив содержит объект со строковым идентификатором и находит элемент с числовым значением c id. Брррр ...

Я пишу другую функцию с тем же кодом с функцией 'найти', и она не работает. Какая? Почему не сейчас?

Хорошо, я изменил функцию getTariff на:

getTariff(id: number): Observable<Tariff> {
    if (!this.tariffCache || !this.tariffCache.find(x => x.id === +id)) {
      const url = ${this.tariffsUrl}/${id};
      this.tariffCache.push({
        id: +id,
        observable: this.http.get<Tariff>(url, this.httpOptions)
          .pipe(shareReplay(1))
      });
    }
    return this.tariffCache.find(x => x.id === +id).observable;
  }

И теперь массив содержит объект с цифрой c id, и другие функции также работают с массивом. Может ли кто-нибудь объяснить это поведение «id» и «find»? Спасибо.

UPD: вызов функции 'getTariff' из функции 'changeCurrentTariff' в службе. Функция clearTariff не работает до изменения getTariff. Это фрагмент кода в сервисе:

export class TariffService extends AbstractModelService {
  private tariffsUrl = environment.baseUrl + 'api/Tariffs';
  private tariffCache: {id: number, observable: Observable<Tariff>}[] = [];
  private tariffSource = new BehaviorSubject<Tariff>(null);
  constructor(private http: HttpClient) {
    super();
  }
  currentTariff = this.tariffSource.asObservable();
  changeCurrentTariff(id: number) {
    if (id) {
      this.getTariff(id)
        .subscribe(tariff => {
          this.tariffSource.next(tariff);
        });
    }
  }
  /** GET tariff by id. Will 404 if id not found */
  getTariff(id: number): Observable<Tariff> {
    if (!this.tariffCache || !this.tariffCache.find(x => x.id === +id)) {
      const url = `${this.tariffsUrl}/${id}`;
      this.tariffCache.push({
        id: +id,
        observable: this.http.get<Tariff>(url, this.httpOptions)
          .pipe(shareReplay(1))
      });
    }
    return this.tariffCache.find(x => x.id === +id).observable;
  }
  clearTariff(id: number) {
    if (this.tariffCache) {
      const index = this.tariffCache.findIndex(x => x.id === +id);
      if (index >= 0) {
        this.tariffCache.splice(index, 1);
      }
    }
  }
}

Но вызов changeCurrentTariff из компонента:

export class TariffComponent implements OnInit, OnDestroy {
  constructor(
    private route: ActivatedRoute,
    private tariffService: TariffService,
  ) { }

  ngOnInit() {
    this.route.params
        .pipe(
          takeUntil(this.unsubscribe)
        )
        .subscribe(params => {
          if (params.id) {
            this.tariffService.changeCurrentTariff(params.id);
          }
        });
  }
}

1 Ответ

0 голосов
/ 06 февраля 2020

Параметры маршрута AFAIK всегда анализируются как строки, поэтому здесь

    this.route.params
        .pipe(
          takeUntil(this.unsubscribe)
        )
        .subscribe(params => {
          if (params.id) {

вам нужно явно преобразовать id в число.

...