jakewendt-rails_extension 2.0.22
Sign up to get free protection for your applications and to get access to all the features.
- data/LICENSE +20 -0
- data/README.rdoc +42 -0
- data/generators/rails_extension/USAGE +0 -0
- data/generators/rails_extension/rails_extension_generator.rb +72 -0
- data/lib/jakewendt-rails_extension.rb +1 -0
- data/lib/rails_extension.rb +18 -0
- data/lib/rails_extension/action_controller_extension.rb +8 -0
- data/lib/rails_extension/action_controller_extension/accessible_via_format.rb +2 -0
- data/lib/rails_extension/action_controller_extension/accessible_via_protocol.rb +403 -0
- data/lib/rails_extension/action_controller_extension/accessible_via_user.rb +606 -0
- data/lib/rails_extension/action_controller_extension/routing.rb +23 -0
- data/lib/rails_extension/action_controller_extension/test_case.rb +19 -0
- data/lib/rails_extension/active_record_extension.rb +5 -0
- data/lib/rails_extension/active_record_extension/base.rb +82 -0
- data/lib/rails_extension/active_record_extension/error.rb +18 -0
- data/lib/rails_extension/active_record_extension/errors.rb +20 -0
- data/lib/rails_extension/active_support_extension.rb +29 -0
- data/lib/rails_extension/active_support_extension/associations.rb +209 -0
- data/lib/rails_extension/active_support_extension/attributes.rb +235 -0
- data/lib/rails_extension/active_support_extension/pending.rb +67 -0
- data/lib/rails_extension/active_support_extension/test_case.rb +211 -0
- data/rails/init.rb +1 -0
- metadata +146 -0
@@ -0,0 +1,23 @@
|
|
1
|
+
module RailsExtension::ActionControllerExtension::Routing
|
2
|
+
|
3
|
+
def self.included(base)
|
4
|
+
base.extend ClassMethods
|
5
|
+
end
|
6
|
+
|
7
|
+
module ClassMethods
|
8
|
+
|
9
|
+
# def assert_route
|
10
|
+
# end
|
11
|
+
|
12
|
+
def assert_no_route(verb,action,args={})
|
13
|
+
test "#{brand}no route to #{verb} #{action} #{args}" do
|
14
|
+
assert_raise(ActionController::RoutingError){
|
15
|
+
send(verb,action,args)
|
16
|
+
}
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
end # module ClassMethods
|
21
|
+
end # module RailsExtension::ActionControllerExtension::Routing
|
22
|
+
ActionController::TestCase.send(:include,
|
23
|
+
RailsExtension::ActionControllerExtension::Routing)
|
@@ -0,0 +1,19 @@
|
|
1
|
+
module RailsExtension::ActionControllerExtension::TestCase
|
2
|
+
|
3
|
+
def turn_https_on
|
4
|
+
@request.env['HTTPS'] = 'on'
|
5
|
+
# @request.env['HTTP_X_FORWARDED_PROTO'] == 'https'
|
6
|
+
end
|
7
|
+
|
8
|
+
def turn_https_off
|
9
|
+
@request.env['HTTPS'] = nil
|
10
|
+
end
|
11
|
+
|
12
|
+
def assert_layout(layout)
|
13
|
+
layout = "layouts/#{layout}" unless layout.match(/^layouts/)
|
14
|
+
assert_equal layout, @response.layout
|
15
|
+
end
|
16
|
+
|
17
|
+
end # module RailsExtension::ActionControllerExtension::TestCase
|
18
|
+
ActionController::TestCase.send(:include,
|
19
|
+
RailsExtension::ActionControllerExtension::TestCase)
|
@@ -0,0 +1,82 @@
|
|
1
|
+
module RailsExtension::ActiveRecordExtension::Base
|
2
|
+
def self.included(base)
|
3
|
+
base.extend(ClassMethods)
|
4
|
+
end
|
5
|
+
|
6
|
+
module ClassMethods
|
7
|
+
|
8
|
+
def random
|
9
|
+
count = count()
|
10
|
+
if count > 0
|
11
|
+
first(:offset => rand(count))
|
12
|
+
else
|
13
|
+
nil
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
def validates_absence_of(*attr_names)
|
18
|
+
configuration = { :on => :save,
|
19
|
+
:message => "is present and must be absent." }
|
20
|
+
configuration.update(attr_names.extract_options!)
|
21
|
+
|
22
|
+
send(validation_method(configuration[:on]), configuration) do |record|
|
23
|
+
attr_names.each do |attr_name|
|
24
|
+
unless record.send(attr_name).blank?
|
25
|
+
record.errors.add(attr_name,
|
26
|
+
ActiveRecord::Error.new(record,attr_name,:present,
|
27
|
+
{ :message => configuration[:message] }))
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def validates_past_date_for(*attr_names)
|
34
|
+
configuration = { :on => :save,
|
35
|
+
:message => "is in the future and must be in the past." }
|
36
|
+
configuration.update(attr_names.extract_options!)
|
37
|
+
|
38
|
+
send(validation_method(configuration[:on]), configuration) do |record|
|
39
|
+
attr_names.each do |attr_name|
|
40
|
+
date = record.send(attr_name)
|
41
|
+
if !date.blank? && Time.now < date
|
42
|
+
record.errors.add(attr_name,
|
43
|
+
ActiveRecord::Error.new(record,attr_name,:not_past_date,
|
44
|
+
{ :message => configuration[:message] }))
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
# This doesn't work as one would expect if the column
|
51
|
+
# is a DateTime instead of just a Date.
|
52
|
+
# For some reason, *_before_type_cast actually
|
53
|
+
# returns a parsed DateTime?
|
54
|
+
def validates_complete_date_for(*attr_names)
|
55
|
+
configuration = { :on => :save,
|
56
|
+
:message => "is not a complete date." }
|
57
|
+
configuration.update(attr_names.extract_options!)
|
58
|
+
|
59
|
+
send(validation_method(configuration[:on]), configuration) do |record|
|
60
|
+
attr_names.each do |attr_name|
|
61
|
+
|
62
|
+
value = record.send("#{attr_name}_before_type_cast")
|
63
|
+
unless( configuration[:allow_nil] && value.blank? ) ||
|
64
|
+
( !value.is_a?(String) )
|
65
|
+
date_hash = Date._parse(value)
|
66
|
+
unless date_hash.has_key?(:year) &&
|
67
|
+
date_hash.has_key?(:mon) &&
|
68
|
+
date_hash.has_key?(:mday)
|
69
|
+
record.errors.add(attr_name,
|
70
|
+
ActiveRecord::Error.new(record,attr_name,:not_complete_date,
|
71
|
+
{ :message => configuration[:message] }))
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
end
|
79
|
+
|
80
|
+
end
|
81
|
+
ActiveRecord::Base.send(:include,
|
82
|
+
RailsExtension::ActiveRecordExtension::Base)
|
@@ -0,0 +1,18 @@
|
|
1
|
+
module RailsExtension::ActiveRecordExtension::Error
|
2
|
+
|
3
|
+
def self.included(base)
|
4
|
+
base.alias_method_chain( :generate_full_message, :attribute_strip ) unless
|
5
|
+
base.method_defined?(:generate_full_message_without_attribute_strip)
|
6
|
+
end
|
7
|
+
|
8
|
+
def generate_full_message_with_attribute_strip(options = {}, &block)
|
9
|
+
m = generate_full_message_without_attribute_strip(options, &block)
|
10
|
+
unless( ( i = m.index('<|X|') ).nil? )
|
11
|
+
m = m[i+4..-1]
|
12
|
+
end
|
13
|
+
m
|
14
|
+
end
|
15
|
+
|
16
|
+
end
|
17
|
+
ActiveRecord::Error.send(:include,
|
18
|
+
RailsExtension::ActiveRecordExtension::Error)
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module RailsExtension::ActiveRecordExtension::Errors
|
2
|
+
def self.included(base)
|
3
|
+
base.extend(ClassMethods)
|
4
|
+
base.send(:include,InstanceMethods)
|
5
|
+
end
|
6
|
+
module InstanceMethods
|
7
|
+
def on_attr_and_type(attribute,type)
|
8
|
+
attribute = attribute.to_s
|
9
|
+
return nil unless @errors.has_key?(attribute)
|
10
|
+
@errors[attribute].collect(&:type).include?(type)
|
11
|
+
end
|
12
|
+
end
|
13
|
+
module ClassMethods
|
14
|
+
def delete(key)
|
15
|
+
@errors.delete(key.to_s)
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end # RailsExtension::ActiveRecordExtension::Errors
|
19
|
+
ActiveRecord::Errors.send(:include,
|
20
|
+
RailsExtension::ActiveRecordExtension::Errors)
|
@@ -0,0 +1,29 @@
|
|
1
|
+
require 'active_support'
|
2
|
+
require 'active_support/test_case'
|
3
|
+
$LOAD_PATH.unshift(File.dirname(__FILE__))
|
4
|
+
require 'active_support_extension/test_case'
|
5
|
+
require 'active_support_extension/associations'
|
6
|
+
require 'active_support_extension/attributes'
|
7
|
+
require 'active_support_extension/pending'
|
8
|
+
|
9
|
+
|
10
|
+
Rails.backtrace_cleaner.add_silencer {|line|
|
11
|
+
# line =~ /\/test\/.*\.\.\/declarative\.rb:/
|
12
|
+
# Due to my modification, every error is accompanied by
|
13
|
+
# 3 additional and unnecessary lines like ...
|
14
|
+
# /test/functional/../declarative.rb:21:in `_test_should_change_locale_to_es_without_verbosity'
|
15
|
+
#/test/functional/../declarative.rb:21:in `send'
|
16
|
+
#/test/functional/../declarative.rb:21:in `_test_should_change_locale_to_es_with_verbosity']:
|
17
|
+
#
|
18
|
+
# in rvm/jruby the error is passing through
|
19
|
+
# test/declarative.rb:21:in `_test_should_NOT_create_new_user_if_invitation_update_fails_with_verbosity']:
|
20
|
+
|
21
|
+
# /Users/jakewendt/github_repo/jakewendt/ucb_ccls_clic/vendor/plugins/ucb_ccls_engine/rails/../test/helpers/declarative.rb:21:in `_test_AWiHTTP_should_get_show_with_admin_login_with_verbosity'
|
22
|
+
|
23
|
+
# This doesn't seem to work at all in the plugin engine.
|
24
|
+
# line =~ /test.*\/declarative\.rb:/
|
25
|
+
# line =~ /simply_testable\/declarative\.rb:/
|
26
|
+
|
27
|
+
# Return true or false. Need to collect if adding multiple conditions.
|
28
|
+
line =~ /rails_extension\/active_support_extension\/test_case\.rb:/
|
29
|
+
} if defined? Rails
|
@@ -0,0 +1,209 @@
|
|
1
|
+
module RailsExtension::ActiveSupportExtension::Associations
|
2
|
+
|
3
|
+
def self.included(base)
|
4
|
+
base.extend ClassMethods
|
5
|
+
# base.send(:include,InstanceMethods)
|
6
|
+
base.class_eval do
|
7
|
+
class << self
|
8
|
+
alias_methods = {
|
9
|
+
:should_have_many => :should_have_many_,
|
10
|
+
:should_have_many_associations => :should_have_many_,
|
11
|
+
:should_require_valid_associations => :requires_valid_associations,
|
12
|
+
:should_require_valid_association => :requires_valid_associations,
|
13
|
+
:requires_valid_association => :requires_valid_associations,
|
14
|
+
:requires_valid => :requires_valid_associations
|
15
|
+
}
|
16
|
+
alias_methods.each do |alias_name,method_name|
|
17
|
+
alias_method( "assert_#{alias_name}",
|
18
|
+
"assert_#{method_name}" ) unless
|
19
|
+
self.method_defined?("assert_#{alias_name}")
|
20
|
+
end # alias_methods.each
|
21
|
+
end # class << self
|
22
|
+
end # base.class_eval
|
23
|
+
end # def self.included
|
24
|
+
|
25
|
+
module ClassMethods
|
26
|
+
|
27
|
+
def assert_should_initially_belong_to(*associations)
|
28
|
+
options = associations.extract_options!
|
29
|
+
model = options[:model] || st_model_name
|
30
|
+
associations.each do |assoc|
|
31
|
+
class_name = ( assoc = assoc.to_s ).camelize
|
32
|
+
title = "#{brand}should initially belong to #{assoc}"
|
33
|
+
if !options[:class_name].blank?
|
34
|
+
title << " ( #{options[:class_name]} )"
|
35
|
+
class_name = options[:class_name].to_s
|
36
|
+
end
|
37
|
+
test title do
|
38
|
+
object = create_object
|
39
|
+
assert_not_nil object.send(assoc)
|
40
|
+
if object.send(assoc).respond_to?(
|
41
|
+
"#{model.underscore.pluralize}_count")
|
42
|
+
assert_equal 1, object.reload.send(assoc).send(
|
43
|
+
"#{model.underscore.pluralize}_count")
|
44
|
+
end
|
45
|
+
if !options[:class_name].blank?
|
46
|
+
assert object.send(assoc).is_a?(class_name.constantize)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
def assert_should_belong_to(*associations)
|
53
|
+
options = associations.extract_options!
|
54
|
+
model = options[:model] || st_model_name
|
55
|
+
associations.each do |assoc|
|
56
|
+
class_name = ( assoc = assoc.to_s ).camelize
|
57
|
+
title = "#{brand}should belong to #{assoc}"
|
58
|
+
# if !options[:as].blank?
|
59
|
+
# title << " as #{options[:as]}"
|
60
|
+
# as = options[:as]
|
61
|
+
# end
|
62
|
+
if !options[:class_name].blank?
|
63
|
+
title << " ( #{options[:class_name]} )"
|
64
|
+
class_name = options[:class_name].to_s
|
65
|
+
end
|
66
|
+
test title do
|
67
|
+
object = create_object
|
68
|
+
assert_nil object.send(assoc)
|
69
|
+
object.send("#{assoc}=",send("create_#{class_name.underscore}"))
|
70
|
+
assert_not_nil object.send(assoc)
|
71
|
+
assert object.send(assoc).is_a?(class_name.constantize
|
72
|
+
) unless options[:polymorphic]
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
77
|
+
def assert_should_have_one(*associations)
|
78
|
+
options = associations.extract_options!
|
79
|
+
model = options[:model] || st_model_name
|
80
|
+
# foreign_key = if !options[:foreign_key].blank?
|
81
|
+
# options[:foreign_key].to_sym
|
82
|
+
# else
|
83
|
+
# "#{model.underscore}_id".to_sym
|
84
|
+
# end
|
85
|
+
associations.each do |assoc|
|
86
|
+
assoc = assoc.to_s
|
87
|
+
test "#{brand}should have one #{assoc}" do
|
88
|
+
object = create_object
|
89
|
+
assert_nil object.reload.send(assoc)
|
90
|
+
# send("create_#{assoc}", foreign_key => object.id)
|
91
|
+
send("create_#{assoc}", model.underscore => object )
|
92
|
+
assert_not_nil object.reload.send(assoc)
|
93
|
+
object.send(assoc).destroy
|
94
|
+
assert_nil object.reload.send(assoc)
|
95
|
+
end
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
def assert_should_have_many_(*associations)
|
100
|
+
options = associations.extract_options!
|
101
|
+
model = options[:model] || st_model_name
|
102
|
+
# foreign_key = if !options[:foreign_key].blank?
|
103
|
+
# options[:foreign_key].to_sym
|
104
|
+
# else
|
105
|
+
# "#{model.underscore}_id".to_sym
|
106
|
+
# end
|
107
|
+
associations.each do |assoc|
|
108
|
+
class_name = ( assoc = assoc.to_s ).camelize
|
109
|
+
title = "#{brand}should have many #{assoc}"
|
110
|
+
if !options[:class_name].blank?
|
111
|
+
title << " ( #{options[:class_name]} )"
|
112
|
+
class_name = options[:class_name].to_s
|
113
|
+
end
|
114
|
+
if !options[:as].blank?
|
115
|
+
title << " ( as #{options[:as]} )"
|
116
|
+
end
|
117
|
+
test title do
|
118
|
+
object = create_object
|
119
|
+
assert_equal 0, object.send(assoc).length
|
120
|
+
command = ["create_#{class_name.singularize.underscore}"]
|
121
|
+
if !options[:foreign_key].blank?
|
122
|
+
command.push( options[:foreign_key].to_sym => object.id )
|
123
|
+
elsif !options[:as].blank?
|
124
|
+
command.push( options[:as].to_sym => object )
|
125
|
+
else
|
126
|
+
command.push( model.underscore => object )
|
127
|
+
end
|
128
|
+
# send("create_#{class_name.singularize.underscore}", foreign_key => object.id)
|
129
|
+
# send("create_#{class_name.singularize.underscore}", model.underscore => object )
|
130
|
+
send *command
|
131
|
+
assert_equal 1, object.reload.send(assoc).length
|
132
|
+
if object.respond_to?("#{assoc}_count")
|
133
|
+
assert_equal 1, object.reload.send("#{assoc}_count")
|
134
|
+
end
|
135
|
+
# send("create_#{class_name.singularize.underscore}", foreign_key => object.id)
|
136
|
+
# send("create_#{class_name.singularize.underscore}", model.underscore => object )
|
137
|
+
send *command
|
138
|
+
assert_equal 2, object.reload.send(assoc).length
|
139
|
+
if object.respond_to?("#{assoc}_count")
|
140
|
+
assert_equal 2, object.reload.send("#{assoc}_count")
|
141
|
+
end
|
142
|
+
end
|
143
|
+
end
|
144
|
+
end
|
145
|
+
|
146
|
+
def assert_should_habtm(*associations)
|
147
|
+
options = associations.extract_options!
|
148
|
+
model = options[:model] || st_model_name
|
149
|
+
associations.each do |assoc|
|
150
|
+
assoc = assoc.to_s
|
151
|
+
test "#{brand}should habtm #{assoc}" do
|
152
|
+
object = create_object
|
153
|
+
assert_equal 0, object.send(assoc).length
|
154
|
+
object.send(assoc) << send("create_#{assoc.singularize}")
|
155
|
+
assert_equal 1, object.reload.send(assoc).length
|
156
|
+
if object.respond_to?("#{assoc}_count")
|
157
|
+
assert_equal 1, object.reload.send("#{assoc}_count")
|
158
|
+
end
|
159
|
+
object.send(assoc) << send("create_#{assoc.singularize}")
|
160
|
+
assert_equal 2, object.reload.send(assoc).length
|
161
|
+
if object.respond_to?("#{assoc}_count")
|
162
|
+
assert_equal 2, object.reload.send("#{assoc}_count")
|
163
|
+
end
|
164
|
+
end
|
165
|
+
end
|
166
|
+
end
|
167
|
+
|
168
|
+
def assert_requires_valid_associations(*associations)
|
169
|
+
# options = associations.extract_options!
|
170
|
+
# model = options[:model] || st_model_name
|
171
|
+
#
|
172
|
+
# associations.each do |assoc|
|
173
|
+
# as = assoc = assoc.to_s
|
174
|
+
# as = options[:as] if !options[:as].blank?
|
175
|
+
#
|
176
|
+
# test "#{brand}should require foreign key #{as}_id" do
|
177
|
+
# assert_difference("#{model}.count",0) do
|
178
|
+
# object = create_object("#{as}_id".to_sym => nil)
|
179
|
+
# assert object.errors.on("#{as}_id".to_sym)
|
180
|
+
# end
|
181
|
+
# end
|
182
|
+
#
|
183
|
+
# # test "#{brand}should require valid foreign key #{as}_id" do
|
184
|
+
# # assert_difference("#{model}.count",0) do
|
185
|
+
# # object = create_object("#{as}_id".to_sym => 0)
|
186
|
+
# # assert object.errors.on("#{as}_id".to_sym)
|
187
|
+
# # end
|
188
|
+
# # end
|
189
|
+
#
|
190
|
+
# title = "#{brand}should require valid association #{assoc}"
|
191
|
+
# title << " as #{options[:as]}" if !options[:as].blank?
|
192
|
+
# test title do
|
193
|
+
# assert_difference("#{model}.count",0) {
|
194
|
+
# object = create_object(
|
195
|
+
# assoc.to_sym => Factory.build(assoc.to_sym))
|
196
|
+
# # as.to_sym => Factory.build(assoc.to_sym))
|
197
|
+
# assert object.errors.on("#{as}_id".to_sym)
|
198
|
+
# }
|
199
|
+
# end
|
200
|
+
#
|
201
|
+
# end
|
202
|
+
|
203
|
+
end
|
204
|
+
|
205
|
+
end # ClassMethods
|
206
|
+
|
207
|
+
end # module RailsExtension::Associations
|
208
|
+
ActiveSupport::TestCase.send(:include,
|
209
|
+
RailsExtension::ActiveSupportExtension::Associations)
|
@@ -0,0 +1,235 @@
|
|
1
|
+
module RailsExtension::ActiveSupportExtension::Attributes
|
2
|
+
|
3
|
+
def self.included(base)
|
4
|
+
base.extend ClassMethods
|
5
|
+
# base.send(:include,InstanceMethods)
|
6
|
+
base.class_eval do
|
7
|
+
class << self
|
8
|
+
alias_methods = {
|
9
|
+
:require_unique_attributes => :require_unique_attribute,
|
10
|
+
:require_unique => :require_unique_attribute,
|
11
|
+
:require_attributes_not_nil => :require_attribute_not_nil,
|
12
|
+
:require_not_nil => :require_attribute_not_nil,
|
13
|
+
:require_attributes => :require_attribute,
|
14
|
+
:require => :require_attribute,
|
15
|
+
:not_require_attributes => :not_require_attribute,
|
16
|
+
:not_require => :not_require_attribute,
|
17
|
+
:require_attributes_length => :require_attribute_length,
|
18
|
+
:require_length => :require_attribute_length,
|
19
|
+
:protect_attributes => :protect_attribute,
|
20
|
+
:protect => :protect_attribute,
|
21
|
+
:not_protect_attributes => :not_protect_attribute,
|
22
|
+
:not_protect => :not_protect_attribute
|
23
|
+
}
|
24
|
+
alias_methods.each do |alias_name,method_name|
|
25
|
+
alias_method( "assert_should_#{alias_name}",
|
26
|
+
"assert_should_#{method_name}" ) unless
|
27
|
+
self.method_defined?("assert_should_#{alias_name}")
|
28
|
+
end # alias_methods.each
|
29
|
+
end # class << self
|
30
|
+
end # base.class_eval
|
31
|
+
end # def self.included
|
32
|
+
|
33
|
+
module ClassMethods
|
34
|
+
|
35
|
+
def assert_should_require_unique_attribute(*attributes)
|
36
|
+
options = attributes.extract_options!
|
37
|
+
model = options[:model] || st_model_name
|
38
|
+
|
39
|
+
attributes.each do |attr|
|
40
|
+
attr = attr.to_s
|
41
|
+
title = "#{brand}should require unique #{attr}"
|
42
|
+
scope = options[:scope]
|
43
|
+
unless scope.blank?
|
44
|
+
title << " scope "
|
45
|
+
title << (( scope.is_a?(Array) )?scope.join(','):scope.to_s)
|
46
|
+
end
|
47
|
+
test title do
|
48
|
+
o = create_object
|
49
|
+
assert_no_difference "#{model}.count" do
|
50
|
+
attrs = { attr.to_sym => o.send(attr) }
|
51
|
+
if( scope.is_a?(String) || scope.is_a?(Symbol) )
|
52
|
+
attrs[scope.to_sym] = o.send(scope.to_sym)
|
53
|
+
elsif scope.is_a?(Array)
|
54
|
+
scope.each do |s|
|
55
|
+
attrs[s.to_sym] = o.send(s.to_sym)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
object = create_object(attrs)
|
59
|
+
assert object.errors.on_attr_and_type(attr.to_sym, :taken)
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
end
|
64
|
+
|
65
|
+
def assert_should_require_attribute_not_nil(*attributes)
|
66
|
+
options = attributes.extract_options!
|
67
|
+
model = options[:model] || st_model_name
|
68
|
+
|
69
|
+
attributes.each do |attr|
|
70
|
+
attr = attr.to_s
|
71
|
+
test "#{brand}should require #{attr} not nil" do
|
72
|
+
assert_no_difference "#{model}.count" do
|
73
|
+
object = create_object(attr.to_sym => nil)
|
74
|
+
assert object.errors.on(attr.to_sym)
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
def assert_should_require_attribute(*attributes)
|
81
|
+
options = attributes.extract_options!
|
82
|
+
model = options[:model] || st_model_name
|
83
|
+
|
84
|
+
attributes.each do |attr|
|
85
|
+
attr = attr.to_s
|
86
|
+
test "#{brand}should require #{attr}" do
|
87
|
+
assert_no_difference "#{model}.count" do
|
88
|
+
object = create_object(attr.to_sym => nil)
|
89
|
+
assert object.errors.on_attr_and_type(attr.to_sym, :blank) ||
|
90
|
+
object.errors.on_attr_and_type(attr.to_sym, :too_short)
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
def assert_should_not_require_attribute(*attributes)
|
97
|
+
options = attributes.extract_options!
|
98
|
+
model = options[:model] || st_model_name
|
99
|
+
|
100
|
+
attributes.each do |attr|
|
101
|
+
attr = attr.to_s
|
102
|
+
test "#{brand}should not require #{attr}" do
|
103
|
+
assert_difference( "#{model}.count", 1 ) do
|
104
|
+
object = create_object(attr.to_sym => nil)
|
105
|
+
assert !object.errors.on(attr.to_sym)
|
106
|
+
if attr =~ /^(.*)_id$/
|
107
|
+
assert !object.errors.on($1.to_sym)
|
108
|
+
end
|
109
|
+
end
|
110
|
+
end
|
111
|
+
end
|
112
|
+
end
|
113
|
+
|
114
|
+
def assert_should_require_attribute_length(*attributes)
|
115
|
+
options = attributes.extract_options!
|
116
|
+
model = options[:model] || st_model_name
|
117
|
+
|
118
|
+
if( ( options.keys & [:in,:within] ).length >= 1 )
|
119
|
+
range = options[:in]||options[:within]
|
120
|
+
options[:minimum] = range.min
|
121
|
+
options[:maximum] = range.max
|
122
|
+
end
|
123
|
+
|
124
|
+
attributes.each do |attr|
|
125
|
+
attr = attr.to_s
|
126
|
+
if options.keys.include?(:is)
|
127
|
+
length = options[:is]
|
128
|
+
test "#{brand}should require exact length of #{length} for #{attr}" do
|
129
|
+
assert_no_difference "#{model}.count" do
|
130
|
+
value = 'x'*(length-1)
|
131
|
+
object = create_object(attr.to_sym => value)
|
132
|
+
assert_equal length-1, object.send(attr.to_sym).length
|
133
|
+
assert_equal object.send(attr.to_sym), value
|
134
|
+
assert object.errors.on_attr_and_type(attr.to_sym, :wrong_length)
|
135
|
+
end
|
136
|
+
assert_no_difference "#{model}.count" do
|
137
|
+
value = 'x'*(length+1)
|
138
|
+
object = create_object(attr.to_sym => value)
|
139
|
+
assert_equal length+1, object.send(attr.to_sym).length
|
140
|
+
assert_equal object.send(attr.to_sym), value
|
141
|
+
assert object.errors.on_attr_and_type(attr.to_sym, :wrong_length)
|
142
|
+
end
|
143
|
+
end
|
144
|
+
end
|
145
|
+
|
146
|
+
if options.keys.include?(:minimum)
|
147
|
+
min = options[:minimum]
|
148
|
+
test "#{brand}should require min length of #{min} for #{attr}" do
|
149
|
+
# because the model may have other requirements
|
150
|
+
# just check to ensure that we don't get a :too_short error
|
151
|
+
# assert_difference "#{model}.count" do
|
152
|
+
value = 'x'*(min)
|
153
|
+
object = create_object(attr.to_sym => value)
|
154
|
+
assert_equal min, object.send(attr.to_sym).length
|
155
|
+
assert_equal object.send(attr.to_sym), value
|
156
|
+
assert !object.errors.on_attr_and_type(attr.to_sym, :too_short)
|
157
|
+
# end
|
158
|
+
assert_no_difference "#{model}.count" do
|
159
|
+
value = 'x'*(min-1)
|
160
|
+
object = create_object(attr.to_sym => value)
|
161
|
+
assert_equal min-1, object.send(attr.to_sym).length
|
162
|
+
assert_equal object.send(attr.to_sym), value
|
163
|
+
assert object.errors.on_attr_and_type(attr.to_sym, :too_short)
|
164
|
+
end
|
165
|
+
end
|
166
|
+
end
|
167
|
+
|
168
|
+
if options.keys.include?(:maximum)
|
169
|
+
max = options[:maximum]
|
170
|
+
test "#{brand}should require max length of #{max} for #{attr}" do
|
171
|
+
# because the model may have other requirements
|
172
|
+
# just check to ensure that we don't get a :too_long error
|
173
|
+
# assert_difference "#{model}.count" do
|
174
|
+
value = 'x'*(max)
|
175
|
+
object = create_object(attr.to_sym => value)
|
176
|
+
assert_equal max, object.send(attr.to_sym).length
|
177
|
+
assert_equal object.send(attr.to_sym), value
|
178
|
+
assert !object.errors.on_attr_and_type(attr.to_sym, :too_long)
|
179
|
+
# end
|
180
|
+
assert_no_difference "#{model}.count" do
|
181
|
+
value = 'x'*(max+1)
|
182
|
+
object = create_object(attr.to_sym => value)
|
183
|
+
assert_equal max+1, object.send(attr.to_sym).length
|
184
|
+
assert_equal object.send(attr.to_sym), value
|
185
|
+
assert object.errors.on_attr_and_type(attr.to_sym, :too_long)
|
186
|
+
end
|
187
|
+
end
|
188
|
+
end
|
189
|
+
|
190
|
+
end
|
191
|
+
end
|
192
|
+
|
193
|
+
def assert_should_protect_attribute(*attributes)
|
194
|
+
options = attributes.extract_options!
|
195
|
+
model_name = options[:model] || st_model_name
|
196
|
+
model = model_name.constantize
|
197
|
+
|
198
|
+
attributes.each do |attr|
|
199
|
+
attr = attr.to_s
|
200
|
+
test "#{brand}should protect attribute #{attr}" do
|
201
|
+
assert model.accessible_attributes||model.protected_attributes,
|
202
|
+
"Both accessible and protected attributes are empty"
|
203
|
+
assert !(model.accessible_attributes||[]).include?(attr),
|
204
|
+
"#{attr} is included in accessible attributes"
|
205
|
+
if !model.protected_attributes.nil?
|
206
|
+
assert model.protected_attributes.include?(attr),
|
207
|
+
"#{attr} is not included in protected attributes"
|
208
|
+
end
|
209
|
+
end
|
210
|
+
end
|
211
|
+
end
|
212
|
+
|
213
|
+
def assert_should_not_protect_attribute(*attributes)
|
214
|
+
options = attributes.extract_options!
|
215
|
+
model_name = options[:model] || st_model_name
|
216
|
+
model = model_name.constantize
|
217
|
+
|
218
|
+
attributes.each do |attr|
|
219
|
+
attr = attr.to_s
|
220
|
+
test "#{brand}should not protect attribute #{attr}" do
|
221
|
+
assert !(model.protected_attributes||[]).include?(attr),
|
222
|
+
"#{attr} is included in protected attributes"
|
223
|
+
if !model.accessible_attributes.nil?
|
224
|
+
assert model.accessible_attributes.include?(attr),
|
225
|
+
"#{attr} is not included in accessible attributes"
|
226
|
+
end
|
227
|
+
end
|
228
|
+
end
|
229
|
+
end
|
230
|
+
|
231
|
+
end
|
232
|
+
|
233
|
+
end # module RailsExtension::Attributes
|
234
|
+
ActiveSupport::TestCase.send(:include,
|
235
|
+
RailsExtension::ActiveSupportExtension::Attributes)
|