React+AWS Cognito教程三:在Cognito中更改密码


在上两篇文章介绍了如何注册,配置AWS Cognito User Pool,用户登录,Cognito中的Session,及如何注销用户的登录。下面介绍如何实现更改密码的功能。其核心步骤包括:获取用户登录后的相关属性,实现更改密码组件。

AWS Cognito
AWS Cognito

声明:本教程代码参考了Alexzander Flores的代码并在其基础上进行了修改和优化。

AWS Cognito系列教程:

更新Accounts.js中getSession方法

在之前的Accounts.js中,getSession方法只是用来获取用户的Session,如果想要更换密码,还需要一些用户属性(主要是email),因此需要对这个方法进行重写:

javascript
user.getSession(async (err, session) => {
  if (err) {
    reject();
  } else {
    const attributes = await new Promise((resolve, reject) => {
      user.getUserAttributes((err, attributes) => {
        if (err) {
          reject(err);
        } else {
          const results = {};

          for (let attribute of attributes) {
            const { Name, Value } = attribute;
            console.log(Name);
            results[Name] = Value;
          }

          resolve(results);
        }
      });
    });

    resolve({
      user,
      ...session,
      ...attributes
    });
  }
});

在控制台可以看到除了Session对象外,还有email,email_verified,sub等属性。

添加ChangePassword.js

这里的核心功能包括:

  • 使用useRef hook获取用户输入的新旧密码。
  • 使用旧密码进行登录验证,验证通过后更改密码。

下面是ChangePassword.js的代码:

javascript
import React, { useRef, useContext } from 'react'
import { AccountContext } from './Accounts';

export default function ChangePassword() {
    const currentPasswordElement = useRef('');
    const newPasswordElement = useRef('');

    const { getSession, authenticate } = useContext(AccountContext);

    const handleSubmit = event => {
        event.preventDefault();

        getSession().then(({ user, email }) => {
            authenticate(email, currentPasswordElement.current.value).then(() => {
              user.changePassword(currentPasswordElement.current.value, newPasswordElement.current.value, (err, result) => {
                if (err) console.error(err);
                console.log(result);
              });
            });
        });
    }

    return (
        <div>
            <form onSubmit={handleSubmit}>
                Current password: 
                <input type="text" ref={currentPasswordElement}/><br/>
                New password: 
                <input type="text" ref={newPasswordElement}/><br/>
                <button type="submit">Change password</button>
            </form>
        </div>
    )
}

添加settings.js

只有用户登录后才需要显示更改密码组件,因此这里定义一个settings.js,在其中实现这个验证逻辑:

Settings.js:

javascript
import React, { useState, useContext, useEffect } from 'react';
import { AccountContext } from './Accounts';
import ChangePassword from './ChangePassword';

export default function Settings() {
    const [loggedIn, setLoggedIn] = useState(false);
    const { getSession } = useContext(AccountContext);

    useEffect(() => {
        getSession()
          .then(session => {
            setLoggedIn(true);
          })
          // eslint-disable-next-line react-hooks/exhaustive-deps
    }, []);

    return (
        <div>
            {loggedIn && (
                <>
                    Settings
                    <ChangePassword/>
                </>
            )}
        </div>
    )
}

更新App.js

javascript
function App() {
  return (
    <Account>
      <Status/>
      <hr/>
      <Signup/>
      <hr/>
      <Login/>
      <hr/>
      <Settings/>
    </Account>
  );
}

这样在用户登录后(需要刷新页面)就可以看到更改密码组件了。


文章作者: 逻思
版权声明: 本博客所有文章除特別声明外,均采用 CC BY-NC-ND 4.0 许可协议。转载请注明来源 逻思 !