我对Angle非常陌生,所以我不知道是否回答了。我调查了一些答案,但无法正确解决。抱歉,如果已经回答。
我有一个调用后端Rest API的Angular服务
export class StudentService {
private studentUrl: string;
constructor(private httpClient: HttpClient) {
this.studentUrl = 'someurl';
}
public getTag(email: string): Observable < PayLoad > {
const params = new HttpParams().set("email", email);
return this.httpClient.get < PayLoad > (this.studentUrl.concat("Tag"), {
params
});
}
getCoursesForStudent(tag: string): Observable < CourseDto > {
const params = new HttpParams().set("tag", tag);
return this.httpClient.get < CourseDto > (this.studentUrl.concat('courses'), {
params
})
}
getStudentByEmail(email: string): Observable < any > {
const params = new HttpParams().set("email", email.toString());
return this.httpClient.get < Student > (this.studentUrl.concat('getstu'), {
params
})
}
}
我还有一个消耗它的组件
export class StudentprofileComponent implements OnInit {
courses: Observable < CourseDto > ;
student: Student;
newstu: Student;
tag: PayLoad;
payload = PayLoad;
constructor(private studentservice: StudentService, private router: Router) {}
loadCourses() {
payload: new PayLoad();
const email = atob(localStorage.getItem('stuemail'));
this.studentservice.getTag(email).subscribe(data => {
this.tag = data,
console.log("data:" + data.value)
});
return this.studentservice.getCoursesForStudent(this.tag.value);
}
loadStudent() {
let email = atob(localStorage.getItem('email'));
return this.studentservice.getStudentByEmail(email.toString());
}
ngOnInit() {
this.loadStudent().subscribe(data => {
this.student = data
}, error =>
console.log(error));
this.courses = this.loadCourses();
}
}
问题是,我不断收到 TypeError无法读取未定义的属性“值” 。甚至数据也会在控制台中打印。
答案 0 :(得分:3)
嵌套订阅是一种反模式,应避免使用。尝试使用switchMap运算符获取所需的值。
export class StudentprofileComponent implements OnInit {
courses: CourseDto ; // Removed the Observable due to new subscription
student: Student;
// newstu: Student;
// tag: PayLoad;
// payload = PayLoad;
constructor(private studentservice: StudentService, private router: Router) {}
// loadCourses() {
// payload: new PayLoad();
// const email = atob(localStorage.getItem('stuemail'));
// this.studentservice.getTag(email).subscribe(data => {
// this.tag = data,
// console.log("data:" + data.value)
// });
// return this.studentservice.getCoursesForStudent(this.tag.value);
// }
// loadStudent() {
// let email = atob(localStorage.getItem('email'));
// return this.studentservice.getStudentByEmail(email.toString());
// }
ngOnInit() {
const email = atob(localStorage.getItem('email')).toString();
const stuEmail = atob(localStorage.getItem('stuemail')).toString();
this.studentservice.getStudentByEmail(email).subscribe(student => this.student = student);
this.studentservice.getTag(stuEmail).pipe(
switchMap(tag => this.studentservice.getCoursesForStudent(tag.value))
).subscribe(courses => this.courses = courses);
}
}
答案 1 :(得分:1)
这是一个异步电话。您不知道服务器何时将返回此get-endpoint-
的答案。您使用.subscribe()函数订阅了呼叫。 在您订阅时,获取将尝试到达后端。
他的订阅函数中的所有内容都将在返回get时执行。
//1.register subscription
this.studentservice.getTag(email).subscribe(
data=>{
//3. will be executed when server answers
this.tag = data ,
console.log("data:"+data.value)});
//2. Will return the value before the tag-object is set in subscribe
return this.studentservice.getCoursesForStudent(this.tag.value);
因此,您遇到的问题是,当您调用返回所在的行时,标记对象仍未定义,因为订阅尚未返回。
您可以尝试在订阅中执行getCoursesForStudent,但这会使它更加复杂。
当另一个完成时,您可以尝试使用switchmap订阅可观察对象 https://www.learnrxjs.io/learn-rxjs/operators/transformation/switchmap