gin 1.2.0 → 1.2.1
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.
- data/History.rdoc +9 -0
- data/lib/gin.rb +1 -1
- data/lib/gin/app.rb +7 -0
- data/lib/gin/controller.rb +44 -0
- data/lib/gin/request.rb +32 -6
- data/test/test_controller.rb +103 -0
- data/test/test_request.rb +49 -2
- metadata +3 -3
data/History.rdoc
CHANGED
@@ -1,3 +1,12 @@
|
|
1
|
+
=== 1.2.1 / 2014-03-12
|
2
|
+
|
3
|
+
* Minor Enhancements
|
4
|
+
* Controller.autocast_params to determine if/which params should be typecast
|
5
|
+
* Warn when sprockets isn't found and asset pipeline is enabled
|
6
|
+
|
7
|
+
* Bugfixes
|
8
|
+
* Fix for numeric and boolean param parsing
|
9
|
+
|
1
10
|
=== 1.2.0 / 2013-11-18
|
2
11
|
|
3
12
|
* Major Enhancements
|
data/lib/gin.rb
CHANGED
data/lib/gin/app.rb
CHANGED
@@ -1134,6 +1134,13 @@ class Gin::App
|
|
1134
1134
|
w.run
|
1135
1135
|
w.wait
|
1136
1136
|
end
|
1137
|
+
|
1138
|
+
rescue LoadError => e
|
1139
|
+
raise e unless e =~ /sprockets/
|
1140
|
+
logger << "\nWARNING: #{self.class} asset pipelining is enabled but the \
|
1141
|
+
sprockets gem wasn't found.\nIf you want asset pipelining turned off, add the \
|
1142
|
+
following to your #{self.class} definition:
|
1143
|
+
asset_pipeline false\n\n"
|
1137
1144
|
end
|
1138
1145
|
|
1139
1146
|
|
data/lib/gin/controller.rb
CHANGED
@@ -69,12 +69,14 @@ class Gin::Controller
|
|
69
69
|
|
70
70
|
def self.inherited subclass
|
71
71
|
subclass.setup
|
72
|
+
subclass.autocast_params self.autocast_params
|
72
73
|
super
|
73
74
|
end
|
74
75
|
|
75
76
|
|
76
77
|
def self.setup # :nodoc:
|
77
78
|
@layout = nil
|
79
|
+
@autocast_params = true
|
78
80
|
@ctrl_name = Gin.underscore(self.to_s).gsub(/_?controller_?/,'')
|
79
81
|
end
|
80
82
|
|
@@ -178,6 +180,47 @@ class Gin::Controller
|
|
178
180
|
end
|
179
181
|
|
180
182
|
|
183
|
+
##
|
184
|
+
# Define if params should be cast to autodetected types.
|
185
|
+
# This is an inherited attribute.
|
186
|
+
# * Passing a boolean turns auto-casting on or off for all params.
|
187
|
+
# * Passing a hash with :only or :except limits auto-casting to the
|
188
|
+
# given param names
|
189
|
+
# By default all params are cast to their autodetected types.
|
190
|
+
#
|
191
|
+
# autocast_params true # enabled for all params
|
192
|
+
# autocast_params false # disabled for all params
|
193
|
+
# autocast_params except: [:zip, :phone, :fax]
|
194
|
+
# autocast_params only: [:timestamp, :age]
|
195
|
+
#
|
196
|
+
# Params get cast as follows:
|
197
|
+
# * TrueClass true
|
198
|
+
# * FalseClass: false
|
199
|
+
# * Fixnum: 1234, -1234
|
200
|
+
# * Float: 1.123, -1.123
|
201
|
+
# * String: Everything else, including numbers that start with a 0
|
202
|
+
|
203
|
+
def self.autocast_params arg=nil
|
204
|
+
if Hash === arg && Hash === @autocast_params
|
205
|
+
arg.each do |k, v|
|
206
|
+
if @autocast_params[k]
|
207
|
+
@autocast_params[k] |= [*v]
|
208
|
+
else
|
209
|
+
@autocast_params[k] = [*v]
|
210
|
+
end
|
211
|
+
end
|
212
|
+
|
213
|
+
elsif arg == true || arg == false
|
214
|
+
@autocast_params = arg
|
215
|
+
|
216
|
+
elsif Hash === arg
|
217
|
+
@autocast_params = arg.dup
|
218
|
+
end
|
219
|
+
|
220
|
+
return @autocast_params
|
221
|
+
end
|
222
|
+
|
223
|
+
|
181
224
|
class_rproxy :controller_name, :actions
|
182
225
|
|
183
226
|
# The Gin::App instance used by the controller. The App instance is meant for
|
@@ -203,6 +246,7 @@ class Gin::Controller
|
|
203
246
|
@env = env
|
204
247
|
@request = Gin::Request.new env
|
205
248
|
@response = Gin::Response.new
|
249
|
+
@request.autocast_params = self.class.autocast_params
|
206
250
|
end
|
207
251
|
|
208
252
|
|
data/lib/gin/request.rb
CHANGED
@@ -1,9 +1,13 @@
|
|
1
1
|
class Gin::Request < Rack::Request
|
2
2
|
include Gin::Constants
|
3
3
|
|
4
|
+
attr_accessor :autocast_params # :nodoc:
|
5
|
+
|
4
6
|
def initialize env
|
7
|
+
@params = nil
|
8
|
+
@params_processed = false
|
9
|
+
@autocast_params = true
|
5
10
|
super
|
6
|
-
self.params.update env[GIN_PATH_PARAMS] if env[GIN_PATH_PARAMS]
|
7
11
|
end
|
8
12
|
|
9
13
|
|
@@ -28,7 +32,12 @@ class Gin::Request < Rack::Request
|
|
28
32
|
|
29
33
|
|
30
34
|
def params
|
31
|
-
@params
|
35
|
+
return @params if @params_processed
|
36
|
+
@params = super
|
37
|
+
@params.update @env[GIN_PATH_PARAMS] if @env[GIN_PATH_PARAMS]
|
38
|
+
@params = process_params(@params)
|
39
|
+
@params_processed = true
|
40
|
+
@params
|
32
41
|
end
|
33
42
|
|
34
43
|
|
@@ -45,19 +54,23 @@ class Gin::Request < Rack::Request
|
|
45
54
|
|
46
55
|
private
|
47
56
|
|
48
|
-
M_BOOLEAN = /^true|false$/
|
49
|
-
M_FLOAT = /^-?([
|
50
|
-
M_INTEGER = /^-?([
|
57
|
+
M_BOOLEAN = /^(true|false)$/ #:nodoc:
|
58
|
+
M_FLOAT = /^-?([1-9]\d+|\d)\.\d+$/ #:nodoc:
|
59
|
+
M_INTEGER = /^-?([1-9]\d+|\d)$/ #:nodoc:
|
51
60
|
|
52
61
|
##
|
53
62
|
# Enable string or symbol key access to the nested params hash.
|
54
63
|
# Make String numbers into Numerics.
|
55
64
|
|
56
65
|
def process_params object
|
66
|
+
return object unless @autocast_params
|
67
|
+
|
57
68
|
case object
|
58
69
|
when Hash
|
59
70
|
new_hash = Gin::StrictHash.new
|
60
|
-
object.each
|
71
|
+
object.each do |key, value|
|
72
|
+
new_hash[key] = process_param?(key) ? process_params(value) : value
|
73
|
+
end
|
61
74
|
new_hash
|
62
75
|
when Array
|
63
76
|
object.map { |item| process_params(item) }
|
@@ -71,4 +84,17 @@ class Gin::Request < Rack::Request
|
|
71
84
|
object
|
72
85
|
end
|
73
86
|
end
|
87
|
+
|
88
|
+
|
89
|
+
def process_param? name
|
90
|
+
if Hash === @autocast_params
|
91
|
+
return false if @autocast_params[:except] &&
|
92
|
+
@autocast_params[:except].include?(name.to_sym)
|
93
|
+
|
94
|
+
return @autocast_params[:only].include?(name.to_sym) if
|
95
|
+
@autocast_params[:only]
|
96
|
+
end
|
97
|
+
|
98
|
+
!!@autocast_params
|
99
|
+
end
|
74
100
|
end
|
data/test/test_controller.rb
CHANGED
@@ -132,6 +132,109 @@ class ControllerTest < Test::Unit::TestCase
|
|
132
132
|
end
|
133
133
|
|
134
134
|
|
135
|
+
def test_autocast_params
|
136
|
+
rack_env['QUERY_STRING'] =
|
137
|
+
'id=456&foo=bar&bar=5&bool=true&nbool=truefalse&zip=01234&nint=m3&nflt=01.123&neg=-12&negf=-2.1'
|
138
|
+
|
139
|
+
klass = Class.new(AppController)
|
140
|
+
params = klass.new(@app, rack_env).params
|
141
|
+
|
142
|
+
assert_equal true, params['bool']
|
143
|
+
assert_equal 'truefalse', params['nbool']
|
144
|
+
assert_equal 'bar', params['foo']
|
145
|
+
assert_equal 5, params['bar']
|
146
|
+
assert_equal '01234', params['zip']
|
147
|
+
assert_equal 'm3', params['nint']
|
148
|
+
assert_equal '01.123', params['nflt']
|
149
|
+
assert_equal -12, params['neg']
|
150
|
+
assert_equal -2.1, params['negf']
|
151
|
+
end
|
152
|
+
|
153
|
+
|
154
|
+
def test_autocast_params_off
|
155
|
+
rack_env['QUERY_STRING'] =
|
156
|
+
'id=456&foo=bar&bar=5&bool=true&nbool=truefalse&zip=01234&nint=m3&nflt=01.123&neg=-12&negf=-2.1'
|
157
|
+
|
158
|
+
klass = Class.new(AppController)
|
159
|
+
klass.autocast_params false
|
160
|
+
params = klass.new(@app, rack_env).params
|
161
|
+
|
162
|
+
assert_equal 'true', params['bool']
|
163
|
+
assert_equal 'truefalse', params['nbool']
|
164
|
+
assert_equal 'bar', params['foo']
|
165
|
+
assert_equal '5', params['bar']
|
166
|
+
assert_equal '01234', params['zip']
|
167
|
+
assert_equal 'm3', params['nint']
|
168
|
+
assert_equal '01.123', params['nflt']
|
169
|
+
assert_equal '-12', params['neg']
|
170
|
+
assert_equal '-2.1', params['negf']
|
171
|
+
end
|
172
|
+
|
173
|
+
|
174
|
+
def test_autocast_params_only
|
175
|
+
rack_env['QUERY_STRING'] =
|
176
|
+
'foo=bar&bar=5&bool=true&nbool=truefalse&zip=01234&nint=m3&nflt=01.123&neg=-12&negf=-2.1'
|
177
|
+
|
178
|
+
klass = Class.new(AppController)
|
179
|
+
klass.autocast_params :only => [:bool, :bar, :zip]
|
180
|
+
params = klass.new(@app, rack_env).params
|
181
|
+
|
182
|
+
assert_equal true, params['bool']
|
183
|
+
assert_equal 'truefalse', params['nbool']
|
184
|
+
assert_equal 'bar', params['foo']
|
185
|
+
assert_equal 5, params['bar']
|
186
|
+
assert_equal '01234', params['zip']
|
187
|
+
assert_equal 'm3', params['nint']
|
188
|
+
assert_equal '01.123', params['nflt']
|
189
|
+
assert_equal '-12', params['neg']
|
190
|
+
assert_equal '-2.1', params['negf']
|
191
|
+
end
|
192
|
+
|
193
|
+
|
194
|
+
def test_autocast_params_except
|
195
|
+
rack_env['QUERY_STRING'] =
|
196
|
+
'id=456&foo=bar&bar=5&bool=true&nbool=truefalse&zip=01234&nint=m3&nflt=01.123&neg=-12&negf=-2.1'
|
197
|
+
|
198
|
+
klass = Class.new(AppController)
|
199
|
+
klass.autocast_params :except => [:bool, :bar, :zip]
|
200
|
+
params = klass.new(@app, rack_env).params
|
201
|
+
|
202
|
+
assert_equal 'true', params['bool']
|
203
|
+
assert_equal 'truefalse', params['nbool']
|
204
|
+
assert_equal 'bar', params['foo']
|
205
|
+
assert_equal '5', params['bar']
|
206
|
+
assert_equal '01234', params['zip']
|
207
|
+
assert_equal 'm3', params['nint']
|
208
|
+
assert_equal '01.123', params['nflt']
|
209
|
+
assert_equal -12, params['neg']
|
210
|
+
assert_equal -2.1, params['negf']
|
211
|
+
end
|
212
|
+
|
213
|
+
|
214
|
+
def test_autocast_params_inherit
|
215
|
+
rack_env['QUERY_STRING'] =
|
216
|
+
'foo=bar&bar=5&bool=true&nbool=truefalse&zip=01234&nint=m3&nflt=01.123&neg=-12&negf=-2.1'
|
217
|
+
|
218
|
+
klass = Class.new(AppController)
|
219
|
+
klass.autocast_params :only => [:bool, :bar, :zip]
|
220
|
+
|
221
|
+
subklass = Class.new(klass)
|
222
|
+
subklass.autocast_params :only => :neg
|
223
|
+
|
224
|
+
params = klass.new(@app, rack_env).params
|
225
|
+
|
226
|
+
assert_equal true, params['bool']
|
227
|
+
assert_equal 5, params['bar']
|
228
|
+
assert_equal '-12', params['neg']
|
229
|
+
|
230
|
+
params = subklass.new(@app, rack_env).params
|
231
|
+
|
232
|
+
assert_equal true, params['bool']
|
233
|
+
assert_equal 5, params['bar']
|
234
|
+
assert_equal -12, params['neg']
|
235
|
+
end
|
236
|
+
|
237
|
+
|
135
238
|
def test_class_layout
|
136
239
|
assert_equal :foo, BarController.layout
|
137
240
|
assert_equal :foo, AppController.layout
|
data/test/test_request.rb
CHANGED
@@ -7,8 +7,8 @@ class RequestTest < Test::Unit::TestCase
|
|
7
7
|
'HTTP_HOST' => 'example.com',
|
8
8
|
'rack.input' => '',
|
9
9
|
'QUERY_STRING' =>
|
10
|
-
'id=456&foo=bar&bar=5&bool=true&zip=01234&nflt=01.123&neg=-12&negf=-2.1',
|
11
|
-
'gin.path_query_hash' => {'id' => 123},
|
10
|
+
'id=456&foo=bar&bar=5&bool=true&nbool=truefalse&zip=01234&nint=m3&nflt=01.123&neg=-12&negf=-2.1',
|
11
|
+
'gin.path_query_hash' => {'id' => 123, 'age' => '22'},
|
12
12
|
}
|
13
13
|
@req = Gin::Request.new @env
|
14
14
|
end
|
@@ -16,9 +16,55 @@ class RequestTest < Test::Unit::TestCase
|
|
16
16
|
|
17
17
|
def test_query_hash_as_param
|
18
18
|
assert_equal 123, @req.params['id']
|
19
|
+
assert_equal 22, @req.params['age']
|
20
|
+
assert_equal true, @req.params['bool']
|
21
|
+
assert_equal 'truefalse', @req.params['nbool']
|
19
22
|
assert_equal 'bar', @req.params['foo']
|
20
23
|
assert_equal 5, @req.params['bar']
|
21
24
|
assert_equal '01234', @req.params['zip']
|
25
|
+
assert_equal 'm3', @req.params['nint']
|
26
|
+
assert_equal '01.123', @req.params['nflt']
|
27
|
+
assert_equal -12, @req.params['neg']
|
28
|
+
assert_equal -2.1, @req.params['negf']
|
29
|
+
end
|
30
|
+
|
31
|
+
|
32
|
+
def test_query_hash_as_param_w_autocast_off
|
33
|
+
@req.autocast_params = false
|
34
|
+
assert_equal '22', @req.params['age']
|
35
|
+
assert_equal 'true', @req.params['bool']
|
36
|
+
assert_equal 'bar', @req.params['foo']
|
37
|
+
assert_equal '5', @req.params['bar']
|
38
|
+
assert_equal '01234', @req.params['zip']
|
39
|
+
assert_equal 'm3', @req.params['nint']
|
40
|
+
assert_equal '01.123', @req.params['nflt']
|
41
|
+
assert_equal '-12', @req.params['neg']
|
42
|
+
assert_equal '-2.1', @req.params['negf']
|
43
|
+
end
|
44
|
+
|
45
|
+
|
46
|
+
def test_query_hash_as_param_w_autocast_only
|
47
|
+
@req.autocast_params = {:only => [:age, :bool, :zip]}
|
48
|
+
assert_equal 22, @req.params['age']
|
49
|
+
assert_equal true, @req.params['bool']
|
50
|
+
assert_equal 'bar', @req.params['foo']
|
51
|
+
assert_equal '5', @req.params['bar']
|
52
|
+
assert_equal '01234', @req.params['zip']
|
53
|
+
assert_equal 'm3', @req.params['nint']
|
54
|
+
assert_equal '01.123', @req.params['nflt']
|
55
|
+
assert_equal '-12', @req.params['neg']
|
56
|
+
assert_equal '-2.1', @req.params['negf']
|
57
|
+
end
|
58
|
+
|
59
|
+
|
60
|
+
def test_query_hash_as_param_w_autocast_except
|
61
|
+
@req.autocast_params = {:except => [:age, :bool, :zip]}
|
62
|
+
assert_equal '22', @req.params['age']
|
63
|
+
assert_equal 'true', @req.params['bool']
|
64
|
+
assert_equal 'bar', @req.params['foo']
|
65
|
+
assert_equal 5, @req.params['bar']
|
66
|
+
assert_equal '01234', @req.params['zip']
|
67
|
+
assert_equal 'm3', @req.params['nint']
|
22
68
|
assert_equal '01.123', @req.params['nflt']
|
23
69
|
assert_equal -12, @req.params['neg']
|
24
70
|
assert_equal -2.1, @req.params['negf']
|
@@ -74,6 +120,7 @@ class RequestTest < Test::Unit::TestCase
|
|
74
120
|
assert_equal false, @req.send(:process_params, "false")
|
75
121
|
assert_equal 1, @req.send(:process_params, "1")
|
76
122
|
assert_equal 1.1, @req.send(:process_params, "1.1")
|
123
|
+
assert_equal "w1", @req.send(:process_params, "w1")
|
77
124
|
assert_equal "not_true", @req.send(:process_params, "not_true")
|
78
125
|
|
79
126
|
ary = @req.send(:process_params, ["true", "1", "foo"])
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: gin
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.2.
|
4
|
+
version: 1.2.1
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date:
|
12
|
+
date: 2014-03-13 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: rack
|
@@ -232,7 +232,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
232
232
|
version: '0'
|
233
233
|
segments:
|
234
234
|
- 0
|
235
|
-
hash: -
|
235
|
+
hash: -1291900085741485412
|
236
236
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
237
237
|
none: false
|
238
238
|
requirements:
|