如何在 recaptcha 回调中访问更新的道具
How to access updated props in recaptcha callback
我正在尝试通过 React 和 Redux 使用集成在 firebase 身份验证中的 reCaptcha。
const Login = props => {
useEffect(() => {
window.recaptchaVerifier = new firebase.auth.RecaptchaVerifier('login-button', {
'size': 'invisible',
'callback': () => login()
}
);
window.recaptchaVerifier.render()
}, []);
function login() {
console.log(props)
firebaseLogin(props.email, props.password).then(() => {
...
}
).catch(function (error) {
console.log(error);
...
});
}
function onChangePassword(event) {
props.onChangePassword(event.target.value)
}
function onChangeEmail(event) {
props.onChangeEmail(event.target.value)
}
return (
...
<form>
<label>Dirección de Email</label>
<div className="form-group">
<input type="email"
className={`form-control ${emailValidation ? "is-invalid" : ""}`}
placeholder="nombre@mail.com"
onChange={onChangeEmail} value={props.email} tabIndex={1}
autoComplete={"username"}
required/>
<div className="invalid-feedback">
{emailValidation}
</div>
</div>
<div className="form-group">
<div className="row">
<div className="col">
<label>Contraseña</label>
</div>
<div className="col-auto">
<Link to="/reset-password" className="form-text small text-muted">
Olvidé mi contraseña
</Link>
</div>
</div>
<div className="input-group input-group-merge">
<input type={showPassword ? "text" : "password"}
className={`form-control ${passwordValidation ? "is-invalid" : ""} form-control-appended`}
placeholder="Ingrese su contraseña" onChange={onChangePassword}
value={props.password} required tabIndex={2}
autoComplete={"current-password"}/>
<div className="input-group-append">
<span className="input-group-text clickable"
onClick={() => setShowPassword(!showPassword)}>
<i className="fe fe-eye"/>
</span>
</div>
<div className="invalid-feedback">
{passwordValidation}
</div>
</div>
</div>
<button type="submit" className="btn btn-lg btn-block btn-primary mb-3"
id={"login-button"}
tabIndex={3}>
Acceder
</button>
</form>
...
)
};
const mapDispatchToProps = dispatch => ({
onChangeEmail: value =>
dispatch({type: UPDATE_LOGIN_FIELD, key: 'formEmail', value}),
onChangePassword: value =>
dispatch({type: UPDATE_LOGIN_FIELD, key: 'password', value}),
});
const mapStateToProps = state => ({
email: state.authentication.formEmail,
password: state.authentication.password,
});
export default connect(mapStateToProps, mapDispatchToProps)(Login);
问题是登录回调中的道具已经过时,并且不包含在 redux 存储中加载的电子邮件和密码,它只包含触发 useEffect 时可用的道具。 (我看到 console.log(props))
我不知道如何保留对更新道具的引用。我试过使用 useRef 挂钩并将其作为参数发送到登录名,但这也没有用。
我也试过使用电子邮件和密码道具作为 useEffect 依赖项,但这会多次触发 recaptcha 生成,而且效率非常低。
感谢您的帮助!
使用回调挂钩以高性能方式访问最新状态。
const login = useCallback( () => {
console.log(props)
firebaseLogin(props.email, props.password).then(() => {
...
}
).catch(function (error) {
console.log(error);
...
});
}, [ props ] ):
在官方 React 文档中它指出:"Pass an inline callback and an array of dependencies. useCallback will return a memoized version of the callback that only changes if one of the dependencies has changed." 在我们的例子中,每次 [props]
更改时,登录功能都会自行更新,这意味着当我们获得新道具时,我们将获得一个新的登录功能。
查看官方 hook documentation 以获取有关如何使用 which hook 的更多信息。
您甚至可以将 useCallback
用于所有三个功能!
const onChangePassword = useCallback( (event) => {
props.onChangePassword(event.target.value)
}, [props.onChangePassword]);
const onChangeEmail = useCallback( (event) => {
props.onChangeEmail(event.target.value)
}, [props.onChangeEmail]);
每次从 redux 或高阶组件更新 props.onChangePassword
和 props.onChangeEmail
函数时,onChangePassword
和 onChangeEmail
回调函数将更新并创建新函数。
似乎可以作为
window.login = useCallback(() => {
console.log(props);
firebaseLogin(props.email, props.password).then(() => {
...
}
).catch(function (error) {
console.log(error);
....
}
}, [props]);
useEffect(() => {
window.recaptchaVerifier = new firebase.auth.RecaptchaVerifier('login-button', {
'size': 'invisible',
'callback': () => window.login(),
}
);
window.recaptchaVerifier.render();
}, []);
还有一个问题,但与本题无关
我正在尝试通过 React 和 Redux 使用集成在 firebase 身份验证中的 reCaptcha。
const Login = props => {
useEffect(() => {
window.recaptchaVerifier = new firebase.auth.RecaptchaVerifier('login-button', {
'size': 'invisible',
'callback': () => login()
}
);
window.recaptchaVerifier.render()
}, []);
function login() {
console.log(props)
firebaseLogin(props.email, props.password).then(() => {
...
}
).catch(function (error) {
console.log(error);
...
});
}
function onChangePassword(event) {
props.onChangePassword(event.target.value)
}
function onChangeEmail(event) {
props.onChangeEmail(event.target.value)
}
return (
...
<form>
<label>Dirección de Email</label>
<div className="form-group">
<input type="email"
className={`form-control ${emailValidation ? "is-invalid" : ""}`}
placeholder="nombre@mail.com"
onChange={onChangeEmail} value={props.email} tabIndex={1}
autoComplete={"username"}
required/>
<div className="invalid-feedback">
{emailValidation}
</div>
</div>
<div className="form-group">
<div className="row">
<div className="col">
<label>Contraseña</label>
</div>
<div className="col-auto">
<Link to="/reset-password" className="form-text small text-muted">
Olvidé mi contraseña
</Link>
</div>
</div>
<div className="input-group input-group-merge">
<input type={showPassword ? "text" : "password"}
className={`form-control ${passwordValidation ? "is-invalid" : ""} form-control-appended`}
placeholder="Ingrese su contraseña" onChange={onChangePassword}
value={props.password} required tabIndex={2}
autoComplete={"current-password"}/>
<div className="input-group-append">
<span className="input-group-text clickable"
onClick={() => setShowPassword(!showPassword)}>
<i className="fe fe-eye"/>
</span>
</div>
<div className="invalid-feedback">
{passwordValidation}
</div>
</div>
</div>
<button type="submit" className="btn btn-lg btn-block btn-primary mb-3"
id={"login-button"}
tabIndex={3}>
Acceder
</button>
</form>
...
)
};
const mapDispatchToProps = dispatch => ({
onChangeEmail: value =>
dispatch({type: UPDATE_LOGIN_FIELD, key: 'formEmail', value}),
onChangePassword: value =>
dispatch({type: UPDATE_LOGIN_FIELD, key: 'password', value}),
});
const mapStateToProps = state => ({
email: state.authentication.formEmail,
password: state.authentication.password,
});
export default connect(mapStateToProps, mapDispatchToProps)(Login);
问题是登录回调中的道具已经过时,并且不包含在 redux 存储中加载的电子邮件和密码,它只包含触发 useEffect 时可用的道具。 (我看到 console.log(props))
我不知道如何保留对更新道具的引用。我试过使用 useRef 挂钩并将其作为参数发送到登录名,但这也没有用。
我也试过使用电子邮件和密码道具作为 useEffect 依赖项,但这会多次触发 recaptcha 生成,而且效率非常低。
感谢您的帮助!
使用回调挂钩以高性能方式访问最新状态。
const login = useCallback( () => {
console.log(props)
firebaseLogin(props.email, props.password).then(() => {
...
}
).catch(function (error) {
console.log(error);
...
});
}, [ props ] ):
在官方 React 文档中它指出:"Pass an inline callback and an array of dependencies. useCallback will return a memoized version of the callback that only changes if one of the dependencies has changed." 在我们的例子中,每次 [props]
更改时,登录功能都会自行更新,这意味着当我们获得新道具时,我们将获得一个新的登录功能。
查看官方 hook documentation 以获取有关如何使用 which hook 的更多信息。
您甚至可以将 useCallback
用于所有三个功能!
const onChangePassword = useCallback( (event) => {
props.onChangePassword(event.target.value)
}, [props.onChangePassword]);
const onChangeEmail = useCallback( (event) => {
props.onChangeEmail(event.target.value)
}, [props.onChangeEmail]);
每次从 redux 或高阶组件更新 props.onChangePassword
和 props.onChangeEmail
函数时,onChangePassword
和 onChangeEmail
回调函数将更新并创建新函数。
似乎可以作为
window.login = useCallback(() => {
console.log(props);
firebaseLogin(props.email, props.password).then(() => {
...
}
).catch(function (error) {
console.log(error);
....
}
}, [props]);
useEffect(() => {
window.recaptchaVerifier = new firebase.auth.RecaptchaVerifier('login-button', {
'size': 'invisible',
'callback': () => window.login(),
}
);
window.recaptchaVerifier.render();
}, []);
还有一个问题,但与本题无关