我使用 AWS Cognito 进行登录身份验证。我可以使用它,但现在我想对其应用会话。为此,我想存储用户名和密码,并将它们传递给所有需要身份验证的页面。我在读取 useContext 中的身份验证函数时遇到问题。
我的 createContext 和 Provider 函数在 Account.js 文件中:
import React, { createContext } from 'react';
import { CognitoUser, AuthenticationDetails } from 'amazon-cognito-identity-js';
import Pool from '../../UserPool';
const AccountContext = createContext();
const Account = (props) => {
const authenticate = async (Username, Password) => {
return await new Promise((resolve, reject) => {
const user = new CognitoUser({ Username, Pool });
const authDetails = new AuthenticationDetails({ Username, Password });
user.authenticateUser(authDetails, {
onSuccess: data => {
console.log('onSuccess: ', data);
resolve(data);
// setIsLoggedIn(true);
},
onFailure: err => {
console.error('onFailure: ', err);
reject(err);
},
newPasswordRequired: function(userAttributes, requiredAttributes) {
// User was signed up by an admin and must provide new
// password and required attributes, if any, to complete
// authentication.
console.log('user attri', userAttributes, this);
// the api doesn't accept this field back
delete userAttributes.email_verified;
// unsure about this field, but I don't send this back
delete userAttributes.phone_number_verified;
// Get these details and call
user.completeNewPasswordChallenge(password, userAttributes, this);
resolve(data);
},
});
});
};
return (
<AccountContext.Provider value={{ authenticate }}>
{props.children}
</AccountContext.Provider>
);
};
export { Account, AccountContext };
我的主要 app.js 文件是:
import {Account} from './components/Login/Account'
return (
<Account>
<ErrorBoundary context="App">
<Provider store={store}>
<AppProvider config={this._appConfig}>
<I18nextProvider i18n={i18n}>
<Router basename={routerBasename}>
<WhiteLabelingContext.Provider value={whiteLabeling}>
<OHIFStandaloneViewer />
</WhiteLabelingContext.Provider>
</Router>
</I18nextProvider>
</AppProvider>
</Provider>
</ErrorBoundary>
</Account>
);
}
我的消费者文件(LoginPage.js)是:
import React, { useState, useContext } from 'react';
import { AccountContext } from './Account';
const LoginPage = () => {
const [username, setUsername] = useState('');
const [password, setPassword] = useState('');
const { authenticate } = useContext(AccountContext);
const onSubmit = e => {
e.preventDefault();
authenticate(username, password)
.then(data => {
console.log('logged in ', data);
})
.catch(err => {
console.error('failed to login: ', err);
});
};
我得到的错误是:“无法读取未定义的属性‘身份验证’”
你能告诉我我哪里出错了吗? 或者有什么更好的方法吗?
提前致谢。
答案 0 :(得分:0)
证据表明 LoginPage
未在上下文提供程序中呈现。如果是,对 useContext
的调用将返回您传递给提供程序的 { authenticate }
对象。相反,它返回 undefined
,这是上下文的默认值,因为您没有在对 createContext
的调用中提供自己的默认值。
幸运的是,有一种简单的方法可以测试这种情况。在对 createContext
的调用中,传递一个如下所示的对象:
{
authenticate() {
return Promise.reject('I'm not inside a provider!');
}
}
如果理论正确,您应该会在触发 onSubmit
时在控制台中看到失败日志。