Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
张重言
rails
提交
e86524c0
R
rails
项目概览
张重言
/
rails
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
R
rails
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
e86524c0
编写于
11月 08, 2016
作者:
X
Xavier Noria
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
adds support for arbitrary hashes in strong parameters
上级
a5e93341
变更
4
隐藏空白更改
内联
并排
Showing
4 changed file
with
101 addition
and
3 deletion
+101
-3
actionpack/CHANGELOG.md
actionpack/CHANGELOG.md
+8
-0
actionpack/lib/action_controller/metal/strong_parameters.rb
actionpack/lib/action_controller/metal/strong_parameters.rb
+45
-0
actionpack/test/controller/parameters/parameters_permit_test.rb
...pack/test/controller/parameters/parameters_permit_test.rb
+33
-0
guides/source/action_controller_overview.md
guides/source/action_controller_overview.md
+15
-3
未找到文件。
actionpack/CHANGELOG.md
浏览文件 @
e86524c0
*
Add support for arbitrary hashes in strong parameters:
```ruby
params.permit(preferences: {})
```
*Xavier Noria*
*
Add
`ActionController::Parameters#merge!`
, which behaves the same as
`Hash#merge!`
.
*
Add
`ActionController::Parameters#merge!`
, which behaves the same as
`Hash#merge!`
.
*Yuji Yaginuma*
*Yuji Yaginuma*
...
...
actionpack/lib/action_controller/metal/strong_parameters.rb
浏览文件 @
e86524c0
...
@@ -334,6 +334,15 @@ def require(key)
...
@@ -334,6 +334,15 @@ def require(key)
# params = ActionController::Parameters.new(tags: ['rails', 'parameters'])
# params = ActionController::Parameters.new(tags: ['rails', 'parameters'])
# params.permit(tags: [])
# params.permit(tags: [])
#
#
# Sometimes it is not possible or convenient to declare the valid keys of
# a hash parameter or its internal structure. Just map to an empty hash:
#
# params.permit(preferences: {})
#
# but be careful because this opens the door to arbitrary input. In this
# case, +permit+ ensures values in the returned structure are permitted
# scalars and filters out anything else.
#
# You can also use +permit+ on nested parameters, like:
# You can also use +permit+ on nested parameters, like:
#
#
# params = ActionController::Parameters.new({
# params = ActionController::Parameters.new({
...
@@ -766,6 +775,7 @@ def non_scalar?(value)
...
@@ -766,6 +775,7 @@ def non_scalar?(value)
end
end
EMPTY_ARRAY
=
[]
EMPTY_ARRAY
=
[]
EMPTY_HASH
=
{}
def
hash_filter
(
params
,
filter
)
def
hash_filter
(
params
,
filter
)
filter
=
filter
.
with_indifferent_access
filter
=
filter
.
with_indifferent_access
...
@@ -779,6 +789,11 @@ def hash_filter(params, filter)
...
@@ -779,6 +789,11 @@ def hash_filter(params, filter)
array_of_permitted_scalars?
(
self
[
key
])
do
|
val
|
array_of_permitted_scalars?
(
self
[
key
])
do
|
val
|
params
[
key
]
=
val
params
[
key
]
=
val
end
end
elsif
filter
[
key
]
==
EMPTY_HASH
# Declaration { preferences: {} }
if
value
.
is_a?
(
Parameters
)
params
[
key
]
=
permit_any_in_parameters
(
value
)
end
elsif
non_scalar?
(
value
)
elsif
non_scalar?
(
value
)
# Declaration { user: :name } or { user: [:name, :age, { address: ... }] }.
# Declaration { user: :name } or { user: [:name, :age, { address: ... }] }.
params
[
key
]
=
each_element
(
value
)
do
|
element
|
params
[
key
]
=
each_element
(
value
)
do
|
element
|
...
@@ -788,6 +803,36 @@ def hash_filter(params, filter)
...
@@ -788,6 +803,36 @@ def hash_filter(params, filter)
end
end
end
end
def
permit_any_in_parameters
(
params
)
self
.
class
.
new
.
tap
do
|
sanitized
|
params
.
each
do
|
key
,
value
|
if
permitted_scalar?
(
value
)
sanitized
[
key
]
=
value
elsif
value
.
is_a?
(
Array
)
sanitized
[
key
]
=
permit_any_in_array
(
value
)
elsif
value
.
is_a?
(
Parameters
)
sanitized
[
key
]
=
permit_any_in_parameters
(
value
)
else
# Filter this one out.
end
end
end
end
def
permit_any_in_array
(
array
)
[].
tap
do
|
sanitized
|
array
.
each
do
|
element
|
if
permitted_scalar?
(
element
)
sanitized
<<
element
elsif
element
.
is_a?
(
Parameters
)
sanitized
<<
permit_any_in_parameters
(
element
)
else
# Filter this one out.
end
end
end
end
def
initialize_copy
(
source
)
def
initialize_copy
(
source
)
super
super
@parameters
=
@parameters
.
dup
@parameters
=
@parameters
.
dup
...
...
actionpack/test/controller/parameters/parameters_permit_test.rb
浏览文件 @
e86524c0
...
@@ -168,6 +168,39 @@ def walk_permitted(params)
...
@@ -168,6 +168,39 @@ def walk_permitted(params)
end
end
end
end
test
"key to empty hash: arbitrary hashes are permitted"
do
params
=
ActionController
::
Parameters
.
new
(
username:
"fxn"
,
preferences:
{
scheme:
"Marazul"
,
font:
{
name:
"Source Code Pro"
,
size:
12
},
tabstops:
[
4
,
8
,
12
,
16
],
suspicious:
[
true
,
Object
.
new
,
false
,
/yo!/
],
dubious:
[{
a: :a
,
b:
/wtf!/
},
{
c: :c
}],
injected:
Object
.
new
},
hacked:
1
# not a hash
)
permitted
=
params
.
permit
(
:username
,
preferences:
{},
hacked:
{})
assert_equal
"fxn"
,
permitted
[
:username
]
assert_equal
"Marazul"
,
permitted
[
:preferences
][
:scheme
]
assert_equal
"Source Code Pro"
,
permitted
[
:preferences
][
:font
][
:name
]
assert_equal
12
,
permitted
[
:preferences
][
:font
][
:size
]
assert_equal
[
4
,
8
,
12
,
16
],
permitted
[
:preferences
][
:tabstops
]
assert_equal
[
true
,
false
],
permitted
[
:preferences
][
:suspicious
]
assert_equal
:a
,
permitted
[
:preferences
][
:dubious
][
0
][
:a
]
assert_equal
:c
,
permitted
[
:preferences
][
:dubious
][
1
][
:c
]
assert_filtered_out
permitted
[
:preferences
][
:dubious
][
0
],
:b
assert_filtered_out
permitted
[
:preferences
],
:injected
assert_filtered_out
permitted
,
:hacked
end
test
"fetch raises ParameterMissing exception"
do
test
"fetch raises ParameterMissing exception"
do
e
=
assert_raises
(
ActionController
::
ParameterMissing
)
do
e
=
assert_raises
(
ActionController
::
ParameterMissing
)
do
@params
.
fetch
:foo
@params
.
fetch
:foo
...
...
guides/source/action_controller_overview.md
浏览文件 @
e86524c0
...
@@ -258,6 +258,17 @@ scalar values, map the key to an empty array:
...
@@ -258,6 +258,17 @@ scalar values, map the key to an empty array:
params
.
permit
(
id:
[])
params
.
permit
(
id:
[])
```
```
Sometimes it is not possible or convenient to declare the valid keys of
a hash parameter or its internal structure. Just map to an empty hash:
```
ruby
params
.
permit
(
preferences:
{})
```
but be careful because this opens the door to arbitrary input. In this
case,
`permit`
ensures values in the returned structure are permitted
scalars and filters out anything else.
To whitelist an entire hash of parameters, the
`permit!`
method can be
To whitelist an entire hash of parameters, the
`permit!`
method can be
used:
used:
...
@@ -265,9 +276,10 @@ used:
...
@@ -265,9 +276,10 @@ used:
params
.
require
(
:log_entry
).
permit!
params
.
require
(
:log_entry
).
permit!
```
```
This will mark the
`:log_entry`
parameters hash and any sub-hash of it as
This marks the
`:log_entry`
parameters hash and any sub-hash of it as
permitted. Extreme care should be taken when using
`permit!`
, as it
permitted and does not check for permitted scalars, anything is accepted.
will allow all current and future model attributes to be mass-assigned.
Extreme care should be taken when using
`permit!`
, as it will allow all current
and future model attributes to be mass-assigned.
#### Nested Parameters
#### Nested Parameters
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录