Search code examples
reactjstypescriptviteyup

Yup: Migrating when to 1.0.2


Given a React state variable

const [selectedFormtype, setSelectedFormtype] = useState<Nullable<MyFormTypeVm>>()

Types/interfaces are defined like this

type Nullable<T> = T | null

interface MyFormTypeVm {
    readonly id: NonNullable<string>
    readonly labelCompanyId: Nullable<string>
}

interface MyFormVm {
    companyId: Nullable<string>
    // remaining properties goes here
}

I have this working solution with yup:0.32.11.

const validationSchema: yup.SchemaOf<MyFormVm> = yup.object().shape({
    companyId: yup.string().when([], {
        is: () => selectedFormtype?.labelCompanyId,
        then: yup.string()
            .required('Company-id is required')
            .matches(/^[8|9]\d{8}$/i, 'Company-id has to start with 8 or 9')
    })
).required()

I can see from here how to implement a when that refers to another field in the validation scope

 string()
-   .when('other', function (other) => {
-      if (other) return this.required()
+   .when('other', ([other], schema) => {
+     return other ? schema.required() : schema
  })

The outline for my validationSchema should look like this according to the migration guide, but it gives me a TS2322-error.

const validationSchema: yup.ObjectSchema<MyFormVm> = yup.object().shape({
        companyId: yup.string().when('other', ([], schema) => {
            return selectedFormtype?.labelCompanyId
                ? schema
                      .required('required text goes here')
                      .matches(/^[8|9]\d{8}$/i, 'regex text goes here')
                : schema
        })
})

I've added the following to tsconfig.json:

"strictNullChecks": true, "strictFunctionTypes": false


Solution

  • Finally found the way through this in the docs. .default<Nullable<string>>(null) solved casting from string | null | undefined to string | null.

    const validationSchema: yup.ObjectSchema<MyFormVm> = yup.object().shape({
        companyId: yup.string().default<Nullable<string>>(null).when(([], schema) =>
            selectedFormtype?.labelCompanyId
                ? schema
                    .required('required msg goes here')
                    .matches(/^[8|9]\d{8}$/i, 'regex msg goes here')
                : schema.nullable()
        )
    })