durable_parameters 0.2.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/MIT-LICENSE +20 -0
- data/README.md +853 -0
- data/Rakefile +29 -0
- data/app/params/account_params.rb.example +38 -0
- data/app/params/application_params.rb +16 -0
- data/lib/durable_parameters/adapters/hanami.rb +138 -0
- data/lib/durable_parameters/adapters/rage.rb +124 -0
- data/lib/durable_parameters/adapters/rails.rb +280 -0
- data/lib/durable_parameters/adapters/sinatra.rb +91 -0
- data/lib/durable_parameters/core/application_params.rb +334 -0
- data/lib/durable_parameters/core/configuration.rb +83 -0
- data/lib/durable_parameters/core/forbidden_attributes_protection.rb +48 -0
- data/lib/durable_parameters/core/parameters.rb +643 -0
- data/lib/durable_parameters/core/params_registry.rb +110 -0
- data/lib/durable_parameters/core.rb +15 -0
- data/lib/durable_parameters/log_subscriber.rb +34 -0
- data/lib/durable_parameters/railtie.rb +65 -0
- data/lib/durable_parameters/version.rb +7 -0
- data/lib/durable_parameters.rb +41 -0
- data/lib/generators/rails/USAGE +12 -0
- data/lib/generators/rails/durable_parameters_controller_generator.rb +17 -0
- data/lib/generators/rails/templates/controller.rb +94 -0
- data/lib/legacy/action_controller/application_params.rb +235 -0
- data/lib/legacy/action_controller/parameters.rb +524 -0
- data/lib/legacy/action_controller/params_registry.rb +108 -0
- data/lib/legacy/active_model/forbidden_attributes_protection.rb +40 -0
- data/test/action_controller_required_params_test.rb +36 -0
- data/test/action_controller_tainted_params_test.rb +29 -0
- data/test/active_model_mass_assignment_taint_protection_test.rb +25 -0
- data/test/application_params_array_test.rb +245 -0
- data/test/application_params_edge_cases_test.rb +361 -0
- data/test/application_params_test.rb +893 -0
- data/test/controller_generator_test.rb +31 -0
- data/test/core_parameters_test.rb +2376 -0
- data/test/durable_parameters_test.rb +115 -0
- data/test/enhanced_error_messages_test.rb +120 -0
- data/test/gemfiles/Gemfile.rails-3.0.x +14 -0
- data/test/gemfiles/Gemfile.rails-3.1.x +14 -0
- data/test/gemfiles/Gemfile.rails-3.2.x +14 -0
- data/test/log_on_unpermitted_params_test.rb +49 -0
- data/test/metadata_validation_test.rb +294 -0
- data/test/multi_parameter_attributes_test.rb +38 -0
- data/test/parameters_core_methods_test.rb +503 -0
- data/test/parameters_integration_test.rb +553 -0
- data/test/parameters_permit_test.rb +491 -0
- data/test/parameters_require_test.rb +9 -0
- data/test/parameters_taint_test.rb +98 -0
- data/test/params_registry_concurrency_test.rb +422 -0
- data/test/params_registry_test.rb +112 -0
- data/test/permit_by_model_test.rb +227 -0
- data/test/raise_on_unpermitted_params_test.rb +32 -0
- data/test/test_helper.rb +38 -0
- data/test/transform_params_edge_cases_test.rb +526 -0
- data/test/transformation_test.rb +360 -0
- metadata +223 -0
|
@@ -0,0 +1,553 @@
|
|
|
1
|
+
require 'test_helper'
|
|
2
|
+
|
|
3
|
+
class ParametersIntegrationTest < Minitest::Test
|
|
4
|
+
def setup
|
|
5
|
+
ActionController::ParamsRegistry.clear!
|
|
6
|
+
end
|
|
7
|
+
|
|
8
|
+
def teardown
|
|
9
|
+
ActionController::ParamsRegistry.clear!
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
# Test complete workflow: define params class, register, use
|
|
13
|
+
def test_complete_workflow
|
|
14
|
+
# Step 1: Define params class
|
|
15
|
+
user_params = Class.new(ActionController::ApplicationParams) do
|
|
16
|
+
def self.name
|
|
17
|
+
'UserParams'
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
allow :first_name
|
|
21
|
+
allow :last_name
|
|
22
|
+
allow :email
|
|
23
|
+
allow :role, only: :create
|
|
24
|
+
deny :password_digest
|
|
25
|
+
metadata :ip_address
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
# Step 2: Register it
|
|
29
|
+
ActionController::ParamsRegistry.register('User', user_params)
|
|
30
|
+
|
|
31
|
+
# Step 3: Use it
|
|
32
|
+
params = ActionController::Parameters.new(
|
|
33
|
+
user: {
|
|
34
|
+
first_name: 'John',
|
|
35
|
+
last_name: 'Doe',
|
|
36
|
+
email: 'john@example.com',
|
|
37
|
+
role: 'admin',
|
|
38
|
+
password_digest: 'secret_hash'
|
|
39
|
+
}
|
|
40
|
+
)
|
|
41
|
+
|
|
42
|
+
permitted = params.require(:user).transform_params(
|
|
43
|
+
action: :create,
|
|
44
|
+
current_user: Object.new,
|
|
45
|
+
ip_address: '127.0.0.1'
|
|
46
|
+
)
|
|
47
|
+
|
|
48
|
+
assert_equal 'John', permitted[:first_name]
|
|
49
|
+
assert_equal 'Doe', permitted[:last_name]
|
|
50
|
+
assert_equal 'john@example.com', permitted[:email]
|
|
51
|
+
assert_equal 'admin', permitted[:role]
|
|
52
|
+
assert_nil permitted[:password_digest]
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
# Test multiple models in same request
|
|
56
|
+
def test_multiple_models_in_same_request
|
|
57
|
+
user_params = Class.new(ActionController::ApplicationParams) do
|
|
58
|
+
def self.name
|
|
59
|
+
'UserParams'
|
|
60
|
+
end
|
|
61
|
+
allow :name
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
account_params = Class.new(ActionController::ApplicationParams) do
|
|
65
|
+
def self.name
|
|
66
|
+
'AccountParams'
|
|
67
|
+
end
|
|
68
|
+
allow :title
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
ActionController::ParamsRegistry.register('User', user_params)
|
|
72
|
+
ActionController::ParamsRegistry.register('Account', account_params)
|
|
73
|
+
|
|
74
|
+
params = ActionController::Parameters.new(
|
|
75
|
+
user: { name: 'John' },
|
|
76
|
+
account: { title: 'My Account' }
|
|
77
|
+
)
|
|
78
|
+
|
|
79
|
+
user_permitted = params.require(:user).transform_params()
|
|
80
|
+
account_permitted = params.require(:account).transform_params()
|
|
81
|
+
|
|
82
|
+
assert_equal 'John', user_permitted[:name]
|
|
83
|
+
assert_equal 'My Account', account_permitted[:title]
|
|
84
|
+
end
|
|
85
|
+
|
|
86
|
+
# Test combining permit and transform_params
|
|
87
|
+
def test_combining_permit_and_transform_params
|
|
88
|
+
user_params = Class.new(ActionController::ApplicationParams) do
|
|
89
|
+
def self.name
|
|
90
|
+
'UserParams'
|
|
91
|
+
end
|
|
92
|
+
allow :name
|
|
93
|
+
allow :email
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
ActionController::ParamsRegistry.register('User', user_params)
|
|
97
|
+
|
|
98
|
+
params = ActionController::Parameters.new(
|
|
99
|
+
user: { name: 'John', email: 'john@example.com' },
|
|
100
|
+
extra: 'value'
|
|
101
|
+
)
|
|
102
|
+
|
|
103
|
+
# First permit top-level
|
|
104
|
+
top_level = params.permit(:extra)
|
|
105
|
+
assert_equal 'value', top_level[:extra]
|
|
106
|
+
|
|
107
|
+
# Then transform nested
|
|
108
|
+
user_permitted = params.require(:user).transform_params()
|
|
109
|
+
assert_equal 'John', user_permitted[:name]
|
|
110
|
+
assert_equal 'john@example.com', user_permitted[:email]
|
|
111
|
+
end
|
|
112
|
+
|
|
113
|
+
# Test params class with complex action filters
|
|
114
|
+
def test_complex_action_filtering_scenarios
|
|
115
|
+
params_class = Class.new(ActionController::ApplicationParams) do
|
|
116
|
+
def self.name
|
|
117
|
+
'ComplexParams'
|
|
118
|
+
end
|
|
119
|
+
|
|
120
|
+
# Always allowed
|
|
121
|
+
allow :id
|
|
122
|
+
allow :name
|
|
123
|
+
|
|
124
|
+
# Only on create
|
|
125
|
+
allow :created_by, only: :create
|
|
126
|
+
|
|
127
|
+
# Only on create and update
|
|
128
|
+
allow :status, only: [:create, :update]
|
|
129
|
+
|
|
130
|
+
# Never on destroy
|
|
131
|
+
allow :notes, except: :destroy
|
|
132
|
+
|
|
133
|
+
# Never on destroy or delete
|
|
134
|
+
allow :metadata, except: [:destroy, :delete]
|
|
135
|
+
end
|
|
136
|
+
|
|
137
|
+
ActionController::ParamsRegistry.register('Complex', params_class)
|
|
138
|
+
|
|
139
|
+
# Test create action
|
|
140
|
+
create_params = ActionController::Parameters.new(
|
|
141
|
+
complex: {
|
|
142
|
+
id: 1,
|
|
143
|
+
name: 'Test',
|
|
144
|
+
created_by: 'admin',
|
|
145
|
+
status: 'active',
|
|
146
|
+
notes: 'Some notes',
|
|
147
|
+
metadata: { key: 'value' }
|
|
148
|
+
}
|
|
149
|
+
)
|
|
150
|
+
create_permitted = create_params.require(:complex).transform_params(action: :create)
|
|
151
|
+
assert_equal 1, create_permitted[:id]
|
|
152
|
+
assert_equal 'Test', create_permitted[:name]
|
|
153
|
+
assert_equal 'admin', create_permitted[:created_by]
|
|
154
|
+
assert_equal 'active', create_permitted[:status]
|
|
155
|
+
assert_equal 'Some notes', create_permitted[:notes]
|
|
156
|
+
|
|
157
|
+
# Test update action
|
|
158
|
+
update_params = ActionController::Parameters.new(
|
|
159
|
+
complex: {
|
|
160
|
+
id: 1,
|
|
161
|
+
name: 'Test',
|
|
162
|
+
created_by: 'admin',
|
|
163
|
+
status: 'active',
|
|
164
|
+
notes: 'Some notes',
|
|
165
|
+
metadata: { key: 'value' }
|
|
166
|
+
}
|
|
167
|
+
)
|
|
168
|
+
update_permitted = update_params.require(:complex).transform_params(action: :update)
|
|
169
|
+
assert_equal 1, update_permitted[:id]
|
|
170
|
+
assert_equal 'Test', update_permitted[:name]
|
|
171
|
+
assert_nil update_permitted[:created_by] # only on create
|
|
172
|
+
assert_equal 'active', update_permitted[:status]
|
|
173
|
+
assert_equal 'Some notes', update_permitted[:notes]
|
|
174
|
+
|
|
175
|
+
# Test destroy action
|
|
176
|
+
destroy_params = ActionController::Parameters.new(
|
|
177
|
+
complex: {
|
|
178
|
+
id: 1,
|
|
179
|
+
name: 'Test',
|
|
180
|
+
created_by: 'admin',
|
|
181
|
+
status: 'active',
|
|
182
|
+
notes: 'Some notes',
|
|
183
|
+
metadata: { key: 'value' }
|
|
184
|
+
}
|
|
185
|
+
)
|
|
186
|
+
destroy_permitted = destroy_params.require(:complex).transform_params(action: :destroy)
|
|
187
|
+
assert_equal 1, destroy_permitted[:id]
|
|
188
|
+
assert_equal 'Test', destroy_permitted[:name]
|
|
189
|
+
assert_nil destroy_permitted[:created_by]
|
|
190
|
+
assert_nil destroy_permitted[:status]
|
|
191
|
+
assert_nil destroy_permitted[:notes] # except destroy
|
|
192
|
+
assert_nil destroy_permitted[:metadata] # except destroy
|
|
193
|
+
|
|
194
|
+
# Test show action
|
|
195
|
+
show_params = ActionController::Parameters.new(
|
|
196
|
+
complex: {
|
|
197
|
+
id: 1,
|
|
198
|
+
name: 'Test',
|
|
199
|
+
created_by: 'admin',
|
|
200
|
+
status: 'active',
|
|
201
|
+
notes: 'Some notes',
|
|
202
|
+
metadata: { key: 'value' }
|
|
203
|
+
}
|
|
204
|
+
)
|
|
205
|
+
show_permitted = show_params.require(:complex).transform_params(action: :show)
|
|
206
|
+
assert_equal 1, show_permitted[:id]
|
|
207
|
+
assert_equal 'Test', show_permitted[:name]
|
|
208
|
+
assert_nil show_permitted[:created_by]
|
|
209
|
+
assert_nil show_permitted[:status]
|
|
210
|
+
assert_equal 'Some notes', show_permitted[:notes]
|
|
211
|
+
end
|
|
212
|
+
|
|
213
|
+
# Test inheritance chain in real usage
|
|
214
|
+
def test_inheritance_chain_in_usage
|
|
215
|
+
base_params = Class.new(ActionController::ApplicationParams) do
|
|
216
|
+
def self.name
|
|
217
|
+
'BaseParams'
|
|
218
|
+
end
|
|
219
|
+
allow :id
|
|
220
|
+
allow :created_at
|
|
221
|
+
end
|
|
222
|
+
|
|
223
|
+
user_params = Class.new(base_params) do
|
|
224
|
+
def self.name
|
|
225
|
+
'UserParams'
|
|
226
|
+
end
|
|
227
|
+
allow :name
|
|
228
|
+
allow :email
|
|
229
|
+
deny :created_at # Override parent
|
|
230
|
+
end
|
|
231
|
+
|
|
232
|
+
admin_params = Class.new(user_params) do
|
|
233
|
+
def self.name
|
|
234
|
+
'AdminParams'
|
|
235
|
+
end
|
|
236
|
+
allow :role
|
|
237
|
+
allow :permissions, array: true
|
|
238
|
+
end
|
|
239
|
+
|
|
240
|
+
ActionController::ParamsRegistry.register('Admin', admin_params)
|
|
241
|
+
|
|
242
|
+
params = ActionController::Parameters.new(
|
|
243
|
+
admin: {
|
|
244
|
+
id: 1,
|
|
245
|
+
name: 'Admin User',
|
|
246
|
+
email: 'admin@example.com',
|
|
247
|
+
role: 'super_admin',
|
|
248
|
+
permissions: ['all'],
|
|
249
|
+
created_at: Time.now
|
|
250
|
+
}
|
|
251
|
+
)
|
|
252
|
+
|
|
253
|
+
permitted = params.require(:admin).transform_params()
|
|
254
|
+
|
|
255
|
+
assert_equal 1, permitted[:id]
|
|
256
|
+
assert_equal 'Admin User', permitted[:name]
|
|
257
|
+
assert_equal 'admin@example.com', permitted[:email]
|
|
258
|
+
assert_equal 'super_admin', permitted[:role]
|
|
259
|
+
assert_equal ['all'], permitted[:permissions]
|
|
260
|
+
assert_nil permitted[:created_at] # denied in child
|
|
261
|
+
end
|
|
262
|
+
|
|
263
|
+
# Test dynamic additional_attrs based on conditions
|
|
264
|
+
def test_dynamic_additional_attrs
|
|
265
|
+
user_params = Class.new(ActionController::ApplicationParams) do
|
|
266
|
+
def self.name
|
|
267
|
+
'UserParams'
|
|
268
|
+
end
|
|
269
|
+
allow :name
|
|
270
|
+
allow :email
|
|
271
|
+
end
|
|
272
|
+
|
|
273
|
+
ActionController::ParamsRegistry.register('User', user_params)
|
|
274
|
+
|
|
275
|
+
# Simulate allowing different fields based on user role
|
|
276
|
+
is_admin = true
|
|
277
|
+
additional = is_admin ? [:role, :status] : []
|
|
278
|
+
|
|
279
|
+
params = ActionController::Parameters.new(
|
|
280
|
+
user: {
|
|
281
|
+
name: 'Test',
|
|
282
|
+
email: 'test@example.com',
|
|
283
|
+
role: 'admin',
|
|
284
|
+
status: 'active'
|
|
285
|
+
}
|
|
286
|
+
)
|
|
287
|
+
|
|
288
|
+
permitted = params.require(:user).transform_params(
|
|
289
|
+
additional_attrs: additional
|
|
290
|
+
)
|
|
291
|
+
|
|
292
|
+
assert_equal 'Test', permitted[:name]
|
|
293
|
+
assert_equal 'test@example.com', permitted[:email]
|
|
294
|
+
assert_equal 'admin', permitted[:role]
|
|
295
|
+
assert_equal 'active', permitted[:status]
|
|
296
|
+
end
|
|
297
|
+
|
|
298
|
+
# Test registry lookup with different naming conventions
|
|
299
|
+
def test_registry_with_different_naming_conventions
|
|
300
|
+
params_class = Class.new(ActionController::ApplicationParams) do
|
|
301
|
+
def self.name
|
|
302
|
+
'UserAccountParams'
|
|
303
|
+
end
|
|
304
|
+
allow :field
|
|
305
|
+
end
|
|
306
|
+
|
|
307
|
+
# Test various registration keys
|
|
308
|
+
ActionController::ParamsRegistry.register('UserAccount', params_class)
|
|
309
|
+
|
|
310
|
+
params1 = ActionController::Parameters.new(
|
|
311
|
+
user_account: { field: 'value1' }
|
|
312
|
+
)
|
|
313
|
+
permitted1 = params1.require(:user_account).transform_params()
|
|
314
|
+
assert_equal 'value1', permitted1[:field]
|
|
315
|
+
|
|
316
|
+
# Clear and try with different registration
|
|
317
|
+
ActionController::ParamsRegistry.clear!
|
|
318
|
+
ActionController::ParamsRegistry.register('user_account', params_class)
|
|
319
|
+
|
|
320
|
+
params2 = ActionController::Parameters.new(
|
|
321
|
+
user_account: { field: 'value2' }
|
|
322
|
+
)
|
|
323
|
+
permitted2 = params2.require(:user_account).transform_params()
|
|
324
|
+
assert_equal 'value2', permitted2[:field]
|
|
325
|
+
end
|
|
326
|
+
|
|
327
|
+
# Test backward compatibility with permit_by_model
|
|
328
|
+
def test_backward_compatibility_permit_by_model
|
|
329
|
+
user_params = Class.new(ActionController::ApplicationParams) do
|
|
330
|
+
def self.name
|
|
331
|
+
'UserParams'
|
|
332
|
+
end
|
|
333
|
+
allow :name
|
|
334
|
+
allow :email
|
|
335
|
+
allow :status, only: :create
|
|
336
|
+
end
|
|
337
|
+
|
|
338
|
+
ActionController::ParamsRegistry.register('User', user_params)
|
|
339
|
+
|
|
340
|
+
params = ActionController::Parameters.new(
|
|
341
|
+
name: 'John',
|
|
342
|
+
email: 'john@example.com',
|
|
343
|
+
status: 'active',
|
|
344
|
+
admin: true
|
|
345
|
+
)
|
|
346
|
+
|
|
347
|
+
# Old API
|
|
348
|
+
permitted = params.permit_by_model(:user, action: :create)
|
|
349
|
+
|
|
350
|
+
assert_equal 'John', permitted[:name]
|
|
351
|
+
assert_equal 'john@example.com', permitted[:email]
|
|
352
|
+
assert_equal 'active', permitted[:status]
|
|
353
|
+
assert_nil permitted[:admin]
|
|
354
|
+
end
|
|
355
|
+
|
|
356
|
+
# Test chaining with slice
|
|
357
|
+
def test_chaining_with_slice
|
|
358
|
+
user_params = Class.new(ActionController::ApplicationParams) do
|
|
359
|
+
def self.name
|
|
360
|
+
'UserParams'
|
|
361
|
+
end
|
|
362
|
+
allow :name
|
|
363
|
+
allow :email
|
|
364
|
+
end
|
|
365
|
+
|
|
366
|
+
ActionController::ParamsRegistry.register('User', user_params)
|
|
367
|
+
|
|
368
|
+
params = ActionController::Parameters.new(
|
|
369
|
+
user: {
|
|
370
|
+
name: 'John',
|
|
371
|
+
email: 'john@example.com',
|
|
372
|
+
age: 30
|
|
373
|
+
}
|
|
374
|
+
)
|
|
375
|
+
|
|
376
|
+
# Slice then transform
|
|
377
|
+
sliced = params.require(:user).slice(:name, :email, :age)
|
|
378
|
+
permitted = sliced.transform_params()
|
|
379
|
+
|
|
380
|
+
assert_equal 'John', permitted[:name]
|
|
381
|
+
assert_equal 'john@example.com', permitted[:email]
|
|
382
|
+
assert_nil permitted[:age] # not allowed
|
|
383
|
+
end
|
|
384
|
+
|
|
385
|
+
# Test with dup
|
|
386
|
+
def test_transform_params_with_dup
|
|
387
|
+
user_params = Class.new(ActionController::ApplicationParams) do
|
|
388
|
+
def self.name
|
|
389
|
+
'UserParams'
|
|
390
|
+
end
|
|
391
|
+
allow :name
|
|
392
|
+
end
|
|
393
|
+
|
|
394
|
+
ActionController::ParamsRegistry.register('User', user_params)
|
|
395
|
+
|
|
396
|
+
params = ActionController::Parameters.new(
|
|
397
|
+
user: { name: 'John' }
|
|
398
|
+
)
|
|
399
|
+
|
|
400
|
+
user_params = params.require(:user)
|
|
401
|
+
duped = user_params.dup
|
|
402
|
+
|
|
403
|
+
# Both should work
|
|
404
|
+
permitted1 = user_params.transform_params()
|
|
405
|
+
permitted2 = duped.transform_params()
|
|
406
|
+
|
|
407
|
+
assert_equal 'John', permitted1[:name]
|
|
408
|
+
assert_equal 'John', permitted2[:name]
|
|
409
|
+
end
|
|
410
|
+
|
|
411
|
+
# Test multiple registrations for same model (last wins)
|
|
412
|
+
def test_multiple_registrations_last_wins
|
|
413
|
+
first_params = Class.new(ActionController::ApplicationParams) do
|
|
414
|
+
def self.name
|
|
415
|
+
'FirstParams'
|
|
416
|
+
end
|
|
417
|
+
allow :field1
|
|
418
|
+
end
|
|
419
|
+
|
|
420
|
+
second_params = Class.new(ActionController::ApplicationParams) do
|
|
421
|
+
def self.name
|
|
422
|
+
'SecondParams'
|
|
423
|
+
end
|
|
424
|
+
allow :field2
|
|
425
|
+
end
|
|
426
|
+
|
|
427
|
+
ActionController::ParamsRegistry.register('Test', first_params)
|
|
428
|
+
ActionController::ParamsRegistry.register('Test', second_params)
|
|
429
|
+
|
|
430
|
+
params = ActionController::Parameters.new(
|
|
431
|
+
test: {
|
|
432
|
+
field1: 'value1',
|
|
433
|
+
field2: 'value2'
|
|
434
|
+
}
|
|
435
|
+
)
|
|
436
|
+
|
|
437
|
+
permitted = params.require(:test).transform_params()
|
|
438
|
+
|
|
439
|
+
# Should use second registration
|
|
440
|
+
assert_nil permitted[:field1]
|
|
441
|
+
assert_equal 'value2', permitted[:field2]
|
|
442
|
+
end
|
|
443
|
+
|
|
444
|
+
# Test metadata in inheritance
|
|
445
|
+
def test_metadata_in_inheritance_chain
|
|
446
|
+
parent_params = Class.new(ActionController::ApplicationParams) do
|
|
447
|
+
def self.name
|
|
448
|
+
'ParentParams'
|
|
449
|
+
end
|
|
450
|
+
allow :name
|
|
451
|
+
metadata :parent_meta
|
|
452
|
+
end
|
|
453
|
+
|
|
454
|
+
child_params = Class.new(parent_params) do
|
|
455
|
+
def self.name
|
|
456
|
+
'ChildParams'
|
|
457
|
+
end
|
|
458
|
+
allow :email
|
|
459
|
+
metadata :child_meta
|
|
460
|
+
end
|
|
461
|
+
|
|
462
|
+
ActionController::ParamsRegistry.register('Child', child_params)
|
|
463
|
+
|
|
464
|
+
params = ActionController::Parameters.new(
|
|
465
|
+
child: {
|
|
466
|
+
name: 'Test',
|
|
467
|
+
email: 'test@example.com'
|
|
468
|
+
}
|
|
469
|
+
)
|
|
470
|
+
|
|
471
|
+
# Should accept both parent and child metadata
|
|
472
|
+
permitted = params.require(:child).transform_params(
|
|
473
|
+
parent_meta: 'parent_value',
|
|
474
|
+
child_meta: 'child_value',
|
|
475
|
+
current_user: Object.new
|
|
476
|
+
)
|
|
477
|
+
|
|
478
|
+
assert_equal 'Test', permitted[:name]
|
|
479
|
+
assert_equal 'test@example.com', permitted[:email]
|
|
480
|
+
end
|
|
481
|
+
|
|
482
|
+
# Test flags don't affect filtering
|
|
483
|
+
def test_flags_dont_affect_filtering
|
|
484
|
+
params_class = Class.new(ActionController::ApplicationParams) do
|
|
485
|
+
def self.name
|
|
486
|
+
'FlaggedParams'
|
|
487
|
+
end
|
|
488
|
+
allow :name
|
|
489
|
+
flag :some_flag, true
|
|
490
|
+
flag :another_flag, 'value'
|
|
491
|
+
end
|
|
492
|
+
|
|
493
|
+
ActionController::ParamsRegistry.register('Flagged', params_class)
|
|
494
|
+
|
|
495
|
+
params = ActionController::Parameters.new(
|
|
496
|
+
flagged: {
|
|
497
|
+
name: 'Test',
|
|
498
|
+
some_flag: 'should not appear',
|
|
499
|
+
another_flag: 'should not appear'
|
|
500
|
+
}
|
|
501
|
+
)
|
|
502
|
+
|
|
503
|
+
permitted = params.require(:flagged).transform_params()
|
|
504
|
+
|
|
505
|
+
assert_equal 'Test', permitted[:name]
|
|
506
|
+
assert_nil permitted[:some_flag]
|
|
507
|
+
assert_nil permitted[:another_flag]
|
|
508
|
+
end
|
|
509
|
+
|
|
510
|
+
# Test empty registry
|
|
511
|
+
def test_empty_registry_all_transforms_return_empty
|
|
512
|
+
params = ActionController::Parameters.new(
|
|
513
|
+
anything: { field: 'value' }
|
|
514
|
+
)
|
|
515
|
+
|
|
516
|
+
permitted = params.require(:anything).transform_params()
|
|
517
|
+
|
|
518
|
+
assert permitted.permitted?
|
|
519
|
+
assert_nil permitted[:field]
|
|
520
|
+
end
|
|
521
|
+
|
|
522
|
+
# Test registry.registered_models
|
|
523
|
+
def test_registry_tracking
|
|
524
|
+
user_params = Class.new(ActionController::ApplicationParams) do
|
|
525
|
+
def self.name
|
|
526
|
+
'UserParams'
|
|
527
|
+
end
|
|
528
|
+
allow :name
|
|
529
|
+
end
|
|
530
|
+
|
|
531
|
+
account_params = Class.new(ActionController::ApplicationParams) do
|
|
532
|
+
def self.name
|
|
533
|
+
'AccountParams'
|
|
534
|
+
end
|
|
535
|
+
allow :title
|
|
536
|
+
end
|
|
537
|
+
|
|
538
|
+
ActionController::ParamsRegistry.register('User', user_params)
|
|
539
|
+
ActionController::ParamsRegistry.register('Account', account_params)
|
|
540
|
+
|
|
541
|
+
models = ActionController::ParamsRegistry.registered_models
|
|
542
|
+
assert_equal 2, models.length
|
|
543
|
+
assert_includes models, 'user'
|
|
544
|
+
assert_includes models, 'account'
|
|
545
|
+
|
|
546
|
+
# Both should work
|
|
547
|
+
user_p = ActionController::Parameters.new(user: { name: 'John' })
|
|
548
|
+
account_p = ActionController::Parameters.new(account: { title: 'My Account' })
|
|
549
|
+
|
|
550
|
+
assert_equal 'John', user_p.require(:user).transform_params()[:name]
|
|
551
|
+
assert_equal 'My Account', account_p.require(:account).transform_params()[:title]
|
|
552
|
+
end
|
|
553
|
+
end
|