无法读取未定义的给定属性
我在渲染函数中调用 this.getAllJobsAPI();。
这成功调用了 getAllJobsAPI(如下所示),并且我能够从作业的 JSON 数组中检索作业名称。
getAllJobsAPI(){
var headers = new Headers();
headers.append('Authorization', 'Basic YWRtaW46YWRtaW4=');
fetch('http://localhost:8080/api/json', {headers: headers})
.then((result) => {
// Get the result
// If we want text, call result.text()
return result.json();
}).then((jsonResult) => {
// get all jobs
var jobs = [];
Object.keys(jsonResult.jobs).forEach(function(key) {
jobs.push(jsonResult.jobs[key].name);
var job = jsonResult.jobs[key].name;
console.log(job);
this.getLastBuildAPI(job);
});
//var a = 'meetup';
//this.getLastBuildAPI(a);
console.log(jsonResult);
})
}
但在 for each 循环中调用 this.getLastBuildAPI(job); 会引发“Uncaught (in promise) TypeError: Cannot read property 'getLastBuildAPI' of undefined”错误。但如果我在函数末尾硬编码一个名称变量并调用 this.getLastBuildAPI(a);,我可以获得成功响应。
有人能告诉我为什么我无法在 JSON 数组的 for-each 中调用 this.getLastBuildAPI(job); 吗?请注意,我能够在控制台中看到作业变量。
谢谢,
因为解析回调中的
this
是
undefined
(因为它是不同的上下文),而当它在回调之外时,
this
就是您期望的对象。您可以先引用
this
var 并将其存储起来。
getAllJobsAPI(){
var headers = new Headers();
headers.append('Authorization', 'Basic YWRtaW46YWRtaW4=');
var self = this;
fetch('http://localhost:8080/api/json', {headers: headers})
.then((result) => {
// Get the result
// If we want text, call result.text()
return result.json();
}).then((jsonResult) => {
// get all jobs
var jobs = [];
Object.keys(jsonResult.jobs).forEach(function(key) {
jobs.push(jsonResult.jobs[key].name);
var job = jsonResult.jobs[key].name;
console.log(job);
self.getLastBuildAPI(job);
});
//var a = 'meetup';
//this.getLastBuildAPI(a);
console.log(jsonResult);
})
您也可以应用其他方法。
1. 使用
bind
方法。
The bind() method creates a new function that, when called, has its this keyword set to the provided value, with a given sequence of arguments preceding any provided when the new function is called.
Object.keys(jsonResult.jobs).forEach(function(key) {
jobs.push(jsonResult.jobs[key].name);
var job = jsonResult.jobs[key].name;
console.log(job);
this.getLastBuildAPI(job);
}.bind(this));
2.使用
arrow
函数。
直到
arrow
函数,每个
new
函数
都定义了自己的
this
值。
例如,在构造函数的情况下,
this
可以是一个新的对象。
function Person(age){
this.age=age;
console.log(this);
}
let person=new Person(22);
或者,如果可以像
obj.getAge()
那样访问创建的函数,则
this
可以
指向
base
对象。
let obj={
getAge:function(){
console.log(this);
return 22;
}
}
console.log(obj.getAge());
arrow
函数不会创建自己的
this
,它仅使用
封闭
执行
上下文
的
this
值。另一方面,
arrow
函数使用父作用域的
this
。
Object.keys(jsonResult.jobs).forEach((key) => {
jobs.push(jsonResult.jobs[key].name);
var job = jsonResult.jobs[key].name;
console.log(job);
this.getLastBuildAPI(job);
});
您已将普通
函数
传递给
forEach
,从而更改了上下文。如果您想保留上下文,请使用箭头函数,或者,您可以创建一个新变量来保留对
this
的引用。
使用箭头函数:
Object.keys(jsonResult.jobs).forEach(key => {
.....
this.getLastBuildAPI(job);
});
保留对
this
的引用:
var that = this;
Object.keys(jsonResult.jobs).forEach(function(key) {
....
that.getLastBuildAPI(job);
});