lo siento por la publicación larga, estoy tratando de restablecer la contraseña por correo electrónico, hasta ahora logré enviar el enlace de restablecimiento al correo electrónico, ahora mismo probé esto en el backend:
userRouter.get('/reset', expressAsyncHandler(async (req, res) => { const user = await User.findOne({ where: { resetPasswordToken: req.query.resetPasswordToken, resetPasswordExpires: { $gt: Date.now(), }, }, }); if (user) { console.log('token matched') res.status(200).send({ message: 'password reset link ok' }) } else { console.log('password reset link is invalid or has expired'); res.json('password reset link is invalid or has expired'); } }) );En la contraseña olvidada, hice algo como esto para actualizar los dos campos:
user.update({ resetPasswordToken: token, resetPasswordExpires: Date.now() + 360000, });Mi modelo de usuario es:
name: { type: String, required: true }, email: { type: String, required: true, unique: true }, password: { type: String, required: true }, isAdmin: { type: Boolean, default: false, required: true }Cuando trato de usar la cláusula where para verificar que resetPasswordToken está devolviendo a todos mis usuarios, lo cual es incorrecto. Estoy pensando que necesito declarar resetPasswordToken y resetPasswordExpires en el modelo para que funcionen dos. ¿O es suficiente? Otra pregunta sería, ¿qué tendría que enviar a la interfaz para que funcione?
En react-redux, tengo la siguiente función, pero estoy 100% seguro de que estoy enviando los datos incorrectos:
export const checktoken = (email) => async (dispatch) => { dispatch({ type: USER_RESET_PASSWORD_REQUEST, payload: { email } }); try { const { data } = await Axios.get('/api/users/reset'); dispatch({ type: USER_RESET_PASSWORD_SUCCESS, payload: data });; localStorage.setItem('userInfo', JSON.stringify(data)); } catch (error) { dispatch({ type: USER_RESET_PASSWORD_FAIL, payload: error.response && error.response.data.message ? error.response.data.message : error.message, }); } };En primer lugar, su modelo no tiene el campo resetPasswordToken y resetPasswordExpires . Lo que significa que su update no funcionará. Supongo que está usando mongoose, y mongoose no actualizará los campos que no existen en el modelo.
Agregue las entradas de la siguiente manera.
name: { type: String, required: true }, email: { type: String, required: true, unique: true }, password: { type: String, required: true }, isAdmin: { type: Boolean, default: false, required: true }, resetPasswordToken: { type: String }, resetPasswordExpires: { type: Number }En segundo lugar, su consulta es incorrecta. La consulta debe ser como...
const user = await User.findOne({ resetPasswordToken: req.query.resetPasswordToken, resetPasswordExpires: { $gt: Date.now(), }, }); Nota : siempre verifique su base de datos para ver si sus entradas de update están realmente actualizadas.
Al verificar que el usuario + token existe, puede res.status(200).send() a su aplicación web.
En su aplicación web, solicitará al usuario la nueva contraseña. Una vez que el usuario ingresó la nueva contraseña, enviará la nueva contraseña Y el token (nuevamente) al backend.
Esta vez, deberá verificar el token nuevamente antes de actualizar la contraseña en el modelo de usuario. Esto asegurará que la contraseña de restablecimiento provenga de una fuente válida.
probablemente desee eliminar resetPasswordToken y resetPasswordExpires del documento una vez que se actualice la contraseña, ya que ya no es necesaria.