Tipe
Tipe

Reputation: 43

ERROR TypeError: Cannot read property 'details' of undefined

I have a plain text on local server that i want to display on my web page using angular. I have my model, service and component. So I am getting an error at this line >> this.paragraphs = this.announcement.details.split('#');

I tried using ? operator (this.paragraphs = this.announcement?.details.split('#')) but it could not build.

MODEL

export class Announcements 
{
    public id: number;
    public details: string;
    public date: Date;
}

SERVICE

getAnnouncementById(id)
{
    return this.http.get<Announcements>('http://localhost:49674/api/Announcements/' + id)
                    .pipe(catchError(this.errorHandler));
}

COMPONENT-.ts

import { Announcements } from '../models/Announcement';

    export class ReadMoreComponent implements OnInit 
    {
      public announcementId;
      public announcement : Announcements
      public paragraphs = [];

      constructor(
        private route: ActivatedRoute,
        private router:Router,
        private announcementservice: AnnouncementsService
      ){}

      ngOnInit() 
      {
        this.route.paramMap.subscribe((params:ParamMap) => {
          let id = parseInt(params.get('id'));
          this.announcementId = id;

          this.getAnnouncenentById(id)

          //split
          this.paragraphs = this.announcement.details.split('#');
        })
      }

      getAnnouncenentById(id){
        this.announcementservice.getAnnouncementById(id)
        .subscribe(data => this.announcement = data);
    }

COMPONENT-.html

<div class="article column full">
     <div *ngFor=" let paragraph of paragraphs">
         <p>{{paragraph.details}}</p>
     </div>
</div>

Upvotes: 0

Views: 606

Answers (1)

Przemyslaw Jan Beigert
Przemyslaw Jan Beigert

Reputation: 2486

this.paragraphs = this.announcement.details.split('#'); is called before this.announcement = data so this.annoucement is undefined in that moment.

To be sure that both values already comes form observables you can use combineLatest function or switchMap operator.

Adding ? operator is workaround. Your observable still can call with unexpected order.

e.g.:

this.route.paramMap.pipe(switchMap((params: ParamMap) => {
  let id = parseInt(params.get('id'));
  this.announcementId = id;

  this.getAnnouncenentById(id);
  return this.announcementservice.getAnnouncementById(id)

})).subscribe((data) => {
  this.announcement = data
  this.paragraphs = this.announcement.details.split('#');
});

In that code subscription will start after first observable emits value.

Upvotes: 1

Related Questions