0

0

如何复用 Joi Schema 的属性定义而不继承校验规则?

霞舞

霞舞

发布时间:2026-01-05 19:26:02

|

690人浏览过

|

来源于php中文网

原创

如何复用 Joi Schema 的属性定义而不继承校验规则?

本文介绍在 joi 中安全复用基础 schema 属性(如字段定义)的方法,避免意外继承 `.xor()`、`.messages()` 等链式配置,核心是使用 `object.keys()` 方法重置 schema 结构。

在使用 Joi 构建复杂验证逻辑时,常需复用已有字段定义(如 a 和 b 的类型、修饰符等),但又不希望继承其附加的约束(如 .xor())或错误消息(.messages())。直接对已链式调用的 schema 调用 .append() 或 .keys() 会保留原有元信息,导致行为不符合预期。

正确做法是:将基础字段定义封装为“纯净”的 Joi.object() 实例(即仅含 keys,无链式修饰),再通过 .keys() 方法扩展新字段。该方法会创建一个全新 schema,仅继承原始对象的键值定义,彻底剥离所有后续链式配置(如 xor、messages、requiredKeys 等)。

以下为推荐实现:

Shakker
Shakker

多功能AI图像生成和编辑平台

下载
const Joi = require('@hapi/joi'); // Joi v17+(注意:v17.9.1 及以上)

// ✅ 纯净基础 schema:仅定义字段结构,不添加任何链式约束
const baseSchema = Joi.object({
  a: Joi.string().trim().empty(null, ''),
  b: Joi.string().guid().empty(null),
});

// ✅ 使用 .keys() 复用并扩展字段(自动清除原有 xor/messages)
const extendedSchema = baseSchema.keys({
  c: Joi.string().trim(),
});

// ✅ 分别为不同场景添加独立约束与消息
const firstSchema = baseSchema.xor('a', 'b')
  .messages({
    'object.missing': 'One of "a", "b" is required.',
    'object.xor': 'Only one of "a", "b" is allowed.',
  });

const secondSchema = extendedSchema.xor('a', 'b', 'c')
  .messages({
    'object.missing': 'One of "a", "b", "c" is required.',
    'object.xor': 'Only one of "a", "b", "c" is allowed.',
  });

⚠️ 注意事项:

  • baseSchema.keys({...}) 是关键:它返回一个新 schema 实例,仅保留原始 keys 定义,不会携带 xor、messages、label() 等链式状态;
  • ❌ 错误示例:baseSchema.append({ c: ... }) 会保留原 xor 和 messages,导致二次应用冲突;
  • ❌ 避免在已调用 .xor() 或 .messages() 后再调用 .keys() —— 应始终从“纯净 schema”出发;
  • Joi v17+ 中 Joi.object() 默认返回不可变 schema,每次链式调用均生成新实例,因此 baseSchema 必须是未修饰的原始定义。

总结:Joi 的 object.keys() 不仅用于覆盖字段,更是解耦“结构定义”与“业务约束”的核心工具。将字段定义(schema structure)与验证策略(validation rules)分离,可显著提升 schema 的可维护性与复用性。

相关专题

更多
append用法
append用法

append是一个常用的命令行工具,用于将一个文件的内容追加到另一个文件的末尾。想了解更多append用法相关内容,可以阅读本专题下面的文章。

342

2023.10.25

python中append的用法
python中append的用法

在Python中,append()是列表对象的一个方法,用于向列表末尾添加一个元素。想了解更多append的更多内容,可以阅读本专题下面的文章。

1066

2023.11.14

python中append的含义
python中append的含义

本专题整合了python中append的相关内容,阅读专题下面的文章了解更多详细内容。

171

2025.09.12

C++ 高性能计算与并行编程
C++ 高性能计算与并行编程

本专题专注于 C++ 在高性能计算(HPC)与并行编程中的应用,涵盖多线程、并发数据处理、OpenMP、MPI、GPU加速等技术。通过实际案例,帮助开发者掌握 如何利用 C++ 进行大规模数据计算和并行处理,提高程序的执行效率,适应高性能计算与数据密集型应用场景。

4

2026.01.08

C++ 高性能计算与并行编程
C++ 高性能计算与并行编程

本专题专注于 C++ 在高性能计算(HPC)与并行编程中的应用,涵盖多线程、并发数据处理、OpenMP、MPI、GPU加速等技术。通过实际案例,帮助开发者掌握 如何利用 C++ 进行大规模数据计算和并行处理,提高程序的执行效率,适应高性能计算与数据密集型应用场景。

0

2026.01.08

PPT动态图表制作教程大全
PPT动态图表制作教程大全

本专题整合了PPT动态图表制作相关教程,阅读专题下面的文章了解更多详细内容。

36

2026.01.07

c++ Libcurl用法详解
c++ Libcurl用法详解

本专题整合了c++ Libcurl用法详解,阅读专题下面的文章了解更多详细内容。

0

2026.01.07

c++ Libcurl用法大全
c++ Libcurl用法大全

本专题整合了c++ Libcurl用法详解,阅读专题下面的文章了解更多详细内容。

0

2026.01.07

C++ vector用法汇总
C++ vector用法汇总

本专题整合了C++中vector的用法大全,阅读专题下面的文章了解更多详细内容。

2

2026.01.07

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
Java 教程
Java 教程

共578课时 | 43.2万人学习

国外Web开发全栈课程全集
国外Web开发全栈课程全集

共12课时 | 0.9万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号