1
resposta

Erro: Type 'Observable<IUnidadeFederativa[]> | undefined' is not assignable to type 'NgIterable<any> | null | undefined'.

Olá, depois de muitas tentativas, resolvi copiar a solução do repositório. O seguinte erro aparece: src/app/shared/form-busca/dropdown-uf/dropdown-uf.component.html:19:32 - error TS2322: Type 'Observable<IUnidadeFederativa[]> | undefined' is not assignable to type 'NgIterable | null | undefined'.

19 <mat-option *ngFor="let es of filteredOptions$" [value]="es.nome"> ~~

src/app/shared/form-busca/dropdown-uf/dropdown-uf.component.ts:11:16 11 templateUrl: './dropdown-uf.component.html', ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Error occurs in the template of component DropdownUfComponent.

dropdown-uf.components.ts

import { Component, Input, OnInit } from '@angular/core';
import { FormControl } from '@angular/forms';
import { Observable, startWith, of } from 'rxjs';
import { map } from 'rxjs/operators';
import { UnidadeFederativaServiceService } from 'src/app/core/services/unidade-federativa-service.service';
import { IUnidadeFederativa } from 'src/app/core/types/type';


@Component({
  selector: 'app-dropdown-uf',
  templateUrl: './dropdown-uf.component.html',
  styleUrls: ['./dropdown-uf.component.scss']
})
export class DropdownUfComponent implements OnInit{
  @Input() label: string = '';
  @Input() iconePrefixo : string = '';
  @Input() control!: FormControl;

  unidadesFederativas: IUnidadeFederativa[] = [];

  filteredOptions$?: Observable<IUnidadeFederativa[]>;
  foo : IUnidadeFederativa[] = [];

  constructor(
    private unidadeFederativaService: UnidadeFederativaServiceService
  ) { }


  ngOnInit(): void {
    this.unidadeFederativaService.listar().
    subscribe(dados =>{
      this.unidadesFederativas = dados
      console.log(this.unidadesFederativas)
    });

    this.filteredOptions$ = this.control.valueChanges.pipe(
      startWith(this.control.value),
      map(value => this.filtrarUfs(value)),
    );



  }

  private filtrarUfs(value: string): IUnidadeFederativa[] {
    const valorFiltrado = value?.toLowerCase();

    const result = this.unidadesFederativas.filter(
      estado => estado.nome.toLowerCase().includes(valorFiltrado)
    )
    return result;
  }

}

dropdown-uf.component.html


<mat-form-field class="input-container" appearance="outline">
  <mat-label>{{ label }}</mat-label>
  <mat-icon matPrefix>
    {{iconePrefixo}}
  </mat-icon>

  <input matInput
    placeholder="Origem"
    [formControl] = "control"
    [name]="label"
    ngDefaultControl
    [matAutocomplete]="auto">

  <mat-icon matSuffix>search</mat-icon>

  <mat-autocomplete autoActiveFirstOption #auto="matAutocomplete">

    <mat-option *ngFor="let es of filteredOptions$" [value]="es.nome">
      {{es.nome}}
    </mat-option>

  </mat-autocomplete>

</mat-form-field>
1 resposta

Olá, João, como vai?

O erro que você mencionou ocorre porque o Angular não consegue garantir que o valor de filteredOptions$ seja compatível com o tipo esperado por *ngFor. Esse tipo de problema acontece quando a variável usada no *ngFor pode ser undefined, o que não é permitido.

Para corrigir, você pode garantir que o valor de filteredOptions$ será tratado como um valor válido para o *ngFor. Uma abordagem seria usar o operador async diretamente no template e ajustar o tipo da variável para evitar inconsistências. Tente da seguinte forma:

Substitua:

<mat-option *ngFor="let es of filteredOptions$" [value]="es.nome">
  {{es.nome}}
</mat-option>

Por:

<mat-option *ngFor="let es of (filteredOptions$ | async) || []" [value]="es.nome">
  {{es.nome}}
</mat-option>

Aqui, o operador async faz a assinatura automática do Observable e retorna os valores, enquanto o || [] garante que, caso o valor seja undefined, o Angular processará uma lista vazia, evitando o erro.

Espero ter ajudado!

Siga firme nos seus estudos e conte com o fórum sempre que precisar!

Abraços :)

Caso este post tenha lhe ajudado, por favor, marcar como solucionado