将基于 class 的组件重构为挂钩 (gapi API)
Refactoring a class based component to hooks (gapi API)
我正在尝试将基于 class 的组件重构为使用挂钩的功能组件。尝试获取我的登录状态时,我卡在了 gapi 中 useState 的正确使用上。
只是想知道,我想得到什么:
1) 获取对"auth"对象初始化后的引用
2) 弄清楚我目前是否已登录
3) 在屏幕上打印我的身份验证状态
这里已经提出了类似的问题: 但不幸的是,我没有将答案应用到我的案例中。
这是 class 组件:
import React from "react";
class GoogleAuth extends React.Component {
componentDidMount() {
window.gapi.load("client: auth2", () => {
window.gapi.client
.init({
clientId: "myVerySecretAPI",
scope: "email"
})
.then(() => {
this.auth = window.gapi.auth2.getAuthInstance(); //this gets me acces to the auth object
this.setState({ isSignedIn: this.auth.isSignedIn.get() });
});
});
}
renderAuthButton() {
if (this.state.isSignedIn === null) {
return <div>I dont know if we are signed in</div>;
} else if (this.state.isSignedIn) {
return <div>I am signed in!</div>;
} else {
return <div>I am not signed in</div>;
}
}
render() {
return <div>{this.renderAuthButton()}</div>;
}
}
export default GoogleAuth;
这是我重构的代码:
import React, { useEffect, useState } from "react";
const GoogleAuth = () => {
const [ auth, setAuth ] = useState(null);
useEffect(
() => {
window.gapi.load("client:auth2", () => {
window.gapi.client
.init({
clientId: "834243588921-gob95b7q7n3eids3fm8du8oharkv5od0.apps.googleusercontent.com",
scope: "email"
})
.then(() => {
setAuth(window.gapi.auth2.getAuthInstance());
auth({ isSignedIn: setAuth.isSignedIn.get() }); // this is the line where I get an error (please see below)
});
});
},
[ auth ]
);
const renderAuthButton = (isSignedIn) => {
if (isSignedIn === null) {
return <div>I dont know if we are signed in</div>;
} else if (isSignedIn) {
return <div>I am signed in!</div>;
} else {
return <div>I am not signed in</div>;
}
};
return <div>{renderAuthButton()}</div>;
};
export default GoogleAuth;
我在 chrome 中收到错误消息:
未捕获类型错误:无法读取 GoogleAuth.js:16
处未定义的 属性 'get'
我知道,我缺少一些了解挂钩使用的小东西。
欢迎任何帮助!
所以你基本上是在节省一些东西。第一个是您从 window.gapi.auth2.getAuthInstance()
获得的 actual 身份验证实例,第二个是已验证状态 isSignedIn
。在您的代码中,您 setAuth
使用实例,但随后尝试调用已保存的实例并向其传递一些新对象,其中 isSignedIn
作为键,状态 setter 作为值。这行不通。
您可以先获取实例,然后使用该实例从中获取身份验证状态以保存到您的状态中。您还应该使用一个空的依赖项数组,这样当 GoogleAuth
被挂载时效果是 运行 一次。
此外,您的 renderAuthButton
函数被定义为采用 isSignedIn
参数,但您没有在 return 中向其传递任何内容。由于这是一个功能组件,尽管您可以简单地省略参数并在范围内使用状态值。
const GoogleAuth = () => {
const [isSignedIn, setIsSignedIn ] = useState(null);
useEffect(
() => {
window.gapi.load("client:auth2", () => {
window.gapi.client
.init({
clientId: "834243588921-gob95b7q7n3eids3fm8du8oharkv5od0.apps.googleusercontent.com",
scope: "email"
})
.then(() => {
const authInstance = window.gapi.auth2.getAuthInstance();
setIsSignedIn(authInstance.isSignedIn.get());
});
});
},
[]
);
const renderAuthButton = () => {
if (isSignedIn === null) {
return <div>I don't know if we are signed in</div>;
} else if (isSignedIn) {
return <div>I am signed in!</div>;
} else {
return <div>I am not signed in</div>;
}
};
return <div>{renderAuthButton()}</div>;
};
我正在尝试将基于 class 的组件重构为使用挂钩的功能组件。尝试获取我的登录状态时,我卡在了 gapi 中 useState 的正确使用上。
只是想知道,我想得到什么:
1) 获取对"auth"对象初始化后的引用
2) 弄清楚我目前是否已登录
3) 在屏幕上打印我的身份验证状态
这里已经提出了类似的问题:
这是 class 组件:
import React from "react";
class GoogleAuth extends React.Component {
componentDidMount() {
window.gapi.load("client: auth2", () => {
window.gapi.client
.init({
clientId: "myVerySecretAPI",
scope: "email"
})
.then(() => {
this.auth = window.gapi.auth2.getAuthInstance(); //this gets me acces to the auth object
this.setState({ isSignedIn: this.auth.isSignedIn.get() });
});
});
}
renderAuthButton() {
if (this.state.isSignedIn === null) {
return <div>I dont know if we are signed in</div>;
} else if (this.state.isSignedIn) {
return <div>I am signed in!</div>;
} else {
return <div>I am not signed in</div>;
}
}
render() {
return <div>{this.renderAuthButton()}</div>;
}
}
export default GoogleAuth;
这是我重构的代码:
import React, { useEffect, useState } from "react";
const GoogleAuth = () => {
const [ auth, setAuth ] = useState(null);
useEffect(
() => {
window.gapi.load("client:auth2", () => {
window.gapi.client
.init({
clientId: "834243588921-gob95b7q7n3eids3fm8du8oharkv5od0.apps.googleusercontent.com",
scope: "email"
})
.then(() => {
setAuth(window.gapi.auth2.getAuthInstance());
auth({ isSignedIn: setAuth.isSignedIn.get() }); // this is the line where I get an error (please see below)
});
});
},
[ auth ]
);
const renderAuthButton = (isSignedIn) => {
if (isSignedIn === null) {
return <div>I dont know if we are signed in</div>;
} else if (isSignedIn) {
return <div>I am signed in!</div>;
} else {
return <div>I am not signed in</div>;
}
};
return <div>{renderAuthButton()}</div>;
};
export default GoogleAuth;
我在 chrome 中收到错误消息:
未捕获类型错误:无法读取 GoogleAuth.js:16
处未定义的 属性 'get'我知道,我缺少一些了解挂钩使用的小东西。 欢迎任何帮助!
所以你基本上是在节省一些东西。第一个是您从 window.gapi.auth2.getAuthInstance()
获得的 actual 身份验证实例,第二个是已验证状态 isSignedIn
。在您的代码中,您 setAuth
使用实例,但随后尝试调用已保存的实例并向其传递一些新对象,其中 isSignedIn
作为键,状态 setter 作为值。这行不通。
您可以先获取实例,然后使用该实例从中获取身份验证状态以保存到您的状态中。您还应该使用一个空的依赖项数组,这样当 GoogleAuth
被挂载时效果是 运行 一次。
此外,您的 renderAuthButton
函数被定义为采用 isSignedIn
参数,但您没有在 return 中向其传递任何内容。由于这是一个功能组件,尽管您可以简单地省略参数并在范围内使用状态值。
const GoogleAuth = () => {
const [isSignedIn, setIsSignedIn ] = useState(null);
useEffect(
() => {
window.gapi.load("client:auth2", () => {
window.gapi.client
.init({
clientId: "834243588921-gob95b7q7n3eids3fm8du8oharkv5od0.apps.googleusercontent.com",
scope: "email"
})
.then(() => {
const authInstance = window.gapi.auth2.getAuthInstance();
setIsSignedIn(authInstance.isSignedIn.get());
});
});
},
[]
);
const renderAuthButton = () => {
if (isSignedIn === null) {
return <div>I don't know if we are signed in</div>;
} else if (isSignedIn) {
return <div>I am signed in!</div>;
} else {
return <div>I am not signed in</div>;
}
};
return <div>{renderAuthButton()}</div>;
};