rack 1.1.6 → 1.2.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of rack might be problematic. Click here for more details.
- data/README +9 -205
- data/SPEC +3 -3
- data/lib/rack.rb +1 -24
- data/lib/rack/auth/abstract/request.rb +1 -5
- data/lib/rack/auth/digest/md5.rb +1 -2
- data/lib/rack/auth/digest/params.rb +1 -1
- data/lib/rack/content_length.rb +1 -1
- data/lib/rack/etag.rb +15 -6
- data/lib/rack/file.rb +3 -1
- data/lib/rack/handler/cgi.rb +8 -7
- data/lib/rack/handler/fastcgi.rb +1 -1
- data/lib/rack/handler/lsws.rb +1 -1
- data/lib/rack/handler/mongrel.rb +1 -1
- data/lib/rack/handler/scgi.rb +1 -4
- data/lib/rack/handler/webrick.rb +10 -6
- data/lib/rack/lint.rb +29 -37
- data/lib/rack/mime.rb +2 -0
- data/lib/rack/mock.rb +2 -1
- data/lib/rack/recursive.rb +4 -0
- data/lib/rack/request.rb +8 -6
- data/lib/rack/response.rb +1 -0
- data/lib/rack/rewindable_input.rb +13 -10
- data/lib/rack/sendfile.rb +8 -6
- data/lib/rack/server.rb +68 -9
- data/lib/rack/session/cookie.rb +1 -10
- data/lib/rack/session/memcache.rb +1 -1
- data/lib/rack/urlmap.rb +6 -7
- data/lib/rack/utils.rb +40 -71
- data/rack.gemspec +7 -11
- data/spec/cgi/lighttpd.conf +25 -0
- data/spec/cgi/rackup_stub.rb +6 -0
- data/spec/cgi/sample_rackup.ru +5 -0
- data/spec/cgi/test +9 -0
- data/spec/cgi/test.fcgi +8 -0
- data/spec/cgi/test.ru +5 -0
- data/spec/multipart/bad_robots +259 -0
- data/spec/multipart/binary +0 -0
- data/spec/multipart/empty +10 -0
- data/spec/multipart/fail_16384_nofile +814 -0
- data/spec/multipart/file1.txt +1 -0
- data/spec/multipart/filename_and_modification_param +7 -0
- data/spec/multipart/filename_with_escaped_quotes +6 -0
- data/spec/multipart/filename_with_escaped_quotes_and_modification_param +7 -0
- data/spec/multipart/filename_with_percent_escaped_quotes +6 -0
- data/spec/multipart/filename_with_unescaped_quotes +6 -0
- data/spec/multipart/ie +6 -0
- data/spec/multipart/nested +10 -0
- data/spec/multipart/none +9 -0
- data/spec/multipart/semicolon +6 -0
- data/spec/multipart/text +10 -0
- data/spec/rackup/config.ru +31 -0
- data/{test/spec_rack_auth_basic.rb → spec/spec_auth_basic.rb} +11 -14
- data/{test/spec_rack_auth_digest.rb → spec/spec_auth_digest.rb} +18 -27
- data/{test/spec_rack_builder.rb → spec/spec_builder.rb} +49 -10
- data/{test/spec_rack_cascade.rb → spec/spec_cascade.rb} +7 -10
- data/{test/spec_rack_cgi.rb → spec/spec_cgi.rb} +34 -32
- data/{test/spec_rack_chunked.rb → spec/spec_chunked.rb} +8 -10
- data/{test/spec_rack_commonlogger.rb → spec/spec_commonlogger.rb} +10 -15
- data/{test/spec_rack_conditionalget.rb → spec/spec_conditionalget.rb} +5 -7
- data/{test/spec_rack_config.rb → spec/spec_config.rb} +6 -7
- data/{test/spec_rack_content_length.rb → spec/spec_content_length.rb} +7 -8
- data/{test/spec_rack_content_type.rb → spec/spec_content_type.rb} +5 -6
- data/{test/spec_rack_deflater.rb → spec/spec_deflater.rb} +11 -13
- data/{test/spec_rack_directory.rb → spec/spec_directory.rb} +6 -10
- data/{test/spec_rack_etag.rb → spec/spec_etag.rb} +3 -5
- data/{test/spec_rack_fastcgi.rb → spec/spec_fastcgi.rb} +36 -29
- data/{test/spec_rack_file.rb → spec/spec_file.rb} +9 -13
- data/{test/spec_rack_handler.rb → spec/spec_handler.rb} +10 -12
- data/{test/spec_rack_head.rb → spec/spec_head.rb} +3 -3
- data/{test/spec_rack_lint.rb → spec/spec_lint.rb} +19 -32
- data/{test/spec_rack_lobster.rb → spec/spec_lobster.rb} +9 -11
- data/{test/spec_rack_lock.rb → spec/spec_lock.rb} +15 -17
- data/{test/spec_rack_logger.rb → spec/spec_logger.rb} +6 -7
- data/{test/spec_rack_methodoverride.rb → spec/spec_methodoverride.rb} +15 -17
- data/{test/spec_rack_mock.rb → spec/spec_mock.rb} +30 -32
- data/{test/spec_rack_mongrel.rb → spec/spec_mongrel.rb} +40 -46
- data/{test/spec_rack_nulllogger.rb → spec/spec_nulllogger.rb} +4 -5
- data/{test/spec_rack_recursive.rb → spec/spec_recursive.rb} +28 -36
- data/{test/spec_rack_request.rb → spec/spec_request.rb} +84 -98
- data/{test/spec_rack_response.rb → spec/spec_response.rb} +46 -27
- data/spec/spec_rewindable_input.rb +118 -0
- data/{test/spec_rack_runtime.rb → spec/spec_runtime.rb} +15 -11
- data/{test/spec_rack_sendfile.rb → spec/spec_sendfile.rb} +11 -14
- data/{test/spec_rack_session_cookie.rb → spec/spec_session_cookie.rb} +14 -36
- data/{test/spec_rack_session_memcache.rb → spec/spec_session_memcache.rb} +32 -26
- data/{test/spec_rack_session_pool.rb → spec/spec_session_pool.rb} +36 -31
- data/spec/spec_showexceptions.rb +23 -0
- data/spec/spec_showstatus.rb +79 -0
- data/{test/spec_rack_static.rb → spec/spec_static.rb} +5 -9
- data/{test/spec_rack_thin.rb → spec/spec_thin.rb} +30 -35
- data/{test/spec_rack_urlmap.rb → spec/spec_urlmap.rb} +6 -8
- data/{test/spec_rack_utils.rb → spec/spec_utils.rb} +134 -74
- data/{test/spec_rack_webrick.rb → spec/spec_webrick.rb} +28 -36
- data/spec/testrequest.rb +77 -0
- data/spec/unregistered_handler/rack/handler/unregistered.rb +7 -0
- data/spec/unregistered_handler/rack/handler/unregistered_long_one.rb +7 -0
- metadata +176 -191
- data/RDOX +0 -0
- data/lib/rack/adapter/camping.rb +0 -22
- data/test/spec_auth.rb +0 -57
- data/test/spec_rack_camping.rb +0 -55
- data/test/spec_rack_rewindable_input.rb +0 -118
- data/test/spec_rack_showexceptions.rb +0 -21
- data/test/spec_rack_showstatus.rb +0 -72
- data/test/spec_rackup.rb +0 -164
@@ -1,13 +1,12 @@
|
|
1
1
|
require 'rack/nulllogger'
|
2
|
-
require 'rack/lint'
|
3
|
-
require 'rack/mock'
|
4
2
|
|
5
|
-
|
6
|
-
|
3
|
+
describe Rack::NullLogger do
|
4
|
+
should "act as a noop logger" do
|
7
5
|
app = lambda { |env|
|
8
6
|
env['rack.logger'].warn "b00m"
|
9
7
|
[200, {'Content-Type' => 'text/plain'}, ["Hello, World!"]]
|
10
8
|
}
|
11
|
-
Rack::NullLogger.new(app)
|
9
|
+
logger = Rack::NullLogger.new(app)
|
10
|
+
lambda{ logger.call({}) }.should.not.raise
|
12
11
|
end
|
13
12
|
end
|
@@ -1,53 +1,45 @@
|
|
1
|
-
require 'test/spec'
|
2
|
-
|
3
1
|
require 'rack/recursive'
|
4
|
-
require 'rack/urlmap'
|
5
|
-
require 'rack/response'
|
6
2
|
require 'rack/mock'
|
7
3
|
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
end
|
18
|
-
}
|
4
|
+
describe Rack::Recursive do
|
5
|
+
@app1 = lambda { |env|
|
6
|
+
res = Rack::Response.new
|
7
|
+
res["X-Path-Info"] = env["PATH_INFO"]
|
8
|
+
res["X-Query-String"] = env["QUERY_STRING"]
|
9
|
+
res.finish do |inner_res|
|
10
|
+
inner_res.write "App1"
|
11
|
+
end
|
12
|
+
}
|
19
13
|
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
14
|
+
@app2 = lambda { |env|
|
15
|
+
Rack::Response.new.finish do |res|
|
16
|
+
res.write "App2"
|
17
|
+
_, _, body = env['rack.recursive.include'].call(env, "/app1")
|
18
|
+
body.each { |b|
|
19
|
+
res.write b
|
20
|
+
}
|
21
|
+
end
|
22
|
+
}
|
29
23
|
|
30
|
-
|
31
|
-
|
32
|
-
|
24
|
+
@app3 = lambda { |env|
|
25
|
+
raise Rack::ForwardRequest.new("/app1")
|
26
|
+
}
|
33
27
|
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
end
|
28
|
+
@app4 = lambda { |env|
|
29
|
+
raise Rack::ForwardRequest.new("http://example.org/app1/quux?meh")
|
30
|
+
}
|
39
31
|
|
40
|
-
|
32
|
+
should "allow for subrequests" do
|
41
33
|
res = Rack::MockRequest.new(Rack::Recursive.new(
|
42
34
|
Rack::URLMap.new("/app1" => @app1,
|
43
35
|
"/app2" => @app2))).
|
44
36
|
get("/app2")
|
45
37
|
|
46
38
|
res.should.be.ok
|
47
|
-
res.body.should.equal "App2App1"
|
39
|
+
res.body.should.equal "App2App1"
|
48
40
|
end
|
49
41
|
|
50
|
-
|
42
|
+
should "raise error on requests not below the app" do
|
51
43
|
app = Rack::URLMap.new("/app1" => @app1,
|
52
44
|
"/app" => Rack::Recursive.new(
|
53
45
|
Rack::URLMap.new("/1" => @app1,
|
@@ -59,7 +51,7 @@ context "Rack::Recursive" do
|
|
59
51
|
message.should =~ /can only include below/
|
60
52
|
end
|
61
53
|
|
62
|
-
|
54
|
+
should "support forwarding" do
|
63
55
|
app = Rack::Recursive.new(Rack::URLMap.new("/app1" => @app1,
|
64
56
|
"/app3" => @app3,
|
65
57
|
"/app4" => @app4))
|
@@ -1,11 +1,10 @@
|
|
1
|
-
require 'test/spec'
|
2
1
|
require 'stringio'
|
3
|
-
|
2
|
+
require 'cgi'
|
4
3
|
require 'rack/request'
|
5
4
|
require 'rack/mock'
|
6
5
|
|
7
|
-
|
8
|
-
|
6
|
+
describe Rack::Request do
|
7
|
+
should "wrap the rack variables" do
|
9
8
|
req = Rack::Request.new(Rack::MockRequest.env_for("http://example.com:8080/"))
|
10
9
|
|
11
10
|
req.body.should.respond_to? :gets
|
@@ -29,7 +28,7 @@ context "Rack::Request" do
|
|
29
28
|
req.content_type.should.be.nil
|
30
29
|
end
|
31
30
|
|
32
|
-
|
31
|
+
should "figure out the correct host" do
|
33
32
|
req = Rack::Request.new \
|
34
33
|
Rack::MockRequest.env_for("/", "HTTP_HOST" => "www2.example.org")
|
35
34
|
req.host.should.equal "www2.example.org"
|
@@ -53,7 +52,7 @@ context "Rack::Request" do
|
|
53
52
|
req.host.should.equal ""
|
54
53
|
end
|
55
54
|
|
56
|
-
|
55
|
+
should "parse the query string" do
|
57
56
|
req = Rack::Request.new(Rack::MockRequest.env_for("/?foo=bar&quux=bla"))
|
58
57
|
req.query_string.should.equal "foo=bar&quux=bla"
|
59
58
|
req.GET.should.equal "foo" => "bar", "quux" => "bla"
|
@@ -61,12 +60,12 @@ context "Rack::Request" do
|
|
61
60
|
req.params.should.equal "foo" => "bar", "quux" => "bla"
|
62
61
|
end
|
63
62
|
|
64
|
-
|
63
|
+
should "raise if rack.input is missing" do
|
65
64
|
req = Rack::Request.new({})
|
66
65
|
lambda { req.POST }.should.raise(RuntimeError)
|
67
66
|
end
|
68
67
|
|
69
|
-
|
68
|
+
should "parse POST data when method is POST and no Content-Type given" do
|
70
69
|
req = Rack::Request.new \
|
71
70
|
Rack::MockRequest.env_for("/?foo=quux",
|
72
71
|
"REQUEST_METHOD" => 'POST',
|
@@ -79,33 +78,7 @@ context "Rack::Request" do
|
|
79
78
|
req.params.should.equal "foo" => "bar", "quux" => "bla"
|
80
79
|
end
|
81
80
|
|
82
|
-
|
83
|
-
env = Rack::MockRequest.env_for("/?foo=bar")
|
84
|
-
|
85
|
-
old, Rack::Utils.key_space_limit = Rack::Utils.key_space_limit, 1
|
86
|
-
begin
|
87
|
-
req = Rack::Request.new(env)
|
88
|
-
lambda { req.GET }.should.raise(RangeError)
|
89
|
-
ensure
|
90
|
-
Rack::Utils.key_space_limit = old
|
91
|
-
end
|
92
|
-
end
|
93
|
-
|
94
|
-
specify "limit the keys from the POST form data" do
|
95
|
-
env = Rack::MockRequest.env_for("",
|
96
|
-
"REQUEST_METHOD" => 'POST',
|
97
|
-
:input => "foo=bar&quux=bla")
|
98
|
-
|
99
|
-
old, Rack::Utils.key_space_limit = Rack::Utils.key_space_limit, 1
|
100
|
-
begin
|
101
|
-
req = Rack::Request.new(env)
|
102
|
-
lambda { req.POST }.should.raise(RangeError)
|
103
|
-
ensure
|
104
|
-
Rack::Utils.key_space_limit = old
|
105
|
-
end
|
106
|
-
end
|
107
|
-
|
108
|
-
specify "can parse POST data with explicit content type regardless of method" do
|
81
|
+
should "parse POST data with explicit content type regardless of method" do
|
109
82
|
req = Rack::Request.new \
|
110
83
|
Rack::MockRequest.env_for("/",
|
111
84
|
"CONTENT_TYPE" => 'application/x-www-form-urlencoded;foo=bar',
|
@@ -117,7 +90,7 @@ context "Rack::Request" do
|
|
117
90
|
req.params.should.equal "foo" => "bar", "quux" => "bla"
|
118
91
|
end
|
119
92
|
|
120
|
-
|
93
|
+
should "not parse POST data when media type is not form-data" do
|
121
94
|
req = Rack::Request.new \
|
122
95
|
Rack::MockRequest.env_for("/?foo=quux",
|
123
96
|
"REQUEST_METHOD" => 'POST',
|
@@ -131,7 +104,7 @@ context "Rack::Request" do
|
|
131
104
|
req.body.read.should.equal "foo=bar&quux=bla"
|
132
105
|
end
|
133
106
|
|
134
|
-
|
107
|
+
should "parse POST data on PUT when media type is form-data" do
|
135
108
|
req = Rack::Request.new \
|
136
109
|
Rack::MockRequest.env_for("/?foo=quux",
|
137
110
|
"REQUEST_METHOD" => 'PUT',
|
@@ -141,7 +114,7 @@ context "Rack::Request" do
|
|
141
114
|
req.body.read.should.equal "foo=bar&quux=bla"
|
142
115
|
end
|
143
116
|
|
144
|
-
|
117
|
+
should "rewind input after parsing POST data" do
|
145
118
|
input = StringIO.new("foo=bar&quux=bla")
|
146
119
|
req = Rack::Request.new \
|
147
120
|
Rack::MockRequest.env_for("/",
|
@@ -151,21 +124,21 @@ context "Rack::Request" do
|
|
151
124
|
input.read.should.equal "foo=bar&quux=bla"
|
152
125
|
end
|
153
126
|
|
154
|
-
|
127
|
+
should "clean up Safari's ajax POST body" do
|
155
128
|
req = Rack::Request.new \
|
156
129
|
Rack::MockRequest.env_for("/",
|
157
130
|
'REQUEST_METHOD' => 'POST', :input => "foo=bar&quux=bla\0")
|
158
131
|
req.POST.should.equal "foo" => "bar", "quux" => "bla"
|
159
132
|
end
|
160
133
|
|
161
|
-
|
134
|
+
should "get value by key from params with #[]" do
|
162
135
|
req = Rack::Request.new \
|
163
136
|
Rack::MockRequest.env_for("?foo=quux")
|
164
137
|
req['foo'].should.equal 'quux'
|
165
138
|
req[:foo].should.equal 'quux'
|
166
139
|
end
|
167
140
|
|
168
|
-
|
141
|
+
should "set value to key on params with #[]=" do
|
169
142
|
req = Rack::Request.new \
|
170
143
|
Rack::MockRequest.env_for("?foo=duh")
|
171
144
|
req['foo'].should.equal 'duh'
|
@@ -183,7 +156,7 @@ context "Rack::Request" do
|
|
183
156
|
req[:foo].should.equal 'jaz'
|
184
157
|
end
|
185
158
|
|
186
|
-
|
159
|
+
should "return values for the keys in the order given from values_at" do
|
187
160
|
req = Rack::Request.new \
|
188
161
|
Rack::MockRequest.env_for("?foo=baz&wun=der&bar=ful")
|
189
162
|
req.values_at('foo').should.equal ['baz']
|
@@ -191,7 +164,7 @@ context "Rack::Request" do
|
|
191
164
|
req.values_at('bar', 'foo', 'wun').should.equal ['ful', 'baz', 'der']
|
192
165
|
end
|
193
166
|
|
194
|
-
|
167
|
+
should "extract referrer correctly" do
|
195
168
|
req = Rack::Request.new \
|
196
169
|
Rack::MockRequest.env_for("/", "HTTP_REFERER" => "/some/path")
|
197
170
|
req.referer.should.equal "/some/path"
|
@@ -201,7 +174,7 @@ context "Rack::Request" do
|
|
201
174
|
req.referer.should.equal "/"
|
202
175
|
end
|
203
176
|
|
204
|
-
|
177
|
+
should "extract user agent correctly" do
|
205
178
|
req = Rack::Request.new \
|
206
179
|
Rack::MockRequest.env_for("/", "HTTP_USER_AGENT" => "Mozilla/4.0 (compatible)")
|
207
180
|
req.user_agent.should.equal "Mozilla/4.0 (compatible)"
|
@@ -211,7 +184,7 @@ context "Rack::Request" do
|
|
211
184
|
req.user_agent.should.equal nil
|
212
185
|
end
|
213
186
|
|
214
|
-
|
187
|
+
should "cache, but invalidates the cache" do
|
215
188
|
req = Rack::Request.new \
|
216
189
|
Rack::MockRequest.env_for("/?foo=quux",
|
217
190
|
"CONTENT_TYPE" => "application/x-www-form-urlencoded",
|
@@ -229,7 +202,7 @@ context "Rack::Request" do
|
|
229
202
|
req.POST.should.equal "foo" => "bla", "quux" => "bar"
|
230
203
|
end
|
231
204
|
|
232
|
-
|
205
|
+
should "figure out if called via XHR" do
|
233
206
|
req = Rack::Request.new(Rack::MockRequest.env_for(""))
|
234
207
|
req.should.not.be.xhr
|
235
208
|
|
@@ -238,7 +211,7 @@ context "Rack::Request" do
|
|
238
211
|
req.should.be.xhr
|
239
212
|
end
|
240
213
|
|
241
|
-
|
214
|
+
should "parse cookies" do
|
242
215
|
req = Rack::Request.new \
|
243
216
|
Rack::MockRequest.env_for("", "HTTP_COOKIE" => "foo=bar;quux=h&m")
|
244
217
|
req.cookies.should.equal "foo" => "bar", "quux" => "h&m"
|
@@ -247,13 +220,13 @@ context "Rack::Request" do
|
|
247
220
|
req.cookies.should.equal({})
|
248
221
|
end
|
249
222
|
|
250
|
-
|
223
|
+
should "parse cookies according to RFC 2109" do
|
251
224
|
req = Rack::Request.new \
|
252
225
|
Rack::MockRequest.env_for('', 'HTTP_COOKIE' => 'foo=bar;foo=car')
|
253
226
|
req.cookies.should.equal 'foo' => 'bar'
|
254
227
|
end
|
255
228
|
|
256
|
-
|
229
|
+
should "provide setters" do
|
257
230
|
req = Rack::Request.new(e=Rack::MockRequest.env_for(""))
|
258
231
|
req.script_name.should.equal ""
|
259
232
|
req.script_name = "/foo"
|
@@ -266,12 +239,12 @@ context "Rack::Request" do
|
|
266
239
|
e["PATH_INFO"].should.equal "/foo"
|
267
240
|
end
|
268
241
|
|
269
|
-
|
270
|
-
req = Rack::Request.new(e=Rack::MockRequest.env_for(""))
|
271
|
-
req.env.should
|
242
|
+
should "provide the original env" do
|
243
|
+
req = Rack::Request.new(e = Rack::MockRequest.env_for(""))
|
244
|
+
req.env.should == e
|
272
245
|
end
|
273
246
|
|
274
|
-
|
247
|
+
should "restore the URL" do
|
275
248
|
Rack::Request.new(Rack::MockRequest.env_for("")).url.
|
276
249
|
should.equal "http://example.org/"
|
277
250
|
Rack::Request.new(Rack::MockRequest.env_for("", "SCRIPT_NAME" => "/foo")).url.
|
@@ -289,7 +262,7 @@ context "Rack::Request" do
|
|
289
262
|
should.equal "https://example.com:8080/foo?foo"
|
290
263
|
end
|
291
264
|
|
292
|
-
|
265
|
+
should "restore the full path" do
|
293
266
|
Rack::Request.new(Rack::MockRequest.env_for("")).fullpath.
|
294
267
|
should.equal "/"
|
295
268
|
Rack::Request.new(Rack::MockRequest.env_for("", "SCRIPT_NAME" => "/foo")).fullpath.
|
@@ -307,7 +280,7 @@ context "Rack::Request" do
|
|
307
280
|
should.equal "/foo?foo"
|
308
281
|
end
|
309
282
|
|
310
|
-
|
283
|
+
should "handle multiple media type parameters" do
|
311
284
|
req = Rack::Request.new \
|
312
285
|
Rack::MockRequest.env_for("/",
|
313
286
|
"CONTENT_TYPE" => 'text/plain; foo=BAR,baz=bizzle dizzle;BLING=bam')
|
@@ -321,30 +294,7 @@ context "Rack::Request" do
|
|
321
294
|
req.media_type_params['bling'].should.equal 'bam'
|
322
295
|
end
|
323
296
|
|
324
|
-
|
325
|
-
input = <<EOF
|
326
|
-
--AaB03x\r
|
327
|
-
Content-Disposition: form-data; name="text"\r
|
328
|
-
Content-Type: text/plain; charset=US-ASCII\r
|
329
|
-
\r
|
330
|
-
contents\r
|
331
|
-
--AaB03x--\r
|
332
|
-
EOF
|
333
|
-
|
334
|
-
env = Rack::MockRequest.env_for("/",
|
335
|
-
"CONTENT_TYPE" => "multipart/form-data, boundary=AaB03x",
|
336
|
-
"CONTENT_LENGTH" => input.size,
|
337
|
-
:input => input)
|
338
|
-
|
339
|
-
old, Rack::Utils.key_space_limit = Rack::Utils.key_space_limit, 1
|
340
|
-
begin
|
341
|
-
lambda { Rack::Utils::Multipart.parse_multipart(env) }.should.raise(RangeError)
|
342
|
-
ensure
|
343
|
-
Rack::Utils.key_space_limit = old
|
344
|
-
end
|
345
|
-
end
|
346
|
-
|
347
|
-
specify "can parse multipart form data" do
|
297
|
+
should "parse multipart form data" do
|
348
298
|
# Adapted from RFC 1867.
|
349
299
|
input = <<EOF
|
350
300
|
--AaB03x\r
|
@@ -383,7 +333,7 @@ EOF
|
|
383
333
|
f[:tempfile].size.should.equal 76
|
384
334
|
end
|
385
335
|
|
386
|
-
|
336
|
+
should "parse big multipart form data" do
|
387
337
|
input = <<EOF
|
388
338
|
--AaB03x\r
|
389
339
|
content-disposition: form-data; name="huge"; filename="huge"\r
|
@@ -405,7 +355,7 @@ EOF
|
|
405
355
|
req.POST["mean"][:tempfile].read.should.equal "--AaB03xha"
|
406
356
|
end
|
407
357
|
|
408
|
-
|
358
|
+
should "detect invalid multipart form data" do
|
409
359
|
input = <<EOF
|
410
360
|
--AaB03x\r
|
411
361
|
content-disposition: form-data; name="huge"; filename="huge"\r
|
@@ -444,12 +394,33 @@ EOF
|
|
444
394
|
lambda { req.POST }.should.raise(EOFError)
|
445
395
|
end
|
446
396
|
|
447
|
-
|
448
|
-
|
449
|
-
|
450
|
-
|
397
|
+
should "not try to interpret binary as utf8" do
|
398
|
+
if /regexp/.respond_to?(:kcode) # < 1.9
|
399
|
+
begin
|
400
|
+
original_kcode = $KCODE
|
401
|
+
$KCODE='UTF8'
|
402
|
+
|
403
|
+
input = <<EOF
|
404
|
+
--AaB03x\r
|
405
|
+
content-disposition: form-data; name="fileupload"; filename="junk.a"\r
|
406
|
+
content-type: application/octet-stream\r
|
407
|
+
\r
|
408
|
+
#{[0x36,0xCF,0x0A,0xF8].pack('c*')}\r
|
409
|
+
--AaB03x--\r
|
410
|
+
EOF
|
451
411
|
|
452
|
-
|
412
|
+
req = Rack::Request.new Rack::MockRequest.env_for("/",
|
413
|
+
"CONTENT_TYPE" => "multipart/form-data, boundary=AaB03x",
|
414
|
+
"CONTENT_LENGTH" => input.size,
|
415
|
+
:input => input)
|
416
|
+
|
417
|
+
lambda{req.POST}.should.not.raise(EOFError)
|
418
|
+
req.POST["fileupload"][:tempfile].size.should.equal 4
|
419
|
+
ensure
|
420
|
+
$KCODE = original_kcode
|
421
|
+
end
|
422
|
+
else # >= 1.9
|
423
|
+
input = <<EOF
|
453
424
|
--AaB03x\r
|
454
425
|
content-disposition: form-data; name="fileupload"; filename="junk.a"\r
|
455
426
|
content-type: application/octet-stream\r
|
@@ -465,13 +436,10 @@ EOF
|
|
465
436
|
|
466
437
|
lambda{req.POST}.should.not.raise(EOFError)
|
467
438
|
req.POST["fileupload"][:tempfile].size.should.equal 4
|
468
|
-
ensure
|
469
|
-
$KCODE = original_kcode
|
470
439
|
end
|
471
440
|
end
|
472
441
|
|
473
|
-
|
474
|
-
specify "should work around buggy 1.8.* Tempfile equality" do
|
442
|
+
should "work around buggy 1.8.* Tempfile equality" do
|
475
443
|
input = <<EOF
|
476
444
|
--AaB03x\r
|
477
445
|
content-disposition: form-data; name="huge"; filename="huge"\r
|
@@ -489,11 +457,11 @@ EOF
|
|
489
457
|
"CONTENT_LENGTH" => input.size,
|
490
458
|
:input => rack_input)
|
491
459
|
|
492
|
-
lambda
|
493
|
-
lambda
|
460
|
+
lambda{ req.POST }.should.not.raise
|
461
|
+
lambda{ req.POST }.should.not.raise("input re-processed!")
|
494
462
|
end
|
495
463
|
|
496
|
-
|
464
|
+
should "conform to the Rack spec" do
|
497
465
|
app = lambda { |env|
|
498
466
|
content = Rack::Request.new(env).POST["file"].inspect
|
499
467
|
size = content.respond_to?(:bytesize) ? content.bytesize : content.size
|
@@ -521,7 +489,7 @@ EOF
|
|
521
489
|
res.should.be.ok
|
522
490
|
end
|
523
491
|
|
524
|
-
|
492
|
+
should "parse Accept-Encoding correctly" do
|
525
493
|
parser = lambda do |x|
|
526
494
|
Rack::Request.new(Rack::MockRequest.env_for("", "HTTP_ACCEPT_ENCODING" => x)).accept_encoding
|
527
495
|
end
|
@@ -537,7 +505,7 @@ EOF
|
|
537
505
|
lambda { parser.call("gzip ; q=1.0") }.should.raise(RuntimeError)
|
538
506
|
end
|
539
507
|
|
540
|
-
|
508
|
+
should 'provide ip information' do
|
541
509
|
app = lambda { |env|
|
542
510
|
request = Rack::Request.new(env)
|
543
511
|
response = Rack::Response.new
|
@@ -559,7 +527,13 @@ EOF
|
|
559
527
|
'REMOTE_ADDR' => '123.123.123.123',
|
560
528
|
'HTTP_X_FORWARDED_FOR' => '234.234.234.234,212.212.212.212'
|
561
529
|
|
562
|
-
res.body.should.equal '
|
530
|
+
res.body.should.equal '234.234.234.234'
|
531
|
+
|
532
|
+
res = mock.get '/',
|
533
|
+
'REMOTE_ADDR' => '123.123.123.123',
|
534
|
+
'HTTP_X_FORWARDED_FOR' => 'unknown,234.234.234.234,212.212.212.212'
|
535
|
+
|
536
|
+
res.body.should.equal '234.234.234.234'
|
563
537
|
end
|
564
538
|
|
565
539
|
class MyRequest < Rack::Request
|
@@ -568,7 +542,7 @@ EOF
|
|
568
542
|
end
|
569
543
|
end
|
570
544
|
|
571
|
-
|
545
|
+
should "allow subclass request to be instantiated after parent request" do
|
572
546
|
env = Rack::MockRequest.env_for("/?foo=bar")
|
573
547
|
|
574
548
|
req1 = Rack::Request.new(env)
|
@@ -580,7 +554,7 @@ EOF
|
|
580
554
|
req2.params.should.equal :foo => "bar"
|
581
555
|
end
|
582
556
|
|
583
|
-
|
557
|
+
should "allow parent request to be instantiated after subclass request" do
|
584
558
|
env = Rack::MockRequest.env_for("/?foo=bar")
|
585
559
|
|
586
560
|
req1 = MyRequest.new(env)
|
@@ -591,4 +565,16 @@ EOF
|
|
591
565
|
req2.GET.should.equal "foo" => "bar"
|
592
566
|
req2.params.should.equal "foo" => "bar"
|
593
567
|
end
|
568
|
+
|
569
|
+
(0x20...0x7E).collect { |a|
|
570
|
+
b = a.chr
|
571
|
+
c = CGI.escape(b)
|
572
|
+
should "not strip '#{a}' => '#{c}' => '#{b}' escaped character from parameters when accessed as string" do
|
573
|
+
url = "/?foo=#{c}bar#{c}"
|
574
|
+
env = Rack::MockRequest.env_for(url)
|
575
|
+
req2 = Rack::Request.new(env)
|
576
|
+
req2.GET.should.equal "foo" => "#{b}bar#{b}"
|
577
|
+
req2.params.should.equal "foo" => "#{b}bar#{b}"
|
578
|
+
end
|
579
|
+
}
|
594
580
|
end
|