Angular 2: TypeError: l_thing0 is undefined in [{{thing.title}} in [email protected]:44]

I'm getting a strange error in my app. It's supposed to print out {{thing.title}} from an object, but it shows an error in the console:

EXCEPTION: TypeError: l_thing0 is undefined in [{{thing.title}} in [email protected]:44]

I'm not sure where l_thing0 is coming from. If I try to show {{thing}}in the page, it displays [object Object]. If I try to JSON.stringify(this.thing) (see the showObj() function), it correctly displays the stringified object. But if I try to access an attribute like {{thing.title}} I get the error that l_thing0 is undefined.

Here is app.component.ts:

import {Component, OnInit} from 'angular2/core';
import {Thing} from './thing';
import {ThingService} from './thing.service';
import {SubThingComponent} from "./subthing.component";

@Component({
    selector: 'thing-app',
    template: `
        <div class="container">
            <div class="row">
                <div class="col-md-12">
                    <h1>{{thing.title}} <a href="#" (click)="showObj()" class="btn btn-default">Show Stringified Obj</a></h1>
                    <subthing></subthing>
                </div>
            </div>
        </div>
    `,
    styles:[`

    `],
    directives: [SubThingComponent],
    providers: [ThingService]
})

export class AppComponent implements OnInit {

    constructor(private _thingService: ThingService) { }

    public thing: Thing;

    showObj() {
        // This correctly shows the stringified object
        alert(JSON.stringify(this.thing));
    }

    getThing() {
        this._thingService.getThing().then(thing => this.thing = thing);
        // This correctly logs the object
        setTimeout(() => {console.log('thing', this.thing)}, 5000);
    }

    ngOnInit() {
        this.getThing();
    }
}

Any ideas?

Answers:

Answer

though I am coming late to the party but thought this might help for those who're using Angular 5. Strangely noticed the elvis operator will not work in *ngFor loop, but works for *ngif. So here's my code to address the issue.

<div *ngIf = "fullObject?.objProperty">
      <h1>{{fullObject.objProperty1}}</h1>
      <div *ngFor = "let o of fullObject.objPropertyArray">
          <h3>{{o._subheader}}</h3>
          <p>
              {{o._subtext}}
          </p>
        </div>
  </div>
</div>
Answer

You could also set a new variable isFinished to false before retrieving data from server or async function and after receiving the data set it to true. Then put isFinished variable in *ngIf to check if server/function process is done?

Answer

I am using Angular 8 and although the data is shown, I also had this error and googling it brought me to this question. The accepted answer (though well explained) did not solve it for me. (Maybe because of a newer version, or the use with *ngFor) It does not suffice to just use *ngIf, as you can see:

throws error: v1

  <div class="row">
    <pre>
      <li *ngFor="let obj of object.content">{{obj | json}}</li>
    </pre>
  </div>

throws error: v2

  <div class="row" *ngIf="object.content">
    <pre>
      <li *ngFor="let obj of object.content">{{obj | json}}</li>
    </pre>
  </div>

throws error: v3

  <div class="row" *ngIf="object.content">
    <pre>
      <li *ngFor="let obj of object?.content">{{obj | json}}</li>
    </pre>
  </div>


no error: v1

  <div class="row">
    <pre>
      <li *ngFor="let obj of object?.content">{{obj | json}}</li>
    </pre>
  </div>

no error: v2

  <div class="row" *ngIf="object?.content">
    <pre>
      <li *ngFor="let obj of object.content">{{obj | json}}</li>
    </pre>
  </div>

no error: v3

  <div class="row" *ngIf="object?.content">
    <pre>
      <li *ngFor="let obj of object?.content">{{obj | json}}</li>
    </pre>
  </div>
Answer

The issue is that the first time you load the page, thing is still undefined, it gets set to its real value later on asyncronously, so the first time it tries to access the property, it will throw an exception. The ? elvis operator is a shortcut to a nullcheck:

{{thing?.title}}

But its usually a best idea more performant not even try to render the component at all until you have the real object by adding something like:

<h1 *ngIf="thing">

to the container.

Tags

Recent Questions

Top Questions

Home Tags Terms of Service Privacy Policy DMCA Contact Us

©2020 All rights reserved.