4

I have created a Angular 2 service which reads a local json using http (could be rest service call later) and returns an Observable.

   @Injectable()
   export class WorkflowDataService {
   constructor(private http: Http) { }
   getProcessTemplates(): Observable<Response> {
       return this.http.get("/assets/jsons/process-templates.json");
   }}

the json that is being read looks like this

{
"process-templates": [
    {
        "name": "ABC",
        "desc": "ABC"
    },
    {
        "name": "XYZ",
        "desc": "XYZ"
    },
    {
        "name": "PQR",
        "desc": "PQR"
    }
 ]
}

My goal is to show the values of name attributes in a dropdown. So, the dropdown should have - ABC, XYZ, PQR.

So in my component, I am calling this service -

processTemplates: Observable<Response>; 
ngOnInit( ) {
  this.workflowDataService.getProcessTemplates()
     .subscribe(function(response) {
       this.processTemplates = response.json();
       console.log(this.processTemplates);
     });
}

In the console.log, I see the below output

JSON output

how can I get the output in a format which can be rendered in a drop down

<select class="form-control dropdown" (ngModel)="processTemplate" 
                name="processTemplate" id="processTemplate" required>
              <option *ngFor="let processTemplate of processTemplates">
                {{ processTemplate.name }}
              </option>
            </select>
1
  • You can map response to json in your service. return this.http.get("/assets/jsons/process-templates.json").map(res => res.json()); Commented Mar 23, 2017 at 7:50

2 Answers 2

4

Your JSON contains an array inside a object, so you need to extract the array from the object process-templates. Made some other changes as well, rather use fat arrow syntax instead of function, so you don't loose the context this :)

selectedT: any;

getProcessTemplates(): Observable<Response> {
   return this.http.get("/assets/jsons/process-templates.json")
     // extract array from process-templates object
     .map(res => res.json().process-templates) 
}}

Then in your component subscribe:

this.workflowDataService.getProcessTemplates()
  .subscribe(data => {
    this.processTemplates = data;
    console.log(this.processTemplates);
  });

And as for your template, do like John said:

<select [(ngModel)]="selectedTemplate"> 
  <option *ngFor="let processTemplate of processTemplates">{{processTemplate.name}}</option>
</select>
Sign up to request clarification or add additional context in comments.

1 Comment

can you please help me to solve this stackoverflow.com/questions/50059278/…
0

From a similar question: Binding select element to object in Angular 2

<select [(ngModel)]="selectedTemplate"> // use banana in a box syntax:[()]
  <option *ngFor="let processTemplate of processTemplates" [ngValue]="processTemplate">{{processTemplate.name}}</option>
</select>

Also. You have a different scope for (this) inside your init method. Chaning to a lambda function will solve this. And as mention by @AJT_82, extract the object inside your json

ngOnInit( ) {
  this.workflowDataService.getProcessTemplates()
     .subscribe(response => { //removed function, added =>
       this.processTemplates = response.json().process-templates; //extract json
       console.log(this.processTemplates);
     });
}

2 Comments

The output printed on the console shows that it is not in a format that can be iterated using *ngFor, that's why I still get the same error - Cannot find a differ supporting object '[object Object]' of type 'object'. NgFor only supports binding to Iterables such as Arrays.
as @AJT_82 mentions in his/her answer, extract the object inside your json: this.processTemplates = response.json().process-templates

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.