Angular 6 - Load Reactive Form after Http request

Asked

Viewed 423 times

0

I’m having trouble displaying a client list obtained by a request GET in a component select. Like the GET is asynchronous, the form is being built before the request is finished and hence the select is empty. If I refresh the page, the client list appears.

Excerpt from the Component:

form: FormGroup;
clientes: Cliente[];

constructor(
    private formBuilder: FormBuilder,
    private clienteService: ClienteService
){}

ngOnInit() {
    this.clienteService.findAll()
        .subscribe(clientes => {
            this.clientes = clientes
        });        

    this.initForm();
}

initForm(){
    this.form = this.formBuilder.group({
        cliente: this.formBuilder.control('')
    }, { updateOn: 'blur' });
}

If I put the call to initForm() in the subscribe, there occurs a delay to initialize the form and thus receive the error:

ERROR Error: formGroup expects a FormGroup instance. Please pass one in.

Excerpt from my select:

<div class="input-field col s6">
     <select id="cliente" formControlName="cliente">
          <option disabled selected>Selecione um cliente...</option>
          <option *ngFor="let cli of clientes" [value]="cli.id">
                    {{ cli.nome }}
          </option>
      </select>
      <label for="cliente">Cliente</label>
 </div>

I’m using Angular 6 with Materialize CSS. I’ve tried applying the suggested solutions in the links below, but none worked:

https://medium.com/front-end-hacking/async-data-in-a-form-with-angular-d2506cbc1114

https://coryrylan.com/blog/using-angular-forms-with-async-data

https://stackoverflow.com/questions/48747281/loading-dynamic-reactive-forms-doesnt-wait-for-the-http-call-to-complete

  • In the form of your HTML you have? <form [formGroup]="form">. Passing the eye seems all right to me, check the detail I told you.

  • Yes. I didn’t post all the HTML code because it’s extensive. In the case of my service, I’m working with Observable, but I’ve already switched to Promise and I have the same behavior.

  • I have just done some tests here and it seems that the problem is not in the order of data acquisition and display, but with the Materialize select component itself. I added a class="browser-default" to select and the client list now appears every time. The problem is that this setting completely modifies the look of the form.

  • Did you even try to use setValue, to enter the value after the form was created? Can’t test it now but take a look there. Or use ngIf to display the info only when the information is already in your array.

  • I tried. I used setValue both in ngAfterViewInit() how much in the ngAfterContentInit(). I made a if (this.form) { this.form.setValue({ cliente: this.clientes });}}. But I’m thinking it’s really some bug of the select component of Materialize, because as I said, with the browser-default no problem. I’ll put Bootstrap in the project to do some tests.

  • Set a mini example here so we can see what you’ve done: https://stackblitz.com/

  • It seems that the select component of Materialize is bugged. It was not possible to do more in-depth tests. But after making the switch to Bootstrap the application worked normally. Thank you for everyone’s collaboration!

Show 2 more comments
No answers

Browser other questions tagged

You are not signed in. Login or sign up in order to post.