如何在React中有条件地进行Yup验证



我得到了这个简单的例子,它与我的怀疑高度相关,所以我用它作为我的例子。因此,在链接中,我们可以看到一个简单的Yup验证模式。因此,当我们在电子邮件字段中键入内容时,电子邮件验证中的控制台日志会被打印出来,这显然很好。但是,即使我们在名称字段中键入一些内容,控制台也会被打印出来。

验证模式

const schema = yup.object({
name: yup.string().required(),
email: yup.string().test('is-jimmy', '${path} is not Jimmy', function (value) {
return new Promise((res, rej) => {
console.log('firing async validation')
setTimeout(() => res(value !== "foo@bar.com"))
}) 
})
})

示例-https://stackblitz.com/edit/yup-async-validation-test?file=index.js

请给我一个解决方案来解决这个问题,这样控制台只有在我在电子邮件字段中键入时才能打印。

替代解决方案-有没有任何方法可以在Formik中添加1个以上的验证模式来避免这个问题?

// like this
<Formik validationSchema = [userValidationSchema,emailSchema] />

这就是yup的工作方式,在一些字段更改时,您传递一个新对象进行验证,而yup不知道最近实际更改了哪个字段,因此对整个对象运行验证。

如果您将验证模式拆分为每个字段的单独验证,则可以将其配置为按预期工作。

您可以通过在启动时初始化一个状态来实现这一点,即

const [check,setCheck]=useState();

然后在手柄更改功能中设置状态:

handleChange = (field) => (e) => {
this.setState({ [field]: e.target.value});
setCheck(field) //setting the state
schema.isValid(this.state);
};

最后在你的yup模式中添加一个检查:

const schema = yup.object({
name: yup.string().required(),
email: yup
.string()
.test('is-jimmy', '${path} is not Jimmy', function (value) {
return new Promise((res, rej) => {
//condition for not logging in case of name
if(check!= "name") {
console.log('firing async validation');
}
setTimeout(() => res(value !== 'foo@bar.com'));
});
}),
});

最新更新