I have tried all methods and checked related stackoverflow questions and nothing worked so asking here. I have to create ui where on select of dropdown an api call is made and data is received in form of an array . Based on this array i want to add as many fields to my form as there are number of elements in array. I tried using FormArray but it did not work. As i keep getting error related to cannot find control with specified name 'name'. I tried using making formcontrol fields dynamic but still getting the same error.
Here is the code that i tried .
.ts file
import { Component, OnInit } from '@angular/core';
import { FormGroup, FormBuilder, Validators, FormControl, FormArray } from '@angular/forms';
import { HttpClient } from '@angular/common/http';
@Component({
selector: 'app-calculator',
templateUrl: './calculator.component.html',
styleUrls: ['./calculator.component.scss']
})
export class CalculatorComponent implements OnInit {
title = 'Formula Calculation Page';
configUrlProducts = 'http://localhost:3000/data/products';
configUrlProductFieldsData = 'http://localhost:3000/data/getproductfields/';
angForm: FormGroup;
ruleset_data=[];
ruleset_data_length=0;
products: any = [];
selected_product_id;
syntax_error=false
show_form=false;
arr=[{'name':''},{'class':''},{'tree':''}];
temp;
// products=[{"id":1,"name":'Product 1'},{"id":2,"name":'Product 2'},{"id":3,"name":'Product 3'}]
constructor(private fb: FormBuilder,private http: HttpClient) {
console.log("inside constructor")
// this.createForm();
// this.fetch_products();
}
// convenience getters for easy access to form fields
get f() { return this.angForm.controls; }
get t() { return this.f.fields as FormArray; }
ngOnInit() {
console.log("inside ngonit");
this.angForm = this.fb.group({
fields: new FormArray([])
});
for(var i=0;i<3;i++){
this.temp=this.arr[i];
this.t.push(this.fb.group({'name':''}))
}
// this.arr.forEach(item=>{
// this.t.push(this.fb.group(item))
// })
console.log(this.angForm)
this.getProducts();
}
getProducts() {
console.log("inside get products");
this.products = [];
this.http.get(this.configUrlProducts).subscribe((res)=>{
console.log(res);
this.products = res["data"];
});
}
fetch_ruleset_data(value: string){
this.selected_product_id=value;
console.log("inside get rule data");
this.ruleset_data = [];
this.http.get(this.configUrlProductFieldsData+value).subscribe((res)=>{
console.log(res);
this.ruleset_data = res["data"];
this.show_form=true;
console.log(this.angForm);
this.ruleset_data_length=res["data"].length;
});
}
onSubmit(value){
console.log(value);
// var data=value;
// data["no_of_variables"]=this.ruleset_data_length;
// data["product_id"]=this.selected_product_id;
// // value=value+this.ruleset_data_length;
// // var formula=JSON.parse(value);
// console.log("final data before sending to api",data);
// return this.http.post('http://localhost:3000/formula/addformula', data)
// .subscribe((res)=>{
// console.log(res);
// })
}
validateFormula=(c: FormControl)=> {
console.log(c.value,typeof c.value);
var data={};
data['formula']=c.value;
data["no_of_variables"]=this.ruleset_data_length;
data["product_id"]=this.selected_product_id;
return this.http.post('http://localhost:3000/formula/validateformula', data)
.subscribe((res)=>{
// console.log("inside validation after api call",res)
// console.log(res["error"])
if(res["error"]){
console.log("inside error block",res);
this.syntax_error=true;
// this.angForm.setErrors({ 'invalid': true });
// return true;
return {
validateFormula: {
valid: true
}
}
}else{
this.syntax_error=false;
// this.angForm.setErrors({ 'invalid': false });
// return true;
return {
validateFormula: {
valid: true
}
}
}
})
// let EMAIL_REGEXP;
// return EMAIL_REGEXP.test(c.value) ? null : {
// validateEmail: {
// valid: false
// }
// };
}
// fetch_ruleset_data(value: string){
// console.log(value);
// }
}
.html file
<!-- app.component.html -->
<div class="container">
<h1>
Welcome to {{title}}!!
</h1>
<select class="custom-select" (change)="fetch_ruleset_data($event.target.value)">
<option value="" disabled>Choose your product</option>
<option *ngFor="let product of products; let i = index" [value]="product.id">
{{product.name}}
</option>
</select>
<div *ngIf="show_form==true">
<form [formGroup]="angForm" (ngSubmit)="onSubmit(angForm.value)">
<div *ngFor="let item of t.controls; let i = index">
<div [formGroup]="item">
<input [formControlName]='item'>
</div>
</div>
<button type="submit">Submit</button>
</form>
</div>
<br />
</div>
Have been struggling with this from past 2 days any help is greatly appreciated. I am new to angular and currently learning it it might be a simple thing but i am unable to figure it out at present and need your help.