Javascript sailsjs:使用嵌入的JSON属性验证模型
如何验证Sails JS中object类型属性的模型 我知道带有简单值(例如字符串)的属性是可以接受的,但是这对于嵌套的JSON是如何工作的呢 例如:Javascript sailsjs:使用嵌入的JSON属性验证模型,javascript,sails.js,Javascript,Sails.js,如何验证Sails JS中object类型属性的模型 我知道带有简单值(例如字符串)的属性是可以接受的,但是这对于嵌套的JSON是如何工作的呢 例如: { name: 'John', location: { x: 23, y: 15, z: 50 } } 那么它的形式是: { name: { type: 'string', required: true, }, loc
{
name: 'John',
location: {
x: 23,
y: 15,
z: 50
}
}
那么它的形式是:
{
name: {
type: 'string',
required: true,
},
location: {
x: {
type: 'number',
required: true
},
y: {
type: 'number',
required: true
},
z: {
type: 'number',
required: true
}
}
}
Waterline(Sails ORM)不直接支持嵌套模式。您可以改为使用验证属性:
module.exports = {
types: {
location: function(val) {
// Make sure that x, y and z are present and are numbers.
// This won't allow numeric strings, but you can adjust to fit your needs.
return (_.isNumber(val.x) && _.isNumber(val.y) && _.isNumber(val.z));
}
},
attributes: {
location: {
type: 'json',
required: true, // If you want the whole attribute to be required
location: true // Validate that the attribute has the schema you want
}
...more attributes...
}
};
到目前为止,我找到的最优雅的解决方案是使用“机器”库(它为sailsjs中的操作提供了动力,由sailsjs人员构建)来定义类型验证“机器” 首先,您需要一个类型定义帮助器:
$ cat api/types/define.js
const buildWithCustomUsage = require("machine").buildWithCustomUsage;
function validateWith(machine, inputs) {
machine(inputs).now();
return true;
}
module.exports = function (def) {
const machine = buildWithCustomUsage({
def,
extraArginsTactic: "doNotCheck"
});
return {
machine,
validate: validateWith.bind(null, machine)
};
};
然后可以定义如下类型:
$ cat api/types/QuoteRequest.js
module.exports = require("./define")({
description: "Quote request type definition",
inputs: {
input_currency_type: {
description: "Input currency type",
type: "string",
required: true
},
amount_requested: {
description: "Requested amount in input currency",
type: "string",
required: true
}
},
sync: true,
fn: function (inputs, exits) {
// your other validation logics
return exits.success();
}
});
inputs: {
request: {
type: "json",
required: true,
custom: require("../../types/QuoteRequest").validate
}
},
您需要确保设置了sync:true
要在控制器中使用它,请执行以下操作:
$ cat api/types/QuoteRequest.js
module.exports = require("./define")({
description: "Quote request type definition",
inputs: {
input_currency_type: {
description: "Input currency type",
type: "string",
required: true
},
amount_requested: {
description: "Requested amount in input currency",
type: "string",
required: true
}
},
sync: true,
fn: function (inputs, exits) {
// your other validation logics
return exits.success();
}
});
inputs: {
request: {
type: "json",
required: true,
custom: require("../../types/QuoteRequest").validate
}
},
希望有帮助 我做了一个结构比较函数来处理这种情况,我想和大家分享一下,希望能给大家带来启发和帮助: 假设您使用的是sails v1 使用以下代码在
/api/services
中创建名为ModelService.js
的文件:
module.exports = {
invalidStructure(schema, input) {
try {
if (schema.type === 'array') {
// Invalid: if input is not array
// OR some of input[items] doesn't match schema.item
return !_.isArray(input) ||
_.some(input, item => this.invalidStructure(schema.item, item));
}
else if (schema.type === 'object') {
// Invalid if input is not an object
// OR if input.keys doesn't match schema.struct.keys
// OR if typeof input[key] doesn't match schema.struct[key]
return !_.isObjectLike(input) ||
!_.isEqual(_.keys(schema.struct), _.keys(input)) ||
_.some(_.keys(input), key => this.invalidStructure(schema.struct[key], input[key]));
}
else { // verifying field value vs schema.type
// TODO: Add other field validations here (i.e. isEmail, required,...etc.)
return typeof input !== schema.type;
}
}
catch (err) {
sails.log.error('Exception in [invalidStructure] : ', err);
return true;
}
}
}
并在您的模型中这样使用:
const address = {
type: 'object',
struct: {
name: { type: 'string' },
location: {
type: 'object',
struct: {
x: { type: 'string' },
y: { type: 'string' },
z: { type: 'string' },
}
}
}
}
module.exports = {
attributes: {
address: {
type: 'json',
custom: value => !ModelService.invalidStructure(address, value)
}
}
}
现在我知道这不适用于任何情况(即必需:false
)
但它应该可以让您使用匹配的json
结构和值类型
注意:这是最重要的。请随意使用或增强PR我想使用验证规则,如
waterlineSchema:true
来使用所有支持的类型和来自sails/waterline的验证。有什么提示吗?图书馆?