reactjs 如何在Yup异步验证中设置动态错误信息?

htzpubme  于 2022-11-29  发布在  React
关注(0)|答案(5)|浏览(293)

我正在Formik中尝试使用Yup的.test()方法进行异步验证,需要设置从API获得的错误消息。根据后端的一些条件,错误消息会有所不同。
尝试了此处提到的几种解决方案
https://github.com/jquense/yup/issues/222Dynamic Validation Messages Using Yup and Typescript的函数
但是Yup抛出了test()中给出的默认错误消息。
文件上说
所有测试都必须提供名称、错误消息和必须返回true或false或ValidationError的验证函数。若要使测试异步,请返回解析true或false或ValidationError的承诺。
我正在使用错误消息解析新的ValidationError,但它仍抛出默认错误。
下面是代码。

const schema = Yup.object().shape({
  email: Yup.string().test(
    "email_async_validation",
    "Email Validation Error", // YUP always throws this error
    value => {
      return new Promise((resolve, reject) => {
        emailValidationApi(value)
          .then(res => {
            const { message } = res.data; // I want this error message to be shown in form.
            resolve(new Yup.ValidationError(message));
          })
          .catch(e => {
            console.log(e);
          });
      });
    }
  )
});
eqqqjvef

eqqqjvef1#

我使用function语法代替了验证函数的箭头函数,使其工作。
医生说:
测试函数是用一个特殊的上下文或this值调用的,它公开了一些有用的元数据和函数。注意,要使用this上下文,测试函数必须是一个函数表达式(function test(value) {}),而不是一个箭头函数,因为箭头函数有词法上下文。
下面是工作代码。

const schema = Yup.object().shape({
  email: Yup.string()
    .email("Not a valid email")
    .required("Required")
    .test("email_async_validation", "Email Validation Error", function (value) { // Use function
      return emailValidationApi(value)
        .then((res) => {
          const message = res;
          console.log("API Response:", message);
          return this.createError({ message: message });
          // return Promise.resolve(this.createError({ message: message })); // This also works
        })
        .catch((e) => {
          console.log(e);
        });
    })
});
eivgtgni

eivgtgni2#

实际上你几乎是正确的。你只需要使用以下代码:

resolve(this.createError({ message: message }));

如果还是不行就告诉我

nzkunb0c

nzkunb0c3#

我也可以用箭头函数来做这件事。

const schema = Yup.object().shape({
 email: Yup.string()
  .email("Not a valid email")
  .required("Required")
  .test("email_async_validation", "Email Validation Error", (value, {createError}) { 
    return emailValidationApi(value)
      .then((res) => {
        const message = res;
        console.log("API Response:", message);
        return createError({ message: message });
      })
      .catch((e) => {
        console.log(e);
      });
    })
  });
9ceoxa92

9ceoxa924#

不要传递第二个参数,因为我们通常将其作为错误消息传递,而是使用“createError”创建您自己的自定义消息,并根据您的条件返回它。

import * as yup from "yup";

const InitiateRefundSchema = yup.object().shape({
  amountPaid: yup.number(),
  refundAmount: yup
    .number()
    .test("test-compare a few values", function (value) {
      let value1 = this.resolve(yup.ref("amountPaid"));
      let value2 = this.resolve(yup.ref("refundAmount"));
      if (value1 < value2) {
        return this.createError({
          message: `refund amount cannot be greater than paid amount '${value1}'`,
          path: "refundAmount", // Fieldname
        });
      } else return true;
    }),
})
yruzcnhs

yruzcnhs5#

通过Internatization('vue-i18 n')和Yup('yup')选项,您可以将其用作:

const fullname = yup.string().required(this.$t('validate.required')).min(8, this.$t('validate.min', {min: '8'}))

因此,对于下面的这一行,文本错误消息将随着区域设置选项的更改而更改。

this.$t('validate.min')

pt.ts

validation: {
        required: 'Esse campo é obrigatório',
        size_min: 'Deve no minimo {min} caracteres',
    }

en.ts

validation: {
        required: 'Required please',
        size_min: 'Please only {min} caracteres',
    }

相关问题