rack 1.1.0 → 1.2.0
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/README +23 -26
- data/SPEC +3 -3
- 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 +66 -7
- data/lib/rack/session/memcache.rb +1 -1
- data/lib/rack/urlmap.rb +6 -7
- data/lib/rack/utils.rb +64 -22
- data/lib/rack.rb +1 -12
- data/rack.gemspec +6 -6
- 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 -21
- 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 -49
- data/{test/spec_rack_response.rb → spec/spec_response.rb} +48 -29
- 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} +15 -18
- 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} +136 -71
- 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 +206 -124
- data/RDOX +0 -0
- data/lib/rack/adapter/camping.rb +0 -22
- data/test/spec_rack_camping.rb +0 -51
- 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 -154
|
@@ -0,0 +1 @@
|
|
|
1
|
+
contents
|
data/spec/multipart/ie
ADDED
data/spec/multipart/none
ADDED
data/spec/multipart/text
ADDED
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
require "#{File.dirname(__FILE__)}/../testrequest"
|
|
2
|
+
|
|
3
|
+
$stderr = File.open("#{File.dirname(__FILE__)}/log_output", "w")
|
|
4
|
+
|
|
5
|
+
class EnvMiddleware
|
|
6
|
+
def initialize(app)
|
|
7
|
+
@app = app
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
def call(env)
|
|
11
|
+
# provides a way to test that lint is present
|
|
12
|
+
if env["PATH_INFO"] == "/broken_lint"
|
|
13
|
+
return [200, {}, ["Broken Lint"]]
|
|
14
|
+
# provides a way to kill the process without knowing the pid
|
|
15
|
+
elsif env["PATH_INFO"] == "/die"
|
|
16
|
+
exit!
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
env["test.$DEBUG"] = $DEBUG
|
|
20
|
+
env["test.$EVAL"] = BUKKIT if defined?(BUKKIT)
|
|
21
|
+
env["test.$VERBOSE"] = $VERBOSE
|
|
22
|
+
env["test.$LOAD_PATH"] = $LOAD_PATH
|
|
23
|
+
env["test.stderr"] = File.expand_path($stderr.path)
|
|
24
|
+
env["test.Ping"] = defined?(Ping)
|
|
25
|
+
env["test.pid"] = Process.pid
|
|
26
|
+
@app.call(env)
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
use EnvMiddleware
|
|
31
|
+
run TestRequest.new
|
|
@@ -1,25 +1,22 @@
|
|
|
1
|
-
require 'test/spec'
|
|
2
|
-
|
|
3
1
|
require 'rack/auth/basic'
|
|
4
2
|
require 'rack/mock'
|
|
5
3
|
|
|
6
|
-
|
|
7
|
-
|
|
4
|
+
describe Rack::Auth::Basic do
|
|
8
5
|
def realm
|
|
9
6
|
'WallysWorld'
|
|
10
7
|
end
|
|
11
|
-
|
|
8
|
+
|
|
12
9
|
def unprotected_app
|
|
13
10
|
lambda { |env| [ 200, {'Content-Type' => 'text/plain'}, ["Hi #{env['REMOTE_USER']}"] ] }
|
|
14
11
|
end
|
|
15
|
-
|
|
12
|
+
|
|
16
13
|
def protected_app
|
|
17
14
|
app = Rack::Auth::Basic.new(unprotected_app) { |username, password| 'Boss' == username }
|
|
18
15
|
app.realm = realm
|
|
19
16
|
app
|
|
20
17
|
end
|
|
21
18
|
|
|
22
|
-
|
|
19
|
+
before do
|
|
23
20
|
@request = Rack::MockRequest.new(protected_app)
|
|
24
21
|
end
|
|
25
22
|
|
|
@@ -39,26 +36,26 @@ context 'Rack::Auth::Basic' do
|
|
|
39
36
|
response.body.should.be.empty
|
|
40
37
|
end
|
|
41
38
|
|
|
42
|
-
|
|
39
|
+
should 'challenge correctly when no credentials are specified' do
|
|
43
40
|
request do |response|
|
|
44
41
|
assert_basic_auth_challenge response
|
|
45
42
|
end
|
|
46
43
|
end
|
|
47
44
|
|
|
48
|
-
|
|
45
|
+
should 'rechallenge if incorrect credentials are specified' do
|
|
49
46
|
request_with_basic_auth 'joe', 'password' do |response|
|
|
50
47
|
assert_basic_auth_challenge response
|
|
51
48
|
end
|
|
52
49
|
end
|
|
53
50
|
|
|
54
|
-
|
|
51
|
+
should 'return application output if correct credentials are specified' do
|
|
55
52
|
request_with_basic_auth 'Boss', 'password' do |response|
|
|
56
53
|
response.status.should.equal 200
|
|
57
54
|
response.body.to_s.should.equal 'Hi Boss'
|
|
58
55
|
end
|
|
59
56
|
end
|
|
60
|
-
|
|
61
|
-
|
|
57
|
+
|
|
58
|
+
should 'return 400 Bad Request if different auth scheme used' do
|
|
62
59
|
request 'HTTP_AUTHORIZATION' => 'Digest params' do |response|
|
|
63
60
|
response.should.be.a.client_error
|
|
64
61
|
response.status.should.equal 400
|
|
@@ -66,8 +63,8 @@ context 'Rack::Auth::Basic' do
|
|
|
66
63
|
end
|
|
67
64
|
end
|
|
68
65
|
|
|
69
|
-
|
|
66
|
+
it 'takes realm as optional constructor arg' do
|
|
70
67
|
app = Rack::Auth::Basic.new(unprotected_app, realm) { true }
|
|
71
|
-
|
|
68
|
+
realm.should == app.realm
|
|
72
69
|
end
|
|
73
70
|
end
|
|
@@ -1,10 +1,7 @@
|
|
|
1
|
-
require 'test/spec'
|
|
2
|
-
|
|
3
1
|
require 'rack/auth/digest/md5'
|
|
4
2
|
require 'rack/mock'
|
|
5
3
|
|
|
6
|
-
|
|
7
|
-
|
|
4
|
+
describe Rack::Auth::Digest::MD5 do
|
|
8
5
|
def realm
|
|
9
6
|
'WallysWorld'
|
|
10
7
|
end
|
|
@@ -45,7 +42,7 @@ context 'Rack::Auth::Digest::MD5' do
|
|
|
45
42
|
Rack::MethodOverride.new(protected_app)
|
|
46
43
|
end
|
|
47
44
|
|
|
48
|
-
|
|
45
|
+
before do
|
|
49
46
|
@request = Rack::MockRequest.new(protected_app)
|
|
50
47
|
end
|
|
51
48
|
|
|
@@ -117,20 +114,20 @@ context 'Rack::Auth::Digest::MD5' do
|
|
|
117
114
|
response.should.not.include 'WWW-Authenticate'
|
|
118
115
|
end
|
|
119
116
|
|
|
120
|
-
|
|
117
|
+
should 'challenge when no credentials are specified' do
|
|
121
118
|
request 'GET', '/' do |response|
|
|
122
119
|
assert_digest_auth_challenge response
|
|
123
120
|
end
|
|
124
121
|
end
|
|
125
122
|
|
|
126
|
-
|
|
123
|
+
should 'return application output if correct credentials given' do
|
|
127
124
|
request_with_digest_auth 'GET', '/', 'Alice', 'correct-password' do |response|
|
|
128
125
|
response.status.should.equal 200
|
|
129
126
|
response.body.to_s.should.equal 'Hi Alice'
|
|
130
127
|
end
|
|
131
128
|
end
|
|
132
129
|
|
|
133
|
-
|
|
130
|
+
should 'return application output if correct credentials given (hashed passwords)' do
|
|
134
131
|
@request = Rack::MockRequest.new(protected_app_with_hashed_passwords)
|
|
135
132
|
|
|
136
133
|
request_with_digest_auth 'GET', '/', 'Alice', 'correct-password' do |response|
|
|
@@ -139,19 +136,19 @@ context 'Rack::Auth::Digest::MD5' do
|
|
|
139
136
|
end
|
|
140
137
|
end
|
|
141
138
|
|
|
142
|
-
|
|
139
|
+
should 'rechallenge if incorrect username given' do
|
|
143
140
|
request_with_digest_auth 'GET', '/', 'Bob', 'correct-password' do |response|
|
|
144
141
|
assert_digest_auth_challenge response
|
|
145
142
|
end
|
|
146
143
|
end
|
|
147
144
|
|
|
148
|
-
|
|
145
|
+
should 'rechallenge if incorrect password given' do
|
|
149
146
|
request_with_digest_auth 'GET', '/', 'Alice', 'wrong-password' do |response|
|
|
150
147
|
assert_digest_auth_challenge response
|
|
151
148
|
end
|
|
152
149
|
end
|
|
153
150
|
|
|
154
|
-
|
|
151
|
+
should 'rechallenge with stale parameter if nonce is stale' do
|
|
155
152
|
begin
|
|
156
153
|
Rack::Auth::Digest::Nonce.time_limit = 1
|
|
157
154
|
|
|
@@ -164,39 +161,39 @@ context 'Rack::Auth::Digest::MD5' do
|
|
|
164
161
|
end
|
|
165
162
|
end
|
|
166
163
|
|
|
167
|
-
|
|
164
|
+
should 'return 400 Bad Request if incorrect qop given' do
|
|
168
165
|
request_with_digest_auth 'GET', '/', 'Alice', 'correct-password', 'qop' => 'auth-int' do |response|
|
|
169
166
|
assert_bad_request response
|
|
170
167
|
end
|
|
171
168
|
end
|
|
172
169
|
|
|
173
|
-
|
|
170
|
+
should 'return 400 Bad Request if incorrect uri given' do
|
|
174
171
|
request_with_digest_auth 'GET', '/', 'Alice', 'correct-password', 'uri' => '/foo' do |response|
|
|
175
172
|
assert_bad_request response
|
|
176
173
|
end
|
|
177
174
|
end
|
|
178
175
|
|
|
179
|
-
|
|
176
|
+
should 'return 400 Bad Request if different auth scheme used' do
|
|
180
177
|
request 'GET', '/', 'HTTP_AUTHORIZATION' => 'Basic QWxhZGRpbjpvcGVuIHNlc2FtZQ==' do |response|
|
|
181
178
|
assert_bad_request response
|
|
182
179
|
end
|
|
183
180
|
end
|
|
184
181
|
|
|
185
|
-
|
|
182
|
+
should 'not require credentials for unprotected path' do
|
|
186
183
|
@request = Rack::MockRequest.new(partially_protected_app)
|
|
187
184
|
request 'GET', '/' do |response|
|
|
188
185
|
response.should.be.ok
|
|
189
186
|
end
|
|
190
187
|
end
|
|
191
188
|
|
|
192
|
-
|
|
189
|
+
should 'challenge when no credentials are specified for protected path' do
|
|
193
190
|
@request = Rack::MockRequest.new(partially_protected_app)
|
|
194
191
|
request 'GET', '/protected' do |response|
|
|
195
192
|
assert_digest_auth_challenge response
|
|
196
193
|
end
|
|
197
194
|
end
|
|
198
195
|
|
|
199
|
-
|
|
196
|
+
should 'return application output if correct credentials given for protected path' do
|
|
200
197
|
@request = Rack::MockRequest.new(partially_protected_app)
|
|
201
198
|
request_with_digest_auth 'GET', '/protected', 'Alice', 'correct-password' do |response|
|
|
202
199
|
response.status.should.equal 200
|
|
@@ -204,14 +201,14 @@ context 'Rack::Auth::Digest::MD5' do
|
|
|
204
201
|
end
|
|
205
202
|
end
|
|
206
203
|
|
|
207
|
-
|
|
204
|
+
should 'return application output if correct credentials given for POST' do
|
|
208
205
|
request_with_digest_auth 'POST', '/', 'Alice', 'correct-password' do |response|
|
|
209
206
|
response.status.should.equal 200
|
|
210
207
|
response.body.to_s.should.equal 'Hi Alice'
|
|
211
208
|
end
|
|
212
209
|
end
|
|
213
210
|
|
|
214
|
-
|
|
211
|
+
should 'return application output if correct credentials given for PUT (using method override of POST)' do
|
|
215
212
|
@request = Rack::MockRequest.new(protected_app_with_method_override)
|
|
216
213
|
request_with_digest_auth 'POST', '/', 'Alice', 'correct-password', :input => "_method=put" do |response|
|
|
217
214
|
response.status.should.equal 200
|
|
@@ -219,8 +216,8 @@ context 'Rack::Auth::Digest::MD5' do
|
|
|
219
216
|
end
|
|
220
217
|
end
|
|
221
218
|
|
|
222
|
-
|
|
219
|
+
it 'takes realm as optional constructor arg' do
|
|
223
220
|
app = Rack::Auth::Digest::MD5.new(unprotected_app, realm) { true }
|
|
224
|
-
|
|
221
|
+
realm.should == app.realm
|
|
225
222
|
end
|
|
226
223
|
end
|
|
@@ -1,12 +1,51 @@
|
|
|
1
|
-
require 'test/spec'
|
|
2
|
-
|
|
3
1
|
require 'rack/builder'
|
|
4
2
|
require 'rack/mock'
|
|
5
3
|
require 'rack/showexceptions'
|
|
6
|
-
require 'rack/
|
|
4
|
+
require 'rack/urlmap'
|
|
5
|
+
|
|
6
|
+
class NothingMiddleware
|
|
7
|
+
def initialize(app)
|
|
8
|
+
@app = app
|
|
9
|
+
end
|
|
10
|
+
def call(env)
|
|
11
|
+
@@env = env
|
|
12
|
+
response = @app.call(env)
|
|
13
|
+
response
|
|
14
|
+
end
|
|
15
|
+
def self.env
|
|
16
|
+
@@env
|
|
17
|
+
end
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
describe Rack::Builder do
|
|
21
|
+
it "supports mapping" do
|
|
22
|
+
app = Rack::Builder.new do
|
|
23
|
+
map '/' do |outer_env|
|
|
24
|
+
run lambda { |inner_env| [200, {}, ['root']] }
|
|
25
|
+
end
|
|
26
|
+
map '/sub' do
|
|
27
|
+
run lambda { |inner_env| [200, {}, ['sub']] }
|
|
28
|
+
end
|
|
29
|
+
end.to_app
|
|
30
|
+
Rack::MockRequest.new(app).get("/").body.to_s.should.equal 'root'
|
|
31
|
+
Rack::MockRequest.new(app).get("/sub").body.to_s.should.equal 'sub'
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
it "doesn't dupe env even when mapping" do
|
|
35
|
+
app = Rack::Builder.new do
|
|
36
|
+
use NothingMiddleware
|
|
37
|
+
map '/' do |outer_env|
|
|
38
|
+
run lambda { |inner_env|
|
|
39
|
+
inner_env['new_key'] = 'new_value'
|
|
40
|
+
[200, {}, ['root']]
|
|
41
|
+
}
|
|
42
|
+
end
|
|
43
|
+
end.to_app
|
|
44
|
+
Rack::MockRequest.new(app).get("/").body.to_s.should.equal 'root'
|
|
45
|
+
NothingMiddleware.env['new_key'].should.equal 'new_value'
|
|
46
|
+
end
|
|
7
47
|
|
|
8
|
-
|
|
9
|
-
specify "chains apps by default" do
|
|
48
|
+
it "chains apps by default" do
|
|
10
49
|
app = Rack::Builder.new do
|
|
11
50
|
use Rack::ShowExceptions
|
|
12
51
|
run lambda { |env| raise "bzzzt" }
|
|
@@ -17,7 +56,7 @@ context "Rack::Builder" do
|
|
|
17
56
|
Rack::MockRequest.new(app).get("/").should.be.server_error
|
|
18
57
|
end
|
|
19
58
|
|
|
20
|
-
|
|
59
|
+
it "has implicit #to_app" do
|
|
21
60
|
app = Rack::Builder.new do
|
|
22
61
|
use Rack::ShowExceptions
|
|
23
62
|
run lambda { |env| raise "bzzzt" }
|
|
@@ -28,7 +67,7 @@ context "Rack::Builder" do
|
|
|
28
67
|
Rack::MockRequest.new(app).get("/").should.be.server_error
|
|
29
68
|
end
|
|
30
69
|
|
|
31
|
-
|
|
70
|
+
it "supports blocks on use" do
|
|
32
71
|
app = Rack::Builder.new do
|
|
33
72
|
use Rack::ShowExceptions
|
|
34
73
|
use Rack::Auth::Basic do |username, password|
|
|
@@ -43,13 +82,13 @@ context "Rack::Builder" do
|
|
|
43
82
|
response.status.should.equal 401
|
|
44
83
|
|
|
45
84
|
# with auth...
|
|
46
|
-
response = Rack::MockRequest.new(app).get("/",
|
|
85
|
+
response = Rack::MockRequest.new(app).get("/",
|
|
47
86
|
'HTTP_AUTHORIZATION' => 'Basic ' + ["joe:secret"].pack("m*"))
|
|
48
87
|
response.status.should.equal 200
|
|
49
88
|
response.body.to_s.should.equal 'Hi Boss'
|
|
50
89
|
end
|
|
51
90
|
|
|
52
|
-
|
|
91
|
+
it "has explicit #to_app" do
|
|
53
92
|
app = Rack::Builder.app do
|
|
54
93
|
use Rack::ShowExceptions
|
|
55
94
|
run lambda { |env| raise "bzzzt" }
|
|
@@ -60,7 +99,7 @@ context "Rack::Builder" do
|
|
|
60
99
|
Rack::MockRequest.new(app).get("/").should.be.server_error
|
|
61
100
|
end
|
|
62
101
|
|
|
63
|
-
|
|
102
|
+
should "initialize apps once" do
|
|
64
103
|
app = Rack::Builder.new do
|
|
65
104
|
class AppClass
|
|
66
105
|
def initialize
|
|
@@ -1,12 +1,9 @@
|
|
|
1
|
-
require 'test/spec'
|
|
2
|
-
|
|
3
1
|
require 'rack/cascade'
|
|
4
|
-
require 'rack/mock'
|
|
5
|
-
|
|
6
|
-
require 'rack/urlmap'
|
|
7
2
|
require 'rack/file'
|
|
3
|
+
require 'rack/urlmap'
|
|
4
|
+
require 'rack/mock'
|
|
8
5
|
|
|
9
|
-
|
|
6
|
+
describe Rack::Cascade do
|
|
10
7
|
docroot = File.expand_path(File.dirname(__FILE__))
|
|
11
8
|
app1 = Rack::File.new(docroot)
|
|
12
9
|
|
|
@@ -15,7 +12,7 @@ context "Rack::Cascade" do
|
|
|
15
12
|
app3 = Rack::URLMap.new("/foo" => lambda { |env|
|
|
16
13
|
[200, { "Content-Type" => "text/plain"}, [""]]})
|
|
17
14
|
|
|
18
|
-
|
|
15
|
+
should "dispatch onward on 404 by default" do
|
|
19
16
|
cascade = Rack::Cascade.new([app1, app2, app3])
|
|
20
17
|
Rack::MockRequest.new(cascade).get("/cgi/test").should.be.ok
|
|
21
18
|
Rack::MockRequest.new(cascade).get("/foo").should.be.ok
|
|
@@ -23,16 +20,16 @@ context "Rack::Cascade" do
|
|
|
23
20
|
Rack::MockRequest.new(cascade).get("/cgi/../bla").should.be.forbidden
|
|
24
21
|
end
|
|
25
22
|
|
|
26
|
-
|
|
23
|
+
should "dispatch onward on whatever is passed" do
|
|
27
24
|
cascade = Rack::Cascade.new([app1, app2, app3], [404, 403])
|
|
28
25
|
Rack::MockRequest.new(cascade).get("/cgi/../bla").should.be.not_found
|
|
29
26
|
end
|
|
30
27
|
|
|
31
|
-
|
|
28
|
+
should "return 404 if empty" do
|
|
32
29
|
Rack::MockRequest.new(Rack::Cascade.new([])).get('/').should.be.not_found
|
|
33
30
|
end
|
|
34
31
|
|
|
35
|
-
|
|
32
|
+
should "append new app" do
|
|
36
33
|
cascade = Rack::Cascade.new([], [404, 403])
|
|
37
34
|
Rack::MockRequest.new(cascade).get('/').should.be.not_found
|
|
38
35
|
cascade << app2
|
|
@@ -1,53 +1,55 @@
|
|
|
1
|
-
require '
|
|
2
|
-
require '
|
|
1
|
+
require File.expand_path('../testrequest', __FILE__)
|
|
2
|
+
require 'rack/handler/cgi'
|
|
3
3
|
|
|
4
|
-
|
|
5
|
-
|
|
4
|
+
describe Rack::Handler::CGI do
|
|
5
|
+
extend TestRequest::Helpers
|
|
6
6
|
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
@port = 9203
|
|
10
|
-
end
|
|
7
|
+
@host = '0.0.0.0'
|
|
8
|
+
@port = 9203
|
|
11
9
|
|
|
12
10
|
# Keep this first.
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
11
|
+
$pid = fork {
|
|
12
|
+
ENV['RACK_ENV'] = 'deployment'
|
|
13
|
+
ENV['RUBYLIB'] = [
|
|
14
|
+
File.expand_path('../../lib', __FILE__),
|
|
15
|
+
ENV['RUBYLIB'],
|
|
16
|
+
].compact.join(':')
|
|
17
|
+
|
|
18
|
+
Dir.chdir(File.expand_path("../cgi", __FILE__)) do
|
|
16
19
|
exec "lighttpd -D -f lighttpd.conf"
|
|
17
|
-
|
|
18
|
-
|
|
20
|
+
end
|
|
21
|
+
}
|
|
19
22
|
|
|
20
|
-
|
|
23
|
+
should "respond" do
|
|
21
24
|
sleep 1
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
}.should.not.raise
|
|
25
|
+
GET("/test")
|
|
26
|
+
response.should.not.be.nil
|
|
25
27
|
end
|
|
26
28
|
|
|
27
|
-
|
|
29
|
+
should "be a lighttpd" do
|
|
28
30
|
GET("/test")
|
|
29
|
-
status.should.
|
|
31
|
+
status.should.equal 200
|
|
30
32
|
response["SERVER_SOFTWARE"].should =~ /lighttpd/
|
|
31
33
|
response["HTTP_VERSION"].should.equal "HTTP/1.1"
|
|
32
34
|
response["SERVER_PROTOCOL"].should.equal "HTTP/1.1"
|
|
33
35
|
response["SERVER_PORT"].should.equal @port.to_s
|
|
34
|
-
response["SERVER_NAME"].should
|
|
36
|
+
response["SERVER_NAME"].should.equal @host
|
|
35
37
|
end
|
|
36
38
|
|
|
37
|
-
|
|
39
|
+
should "have rack headers" do
|
|
38
40
|
GET("/test")
|
|
39
|
-
response["rack.version"].should.equal
|
|
40
|
-
response["rack.multithread"].should.be
|
|
41
|
-
response["rack.multiprocess"].should.be
|
|
42
|
-
response["rack.run_once"].should.be
|
|
41
|
+
response["rack.version"].should.equal([1,1])
|
|
42
|
+
response["rack.multithread"].should.be.false
|
|
43
|
+
response["rack.multiprocess"].should.be.true
|
|
44
|
+
response["rack.run_once"].should.be.true
|
|
43
45
|
end
|
|
44
46
|
|
|
45
|
-
|
|
47
|
+
should "have CGI headers on GET" do
|
|
46
48
|
GET("/test")
|
|
47
49
|
response["REQUEST_METHOD"].should.equal "GET"
|
|
48
50
|
response["SCRIPT_NAME"].should.equal "/test"
|
|
49
51
|
response["REQUEST_PATH"].should.equal "/"
|
|
50
|
-
response["PATH_INFO"].should.
|
|
52
|
+
response["PATH_INFO"].should.be.nil
|
|
51
53
|
response["QUERY_STRING"].should.equal ""
|
|
52
54
|
response["test.postdata"].should.equal ""
|
|
53
55
|
|
|
@@ -59,7 +61,7 @@ context "Rack::Handler::CGI" do
|
|
|
59
61
|
response["QUERY_STRING"].should.equal "quux=1"
|
|
60
62
|
end
|
|
61
63
|
|
|
62
|
-
|
|
64
|
+
should "have CGI headers on POST" do
|
|
63
65
|
POST("/test", {"rack-form-data" => "23"}, {'X-test-header' => '42'})
|
|
64
66
|
status.should.equal 200
|
|
65
67
|
response["REQUEST_METHOD"].should.equal "POST"
|
|
@@ -70,20 +72,20 @@ context "Rack::Handler::CGI" do
|
|
|
70
72
|
response["test.postdata"].should.equal "rack-form-data=23"
|
|
71
73
|
end
|
|
72
74
|
|
|
73
|
-
|
|
75
|
+
should "support HTTP auth" do
|
|
74
76
|
GET("/test", {:user => "ruth", :passwd => "secret"})
|
|
75
77
|
response["HTTP_AUTHORIZATION"].should.equal "Basic cnV0aDpzZWNyZXQ="
|
|
76
78
|
end
|
|
77
79
|
|
|
78
|
-
|
|
80
|
+
should "set status" do
|
|
79
81
|
GET("/test?secret")
|
|
80
82
|
status.should.equal 403
|
|
81
83
|
response["rack.url_scheme"].should.equal "http"
|
|
82
84
|
end
|
|
83
85
|
|
|
84
86
|
# Keep this last.
|
|
85
|
-
|
|
87
|
+
should "shutdown" do
|
|
86
88
|
Process.kill 15, $pid
|
|
87
|
-
Process.wait($pid).should
|
|
89
|
+
Process.wait($pid).should == $pid
|
|
88
90
|
end
|
|
89
91
|
end
|
|
@@ -1,15 +1,13 @@
|
|
|
1
|
-
require 'rack/mock'
|
|
2
1
|
require 'rack/chunked'
|
|
3
|
-
require 'rack/
|
|
4
|
-
|
|
5
|
-
context "Rack::Chunked" do
|
|
2
|
+
require 'rack/mock'
|
|
6
3
|
|
|
4
|
+
describe Rack::Chunked do
|
|
7
5
|
before do
|
|
8
6
|
@env = Rack::MockRequest.
|
|
9
7
|
env_for('/', 'HTTP_VERSION' => '1.1', 'REQUEST_METHOD' => 'GET')
|
|
10
8
|
end
|
|
11
9
|
|
|
12
|
-
|
|
10
|
+
should 'chunk responses with no Content-Length' do
|
|
13
11
|
app = lambda { |env| [200, {}, ['Hello', ' ', 'World!']] }
|
|
14
12
|
response = Rack::MockResponse.new(*Rack::Chunked.new(app).call(@env))
|
|
15
13
|
response.headers.should.not.include 'Content-Length'
|
|
@@ -17,7 +15,7 @@ context "Rack::Chunked" do
|
|
|
17
15
|
response.body.should.equal "5\r\nHello\r\n1\r\n \r\n6\r\nWorld!\r\n0\r\n\r\n"
|
|
18
16
|
end
|
|
19
17
|
|
|
20
|
-
|
|
18
|
+
should 'chunks empty bodies properly' do
|
|
21
19
|
app = lambda { |env| [200, {}, []] }
|
|
22
20
|
response = Rack::MockResponse.new(*Rack::Chunked.new(app).call(@env))
|
|
23
21
|
response.headers.should.not.include 'Content-Length'
|
|
@@ -25,7 +23,7 @@ context "Rack::Chunked" do
|
|
|
25
23
|
response.body.should.equal "0\r\n\r\n"
|
|
26
24
|
end
|
|
27
25
|
|
|
28
|
-
|
|
26
|
+
should 'not modify response when Content-Length header present' do
|
|
29
27
|
app = lambda { |env| [200, {'Content-Length'=>'12'}, ['Hello', ' ', 'World!']] }
|
|
30
28
|
status, headers, body = Rack::Chunked.new(app).call(@env)
|
|
31
29
|
status.should.equal 200
|
|
@@ -34,7 +32,7 @@ context "Rack::Chunked" do
|
|
|
34
32
|
body.join.should.equal 'Hello World!'
|
|
35
33
|
end
|
|
36
34
|
|
|
37
|
-
|
|
35
|
+
should 'not modify response when client is HTTP/1.0' do
|
|
38
36
|
app = lambda { |env| [200, {}, ['Hello', ' ', 'World!']] }
|
|
39
37
|
@env['HTTP_VERSION'] = 'HTTP/1.0'
|
|
40
38
|
status, headers, body = Rack::Chunked.new(app).call(@env)
|
|
@@ -43,7 +41,7 @@ context "Rack::Chunked" do
|
|
|
43
41
|
body.join.should.equal 'Hello World!'
|
|
44
42
|
end
|
|
45
43
|
|
|
46
|
-
|
|
44
|
+
should 'not modify response when Transfer-Encoding header already present' do
|
|
47
45
|
app = lambda { |env| [200, {'Transfer-Encoding' => 'identity'}, ['Hello', ' ', 'World!']] }
|
|
48
46
|
status, headers, body = Rack::Chunked.new(app).call(@env)
|
|
49
47
|
status.should.equal 200
|
|
@@ -52,7 +50,7 @@ context "Rack::Chunked" do
|
|
|
52
50
|
end
|
|
53
51
|
|
|
54
52
|
[100, 204, 304].each do |status_code|
|
|
55
|
-
|
|
53
|
+
should "not modify response when status code is #{status_code}" do
|
|
56
54
|
app = lambda { |env| [status_code, {}, []] }
|
|
57
55
|
status, headers, body = Rack::Chunked.new(app).call(@env)
|
|
58
56
|
status.should.equal status_code
|