You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何借助Yup的when条件实现开始/结束日期的合法范围校验?

Yup 日期范围校验:确保开始日期不晚于结束日期

要实现startAt不晚于endAt、endAt不早于startAt的校验,你可以通过Yup的when结合自定义test,或者直接在对象层面添加全局校验来实现,以下是具体方案:

方案一:使用when针对单个字段校验

通过when监听另一个字段的状态,仅当该字段存在时触发日期范围校验,同时支持字段为null的场景:

import { date, object } from 'yup';

export const yupSchema = object({
  startAt: date()
    .typeError('Invalid date')
    .nullable()
    // 当endAt不为空时,校验startAt不晚于endAt
    .when('endAt', {
      is: (endAt) => endAt !== null,
      then: (schema) => schema.test({
        test: (startAt, { parent }) => startAt === null || startAt <= parent.endAt,
        message: '开始日期不能晚于结束日期',
      }),
    }),
  endAt: date()
    .typeError('Invalid date')
    .nullable()
    // 当startAt不为空时,校验endAt不早于startAt
    .when('startAt', {
      is: (startAt) => startAt !== null,
      then: (schema) => schema.test({
        test: (endAt, { parent }) => endAt === null || endAt >= parent.startAt,
        message: '结束日期不能早于开始日期',
      }),
    }),
});

说明

  • when的is条件用于判断是否触发后续校验:这里仅当另一个日期字段不为null时才执行范围校验
  • 自定义test中通过context.parent可以获取整个表单的字段值,从而对比两个日期
  • 保留nullable(),允许字段为空;如果需要强制必填,可移除nullable()并添加required('必填提示')

方案二:对象层面全局校验(更简洁)

如果不需要给单个字段单独提示错误,可直接在对象Schema上添加全局校验,一次性验证两个日期的范围:

import { date, object } from 'yup';

export const yupSchema = object({
  startAt: date().typeError('Invalid date').nullable(),
  endAt: date().typeError('Invalid date').nullable(),
})
.test({
  test: ({ startAt, endAt }) => {
    // 仅当两个日期都不为空时才校验范围
    if (startAt && endAt) {
      return startAt <= endAt;
    }
    return true;
  },
  message: '开始日期不能晚于结束日期',
});

这种方式代码更简洁,适合不需要区分单个字段错误提示的场景。

内容的提问来源于stack exchange,提问作者niltonxp

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.26 02:06:25