Angular4 - 为什么服务承诺解析为undefined?

时间:2017-07-28 14:31:18

标签: angular typescript promise angular-services arrow-functions

我正在与诺言的未定义回归搏斗。从我的侦探工作来看,似乎问题是将promise的结果分配给我调用promise的组件上的实例变量。我认为这是箭头函数的类型(或类似)问题,我尝试将返回的调查分配给this.survey。

任何见解都将受到赞赏!

./ survey.service.ts

import { Injectable } from '@angular/core';
import { Observable } from 'rxjs/Observable';
import { SURVEYS } from './mock-survey';

export class Option {
constructor(public id: number,
          public text: string,
          public value: number
        ){}
}

export class Question {
constructor(public id: number,
          public type: string,
          public text: string,
          public required: boolean,
          public options: Option[] = []
        ){}
}

export class Survey {
constructor(public id: number,
          public name: string,
          public description: string,
          public instructions: string,
          public questions: Question[] = []
        ){}
}

@Injectable()
export class SurveyService {

  getSurveys(): Promise<Survey[]> {
    return Promise.resolve(SURVEYS);
  }

  getSurvey(id: number | string): Promise<Survey> {
    return this.getSurveys()
      .then(surveys => surveys
      .find(survey => survey.id === +id));
  }

  public observable: Observable<any>;
}

./ survey.component.ts

import 'rxjs/add/operator/switchMap';
import { Observable } from 'rxjs/Observable';
import { Component, OnInit, Inject, HostBinding }      from '@angular/core';
import { MdDialogRef, MD_DIALOG_DATA }  from '@angular/material';
import { Survey, SurveyService } from '../survey.service';

@Component({
  selector: 'app-survey',
  templateUrl: './survey.component.html',
  styleUrls: ['./survey.component.scss'],
  providers: [SurveyService]
})
export class SurveyComponent implements OnInit {

  survey: Survey
  surveyResults: {}

  constructor(
    private surveyService: SurveyService,
    public dialogRef: MdDialogRef<SurveyComponent>,
    @Inject(MD_DIALOG_DATA) public data: any
  ) { }

  // getSurveys(): void {
  //   this.surveyService.getSurveys().then(
  //     surveys => this.surveys= surveys);
  // }


  // *This method also returns an undefined this.survey; Not issue with ngOnInit()
  // getSurvey(): void {
  //   let survey_id = this.data.survey_id
  //   this.surveyService
  //       .getSurvey(survey_id)
  //       .then(s => {this.survey = s});
  // }

  ngOnInit(): void {
     this.surveyService
      .getSurvey(this.data.survey_id)
      .then((survey: Survey) => {this.survey = survey});

    // returns survey_id from MD_DIALOG_DATA
    console.log(this.data.survey_id)
    // returns survey JSON object; This arrives in browser console
    console.log(this.surveyService.getSurvey(this.data.survey_id));
    // returns undefined
    console.log(this.survey);
  }

  confirmSurveyResults() {
    this.dialogRef.close(this.surveyResults);
    console.log(this.survey);
  }


}

2 个答案:

答案 0 :(得分:1)

Promise是异步的,因此调查将始终在ngOnInit方法的上下文中未定义:

  ngOnInit(): void {
     this.surveyService
      .getSurvey(this.data.survey_id)
      .then((survey: Survey) => {
         this.survey = survey
         console.log(this.survey);// here it WILL NOT be undefined
       });


    // returns undefined because the promise is not fulfilled yet
    console.log(this.survey);
  }

答案 1 :(得分:0)

如上所述,调查还没有在init上进行。当您加载html时,它仍然不会存在,因此您必须确保调查存在,然后才能在ngfor中使用它。

也许使用ngIf?