protected_attributes 1.0.7 → 1.0.8
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/active_model/mass_assignment_security/sanitizer.rb +4 -3
- data/lib/active_record/mass_assignment_security/associations.rb +5 -1
- data/lib/protected_attributes/version.rb +1 -1
- data/test/ar_helper.rb +20 -10
- data/test/attribute_sanitization_test.rb +1 -1
- data/test/mass_assignment_security_test.rb +24 -0
- data/test/models/battle.rb +5 -0
- data/test/models/company.rb +0 -90
- data/test/models/group.rb +6 -0
- data/test/models/membership.rb +8 -0
- data/test/models/person.rb +0 -35
- data/test/models/pirate.rb +5 -0
- data/test/models/team.rb +5 -0
- data/test/models/vampire.rb +4 -0
- data/test/models/wolf.rb +4 -0
- metadata +16 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 36faf1653ed8ee17a3e6b1ae5bccb2ba3bd0b546
|
4
|
+
data.tar.gz: 614f266410d2a0885bd6d496927cdc5c0e4c9ae3
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: a775497367e9893d23a26983ec37e8c2110a79e13e3a215a94785f18d43e215d5e42ce176325fd5c09ac8a65b771a35630f377536e05b0712c62cf52f73a7818
|
7
|
+
data.tar.gz: cb338465c2fa0f8d37e491f21e411cd195c7d3a875a8d700477c47ab22a17b0687f0ba527da278d1b314707188ea0ddb2197bfcad8d934d28f9fb50f9b7d7b6a
|
@@ -14,7 +14,7 @@ module ActiveModel
|
|
14
14
|
protected
|
15
15
|
|
16
16
|
def process_removed_attributes(klass, attrs)
|
17
|
-
raise NotImplementedError, "#process_removed_attributes(attrs)
|
17
|
+
raise NotImplementedError, "#process_removed_attributes(klass, attrs) is intended to be overwritten by a subclass"
|
18
18
|
end
|
19
19
|
end
|
20
20
|
|
@@ -56,8 +56,9 @@ module ActiveModel
|
|
56
56
|
end
|
57
57
|
|
58
58
|
def process_removed_attributes(klass, attrs)
|
59
|
-
|
60
|
-
|
59
|
+
unless (attrs - insensitive_attributes).empty?
|
60
|
+
raise ActiveModel::MassAssignmentSecurity::Error.new(klass, attrs)
|
61
|
+
end
|
61
62
|
end
|
62
63
|
|
63
64
|
def insensitive_attributes
|
data/test/ar_helper.rb
CHANGED
@@ -4,14 +4,12 @@ ActiveRecord::Base.establish_connection(adapter: 'sqlite3', database: ':memory:'
|
|
4
4
|
|
5
5
|
ActiveRecord::Schema.verbose = false
|
6
6
|
ActiveRecord::Schema.define do
|
7
|
-
|
8
7
|
create_table :accounts, :force => true do |t|
|
9
8
|
t.integer :firm_id
|
10
9
|
t.string :firm_name
|
11
10
|
t.integer :credit_limit
|
12
11
|
end
|
13
12
|
|
14
|
-
|
15
13
|
create_table :companies, :force => true do |t|
|
16
14
|
t.string :type
|
17
15
|
t.integer :firm_id
|
@@ -26,38 +24,50 @@ ActiveRecord::Schema.define do
|
|
26
24
|
add_index :companies, [:firm_id, :type, :rating], :name => "company_index"
|
27
25
|
add_index :companies, [:firm_id, :type], :name => "company_partial_index", :where => "rating > 10"
|
28
26
|
|
29
|
-
|
30
27
|
create_table :keyboards, :force => true, :id => false do |t|
|
31
28
|
t.primary_key :key_number
|
32
29
|
t.string :name
|
33
30
|
end
|
34
31
|
|
35
|
-
|
36
32
|
create_table :people, :force => true do |t|
|
37
33
|
t.string :first_name, :null => false
|
38
|
-
t.references :primary_contact
|
39
34
|
t.string :gender, :limit => 1
|
40
|
-
t.references :number1_fan
|
41
|
-
t.integer :lock_version, :null => false, :default => 0
|
42
35
|
t.string :comments
|
43
|
-
t.integer :followers_count, :default => 0
|
44
36
|
t.references :best_friend
|
45
37
|
t.references :best_friend_of
|
46
38
|
t.timestamps
|
47
39
|
end
|
48
40
|
|
49
|
-
|
50
41
|
create_table :subscribers, :force => true, :id => false do |t|
|
51
42
|
t.string :nick, :null => false
|
52
43
|
t.string :name
|
53
44
|
end
|
54
45
|
add_index :subscribers, :nick, :unique => true
|
55
46
|
|
56
|
-
|
57
47
|
create_table :tasks, :force => true do |t|
|
58
48
|
t.datetime :starting
|
59
49
|
t.datetime :ending
|
60
50
|
end
|
51
|
+
|
52
|
+
create_table :pirates, :force => true do |t|
|
53
|
+
end
|
54
|
+
|
55
|
+
create_table :groups, :force => true do |t|
|
56
|
+
end
|
57
|
+
|
58
|
+
create_table :memberships, :force => true do |t|
|
59
|
+
t.integer "group_id"
|
60
|
+
t.integer "pirate_id"
|
61
|
+
end
|
62
|
+
|
63
|
+
create_table :teams, :force => true
|
64
|
+
create_table :wolves, :force => true
|
65
|
+
create_table :vampires, :force => true
|
66
|
+
create_table :battles, :force => true do |t|
|
67
|
+
t.integer "team_id"
|
68
|
+
t.integer "battle_id"
|
69
|
+
t.string "battle_type"
|
70
|
+
end
|
61
71
|
end
|
62
72
|
|
63
73
|
QUOTED_TYPE = ActiveRecord::Base.connection.quote_column_name('type')
|
@@ -246,7 +246,7 @@ class AttributeSanitizationTest < ActiveSupport::TestCase
|
|
246
246
|
def test_protection_against_class_attribute_writers
|
247
247
|
attribute_writers = [:logger, :configurations, :primary_key_prefix_type, :table_name_prefix, :table_name_suffix, :pluralize_table_names,
|
248
248
|
:default_timezone, :schema_format, :lock_optimistically, :timestamped_migrations, :default_scopes,
|
249
|
-
:connection_handler, :nested_attributes_options,
|
249
|
+
:connection_handler, :nested_attributes_options,
|
250
250
|
:attribute_method_matchers, :time_zone_aware_attributes, :skip_time_zone_conversion_for_attributes]
|
251
251
|
|
252
252
|
attribute_writers.push(:_attr_readonly) if active_record_40?
|
@@ -1,6 +1,13 @@
|
|
1
1
|
require 'test_helper'
|
2
2
|
require 'active_model/mass_assignment_security'
|
3
3
|
require 'models/mass_assignment_specific'
|
4
|
+
require 'models/pirate'
|
5
|
+
require 'models/group'
|
6
|
+
require 'models/membership'
|
7
|
+
require 'models/battle'
|
8
|
+
require 'models/vampire'
|
9
|
+
require 'models/wolf'
|
10
|
+
require 'models/team'
|
4
11
|
|
5
12
|
class CustomSanitizer < ActiveModel::MassAssignmentSecurity::Sanitizer
|
6
13
|
|
@@ -115,4 +122,21 @@ class MassAssignmentSecurityTest < ActiveModel::TestCase
|
|
115
122
|
ensure
|
116
123
|
User.mass_assignment_sanitizer = old_sanitizer
|
117
124
|
end
|
125
|
+
|
126
|
+
def test_concat_has_many_through_association_member
|
127
|
+
group = Group.create!
|
128
|
+
pirate = Pirate.create!
|
129
|
+
group.members << pirate
|
130
|
+
assert_equal pirate.memberships.first, group.memberships.first
|
131
|
+
end
|
132
|
+
|
133
|
+
def test_concat_has_many_through_polymorphic_association
|
134
|
+
team = Team.create!
|
135
|
+
vampire = Vampire.create!
|
136
|
+
wolf = Wolf.create!
|
137
|
+
|
138
|
+
team.vampire_battles << vampire
|
139
|
+
wolf.teams << team
|
140
|
+
assert_equal team.wolf_battles.first, wolf
|
141
|
+
end
|
118
142
|
end
|
data/test/models/company.rb
CHANGED
@@ -4,99 +4,9 @@ end
|
|
4
4
|
|
5
5
|
class Company < AbstractCompany
|
6
6
|
attr_protected :rating
|
7
|
-
self.sequence_name = :companies_nonstd_seq
|
8
|
-
|
9
|
-
validates_presence_of :name
|
10
|
-
|
11
|
-
has_one :dummy_account, :foreign_key => "firm_id", :class_name => "Account"
|
12
|
-
has_many :contracts
|
13
|
-
has_many :developers, :through => :contracts
|
14
|
-
|
15
|
-
def arbitrary_method
|
16
|
-
"I am Jack's profound disappointment"
|
17
|
-
end
|
18
|
-
|
19
|
-
private
|
20
|
-
|
21
|
-
def private_method
|
22
|
-
"I am Jack's innermost fears and aspirations"
|
23
|
-
end
|
24
7
|
end
|
25
8
|
|
26
9
|
class Firm < Company
|
27
|
-
has_many :unsorted_clients, :class_name => "Client"
|
28
|
-
has_many :unsorted_clients_with_symbol, :class_name => :Client
|
29
|
-
has_many :clients_sorted_desc, -> { order "id DESC" }, :class_name => "Client"
|
30
|
-
has_many :clients_of_firm, -> { order "id" }, :foreign_key => "client_of", :class_name => "Client"
|
31
|
-
has_many :clients_ordered_by_name, -> { order "name" }, :class_name => "Client"
|
32
|
-
has_many :unvalidated_clients_of_firm, :foreign_key => "client_of", :class_name => "Client", :validate => false
|
33
|
-
has_many :dependent_clients_of_firm, -> { order "id" }, :foreign_key => "client_of", :class_name => "Client", :dependent => :destroy
|
34
|
-
has_many :exclusively_dependent_clients_of_firm, -> { order "id" }, :foreign_key => "client_of", :class_name => "Client", :dependent => :delete_all
|
35
|
-
has_many :limited_clients, -> { limit 1 }, :class_name => "Client"
|
36
|
-
has_many :clients_with_interpolated_conditions, ->(firm) { where "rating > #{firm.rating}" }, :class_name => "Client"
|
37
|
-
has_many :clients_like_ms, -> { where("name = 'Microsoft'").order("id") }, :class_name => "Client"
|
38
|
-
has_many :clients_like_ms_with_hash_conditions, -> { where(:name => 'Microsoft').order("id") }, :class_name => "Client"
|
39
|
-
|
40
|
-
if active_record_40?
|
41
|
-
ActiveSupport::Deprecation.silence do
|
42
|
-
has_many :clients, -> { order "id" }, :dependent => :destroy, :counter_sql =>
|
43
|
-
"SELECT COUNT(*) FROM companies WHERE firm_id = 1 " +
|
44
|
-
"AND (#{QUOTED_TYPE} = 'Client' OR #{QUOTED_TYPE} = 'SpecialClient' OR #{QUOTED_TYPE} = 'VerySpecialClient' )",
|
45
|
-
:before_remove => :log_before_remove,
|
46
|
-
:after_remove => :log_after_remove
|
47
|
-
has_many :clients_using_sql, :class_name => "Client", :finder_sql => proc { "SELECT * FROM companies WHERE client_of = #{id}" }
|
48
|
-
has_many :clients_using_counter_sql, :class_name => "Client",
|
49
|
-
:finder_sql => proc { "SELECT * FROM companies WHERE client_of = #{id} " },
|
50
|
-
:counter_sql => proc { "SELECT COUNT(*) FROM companies WHERE client_of = #{id}" }
|
51
|
-
has_many :clients_using_zero_counter_sql, :class_name => "Client",
|
52
|
-
:finder_sql => proc { "SELECT * FROM companies WHERE client_of = #{id}" },
|
53
|
-
:counter_sql => proc { "SELECT 0 FROM companies WHERE client_of = #{id}" }
|
54
|
-
has_many :no_clients_using_counter_sql, :class_name => "Client",
|
55
|
-
:finder_sql => 'SELECT * FROM companies WHERE client_of = 1000',
|
56
|
-
:counter_sql => 'SELECT COUNT(*) FROM companies WHERE client_of = 1000'
|
57
|
-
has_many :clients_using_finder_sql, :class_name => "Client", :finder_sql => 'SELECT * FROM companies WHERE 1=1'
|
58
|
-
end
|
59
|
-
end
|
60
|
-
|
61
|
-
has_many :plain_clients, :class_name => 'Client'
|
62
|
-
has_many :readonly_clients, -> { readonly }, :class_name => 'Client'
|
63
|
-
has_many :clients_using_primary_key, :class_name => 'Client',
|
64
|
-
:primary_key => 'name', :foreign_key => 'firm_name'
|
65
|
-
has_many :clients_using_primary_key_with_delete_all, :class_name => 'Client',
|
66
|
-
:primary_key => 'name', :foreign_key => 'firm_name', :dependent => :delete_all
|
67
|
-
has_many :clients_grouped_by_firm_id, -> { group("firm_id").select("firm_id") }, :class_name => "Client"
|
68
|
-
has_many :clients_grouped_by_name, -> { group("name").select("name") }, :class_name => "Client"
|
69
|
-
|
70
|
-
has_one :account, :foreign_key => "firm_id", :dependent => :destroy, :validate => true
|
71
|
-
has_one :unvalidated_account, :foreign_key => "firm_id", :class_name => 'Account', :validate => false
|
72
|
-
has_one :account_with_select, -> { select("id, firm_id") }, :foreign_key => "firm_id", :class_name=>'Account'
|
73
|
-
has_one :readonly_account, -> { readonly }, :foreign_key => "firm_id", :class_name => "Account"
|
74
|
-
# added order by id as in fixtures there are two accounts for Rails Core
|
75
|
-
# Oracle tests were failing because of that as the second fixture was selected
|
76
|
-
has_one :account_using_primary_key, -> { order('id') }, :primary_key => "firm_id", :class_name => "Account"
|
77
|
-
has_one :account_using_foreign_and_primary_keys, :foreign_key => "firm_name", :primary_key => "name", :class_name => "Account"
|
78
|
-
has_one :deletable_account, :foreign_key => "firm_id", :class_name => "Account", :dependent => :delete
|
79
|
-
|
80
|
-
has_one :account_limit_500_with_hash_conditions, -> { where :credit_limit => 500 }, :foreign_key => "firm_id", :class_name => "Account"
|
81
|
-
|
82
|
-
has_one :unautosaved_account, :foreign_key => "firm_id", :class_name => 'Account', :autosave => false
|
83
|
-
has_many :accounts
|
84
|
-
has_many :unautosaved_accounts, :foreign_key => "firm_id", :class_name => 'Account', :autosave => false
|
85
|
-
|
86
|
-
has_many :association_with_references, -> { references(:foo) }, :class_name => 'Client'
|
87
|
-
|
88
|
-
def log
|
89
|
-
@log ||= []
|
90
|
-
end
|
91
|
-
|
92
|
-
private
|
93
|
-
def log_before_remove(record)
|
94
|
-
log << "before_remove#{record.id}"
|
95
|
-
end
|
96
|
-
|
97
|
-
def log_after_remove(record)
|
98
|
-
log << "after_remove#{record.id}"
|
99
|
-
end
|
100
10
|
end
|
101
11
|
|
102
12
|
class Corporation < Company
|
data/test/models/person.rb
CHANGED
@@ -1,38 +1,3 @@
|
|
1
|
-
class Person < ActiveRecord::Base
|
2
|
-
has_many :readers
|
3
|
-
has_many :secure_readers
|
4
|
-
has_one :reader
|
5
|
-
|
6
|
-
has_many :posts, :through => :readers
|
7
|
-
has_many :secure_posts, :through => :secure_readers
|
8
|
-
has_many :posts_with_no_comments, -> { includes(:comments).where('comments.id is null').references(:comments) },
|
9
|
-
:through => :readers, :source => :post
|
10
|
-
|
11
|
-
has_many :followers, foreign_key: 'friend_id', class_name: 'Friendship'
|
12
|
-
|
13
|
-
has_many :references
|
14
|
-
has_many :bad_references
|
15
|
-
has_many :fixed_bad_references, -> { where :favourite => true }, :class_name => 'BadReference'
|
16
|
-
has_one :favourite_reference, -> { where 'favourite=?', true }, :class_name => 'Reference'
|
17
|
-
has_many :posts_with_comments_sorted_by_comment_id, -> { includes(:comments).order('comments.id') }, :through => :readers, :source => :post
|
18
|
-
|
19
|
-
has_many :jobs, :through => :references
|
20
|
-
has_many :jobs_with_dependent_destroy, :source => :job, :through => :references, :dependent => :destroy
|
21
|
-
has_many :jobs_with_dependent_delete_all, :source => :job, :through => :references, :dependent => :delete_all
|
22
|
-
has_many :jobs_with_dependent_nullify, :source => :job, :through => :references, :dependent => :nullify
|
23
|
-
|
24
|
-
belongs_to :primary_contact, :class_name => 'Person'
|
25
|
-
has_many :agents, :class_name => 'Person', :foreign_key => 'primary_contact_id'
|
26
|
-
has_many :agents_of_agents, :through => :agents, :source => :agents
|
27
|
-
belongs_to :number1_fan, :class_name => 'Person'
|
28
|
-
|
29
|
-
has_many :agents_posts, :through => :agents, :source => :posts
|
30
|
-
has_many :agents_posts_authors, :through => :agents_posts, :source => :author
|
31
|
-
|
32
|
-
scope :males, -> { where(:gender => 'M') }
|
33
|
-
scope :females, -> { where(:gender => 'F') }
|
34
|
-
end
|
35
|
-
|
36
1
|
class LoosePerson < ActiveRecord::Base
|
37
2
|
self.table_name = 'people'
|
38
3
|
|
data/test/models/team.rb
ADDED
@@ -0,0 +1,5 @@
|
|
1
|
+
class Team < ActiveRecord::Base
|
2
|
+
has_many :battles
|
3
|
+
has_many :wolf_battles, :through => :battles, :class_name => 'Wolf', :source => :battle, :source_type => 'Wolf'
|
4
|
+
has_many :vampire_battles, :through => :battles, :class_name => 'Vampire', :source => :battle, :source_type => 'Vampire'
|
5
|
+
end
|
data/test/models/wolf.rb
ADDED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: protected_attributes
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0.
|
4
|
+
version: 1.0.8
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- David Heinemeier Hansson
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2014-
|
11
|
+
date: 2014-06-16 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activemodel
|
@@ -133,12 +133,19 @@ files:
|
|
133
133
|
- test/mass_assignment_security/sanitizer_test.rb
|
134
134
|
- test/mass_assignment_security/white_list_test.rb
|
135
135
|
- test/mass_assignment_security_test.rb
|
136
|
+
- test/models/battle.rb
|
136
137
|
- test/models/company.rb
|
138
|
+
- test/models/group.rb
|
137
139
|
- test/models/keyboard.rb
|
138
140
|
- test/models/mass_assignment_specific.rb
|
141
|
+
- test/models/membership.rb
|
139
142
|
- test/models/person.rb
|
143
|
+
- test/models/pirate.rb
|
140
144
|
- test/models/subscriber.rb
|
141
145
|
- test/models/task.rb
|
146
|
+
- test/models/team.rb
|
147
|
+
- test/models/vampire.rb
|
148
|
+
- test/models/wolf.rb
|
142
149
|
- test/test_helper.rb
|
143
150
|
homepage: https://github.com/rails/protected_attributes
|
144
151
|
licenses:
|
@@ -174,10 +181,17 @@ test_files:
|
|
174
181
|
- test/mass_assignment_security/sanitizer_test.rb
|
175
182
|
- test/mass_assignment_security/white_list_test.rb
|
176
183
|
- test/mass_assignment_security_test.rb
|
184
|
+
- test/models/battle.rb
|
177
185
|
- test/models/company.rb
|
186
|
+
- test/models/group.rb
|
178
187
|
- test/models/keyboard.rb
|
179
188
|
- test/models/mass_assignment_specific.rb
|
189
|
+
- test/models/membership.rb
|
180
190
|
- test/models/person.rb
|
191
|
+
- test/models/pirate.rb
|
181
192
|
- test/models/subscriber.rb
|
182
193
|
- test/models/task.rb
|
194
|
+
- test/models/team.rb
|
195
|
+
- test/models/vampire.rb
|
196
|
+
- test/models/wolf.rb
|
183
197
|
- test/test_helper.rb
|