如何验证此哈希参数? [英] How to validate this hash parameter?
问题描述
如何为此散列参数编写正确的params
验证:
How do I write the correct params
validations for this hash parameter:
{
"files": {
"main.c": {
"contents": "#include <stdio.h> ...",
"foo": "bar"
},
"main.h": {
"contents": "#define BLAH ...",
"foo": "baz"
},
... more files here ...
}
}
files
是我要验证的哈希参数. files
的每个键都可以是任何内容(字符串);这些值是具有特定格式的哈希,该哈希也需要进行验证(需要contents
和foo
).我正在使用葡萄0.9.0.
files
is the hash parameter that I want to validate. Each key of files
can be anything (a string); the values are hashes with a specific format that also needs to be validated (requires contents
and foo
). I'm using grape 0.9.0.
这就是我想要的:
params do
optional :files, type: Hash do
requires <any key>, type: Hash do
requires :contents, type: String
requires :foo, type: String
end
end
end
我已经阅读了文档,但我看不到如何实现这种验证.可能吗?我需要写一个自定义验证器吗?
I've read the documentation but I couldn't see how to achieve this kind of validation. Is it even possible? Do I need to write a custom validator?
一种替代方法是使用它:
An alternative is to have this instead:
{
"files":
[
{
"name": "main.c",
"contents": "#include <stdio.h> ...",
"foo": "bar"
},
{
"name": "main.h",
"contents": "#define BLAH ...",
"foo": "baz"
}
]
}
可以很容易地像这样验证:
which can be easily validated like this:
params do
optional :files, type: Array do
requires :name, type: String
requires :contents, type: String
requires :foo, type: String
end
end
但是现在我失去了拥有唯一文件名的能力.
but now I lose the ability to have unique file names.
推荐答案
基于葡萄文档我会想到编写您自己的自定义验证器并选择第二种方法的想法.
Based on the grape documentation I would come up with the idea of writing your own custom validator and go with your second alternative.
class UniqueHashAttributes < Grape::Validations::Base
def validate_param!(attr_name, params)
# assuming @option is an array
@option.each do |attribute|
# detects if the value of the attribute is found more than once
if params[attr_name].group_by { |h| h[attribute] }.values.collect(&:size).max > 1
fail Grape::Exceptions::Validation, params: [@scope.full_name(attr_name)],
message: "must have only unique values for properties: '#{@option.join(', ')}'"
end
end
end
end
还可以报告表示唯一性违规的自定义错误.当然,除了唯一性之外,该原理还可以用于执行不同类型的验证.
It would also be possible to report custom errors that present the uniqueness violations. Of course this principle can also be applied to perform different kind of validations than the uniqueness.
如果此验证器已加载到您的应用程序中,则可以在路由的params
定义中使用它,如下所示:
If this validator is loaded in your application, you can utilize it in your params
definition of the route as follows:
params do
optional :files, unique_hash_attributes: [:name], type: Array do
requires :name, type: String
requires :contents, type: String
requires :foo, type: String
end
end
post '/validation' do
'passed'
end
通过此实现,您还可以通过将:foo
字段(或任何其他字段)添加到唯一的哈希属性数组中来将其指定为唯一.
With this implementation you could also specify the :foo
field (or any other) to be unique by adding it to the array of the unique hash attributes.
对哈希值(名称,内容,foo)的任何验证在files
验证器中保持不变,并且仍然适用.
Any validations of the Hash's values (name, contents, foo) remain unchanged of the files
validator and still apply.
具有以下数据的邮寄请求将无法通过验证:
A post request with the following data would not pass the verification:
{ "files":
[
{
"name": "main.c",
"contents": "#include <stdio.h> ...",
"foo": "bar"
},
{
"name": "main.c",
"contents": "#define BLAH ...",
"foo": "baz"
}
]
}
这篇关于如何验证此哈希参数?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!