如何在JSON Schema中添加自定义属性并基于属性值执行对应操作
如何添加自定义属性,并对自定义属性为特定值的JSON数据执行对应操作?
你这个场景完全可以基于JSON Schema实现,JSON Schema原生支持自定义扩展关键字,不需要换其他方案。
具体实现逻辑
核心思路分两步:先从Schema里提取所有persist属性为true的字段清单,再从实际业务数据中筛选对应字段完成持久化。
- 自定义属性不需要做特殊声明,直接在字段定义里加
persist字段即可,所有主流JSON Schema校验库都会自动忽略非标准的自定义关键字,不会影响原有校验逻辑。如果后续要跨团队/跨工具复用这套Schema,也可以给自定义关键字加专属前缀(比如x-persist),避免和未来的标准关键字冲突。 - 提取字段时要注意递归处理嵌套结构:如果字段类型是嵌套对象、元素为对象的数组,要深入子节点继续扫描,不要只处理第一层属性。如果Schema里用了
$ref做片段引用,扫描前先调用工具库的解引用方法把Schema展开,否则会漏掉引用节点里的标记。
给一个可直接运行的字段提取参考实现(JavaScript):
/** * 递归从JSON Schema中提取所有标记persist: true的字段路径 * @param {object} schema 待处理的JSON Schema对象 * @param {string} parentPath 父级路径,递归时内部传参用 * @returns {string[]} 需要持久化的字段路径列表 */ function getPersistFields(schema, parentPath = '') { const result = [] if (schema.type !== 'object' || !schema.properties) return result for (const [field, config] of Object.entries(schema.properties)) { const currentPath = parentPath ? `${parentPath}.${field}` : field if (config.persist === true) result.push(currentPath) // 递归处理嵌套对象 if (config.type === 'object' && config.properties) { result.push(...getPersistFields(config, currentPath)) } // 递归处理对象数组的元素属性 if (config.type === 'array' && config.items?.type === 'object') { result.push(...getPersistFields(config.items, `${currentPath}[]`)) } } return result } // 测试示例Schema const demoSchema = { "type": "object", "properties": { "productId": { "description": "The unique identifier for a product", "type": "integer", "persist": true }, "productCost": { "description": "The cost of a product", "type": "integer", "persist": false } }, "required": ["productCost"] } console.log(getPersistFields(demoSchema)) // 输出: ['productId']
拿到字段路径列表后,按路径从实际传入的业务JSON中取值,组装成数据库插入/更新的实体即可,不要直接把全量请求数据写入数据库。
什么时候不适合把标记写在JSON Schema里?
如果你的持久化逻辑比较复杂,就不要硬往Schema里塞配置,建议单独抽离持久化规则配置:
- 存在动态持久化规则:比如不同权限等级的用户提交同一份数据,可持久化的字段不一样
- 字段需要额外的入库配置:比如字段要做类型转换、对应数据库列名和JSON字段名不一致、有字段加密/脱敏要求
- 存在关联表逻辑:比如部分字段要写入其他关联表,不是存在主表中
这种场景单独维护一份持久化映射配置表,把字段规则、转换逻辑、存储位置都写在配置里,维护成本比混在Schema里低很多。
内容的提问来源于stack exchange,提问作者user19316574
相关产品推荐
相关产品推荐

