Skip to content

Commit 5822c33

Browse files
committed
Reorganize tests in prepartion to improve test coverage.
1 parent e6a9c46 commit 5822c33

File tree

13 files changed

+345
-197
lines changed

13 files changed

+345
-197
lines changed

fixtures/disable_console_context.rb

Lines changed: 0 additions & 17 deletions
This file was deleted.
Lines changed: 141 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,141 @@
1+
#!/usr/bin/env ruby
2+
# frozen_string_literal: true
3+
4+
require "sus"
5+
require "rack/lint"
6+
require "sus/fixtures/console"
7+
require "protocol/rack/server_context"
8+
9+
module Protocol
10+
module Rack
11+
AnAdapter = Sus::Shared("an adapter") do
12+
AServer = Sus::Shared("a server") do
13+
include Protocol::Rack::ServerContext
14+
15+
let(:protocol) {subject}
16+
17+
with "successful response" do
18+
let(:app) do
19+
::Rack::Lint.new(
20+
lambda do |env|
21+
[200, {}, ["Hello World!"]]
22+
end
23+
)
24+
end
25+
26+
let(:response) {client.get("/")}
27+
28+
it "get valid HTTP_HOST" do
29+
expect(response.read).to be == "Hello World!"
30+
end
31+
end
32+
33+
with "HTTP_HOST" do
34+
let(:app) do
35+
lambda do |env|
36+
[200, {}, ["HTTP_HOST: #{env['HTTP_HOST']}"]]
37+
end
38+
end
39+
40+
let(:response) {client.get("/")}
41+
42+
it "get valid HTTP_HOST" do
43+
expect(response.read).to be =~ /HTTP_HOST: (.*?):(\d+)+/
44+
end
45+
end
46+
47+
with "connection: close", timeout: 1 do
48+
let(:app) do
49+
lambda do |env|
50+
[200, {"connection" => "close"}, ["Hello World!"]]
51+
end
52+
end
53+
54+
let(:response) {client.get("/")}
55+
56+
it "get valid response" do
57+
expect(response.read).to be == "Hello World!"
58+
end
59+
end
60+
61+
with "non-string header value" do
62+
let(:app) do
63+
lambda do |env|
64+
[200, {"x-custom" => 123}, ["Hello World!"]]
65+
end
66+
end
67+
68+
let(:response) {client.get("/")}
69+
70+
it "get valid response" do
71+
expect(response.read).to be == "Hello World!"
72+
expect(response.headers["x-custom"]).to be == ["123"]
73+
end
74+
end
75+
76+
with "REQUEST_URI", timeout: 1 do
77+
let(:app) do
78+
lambda do |env|
79+
[200, {}, ["REQUEST_URI: #{env['REQUEST_URI']}"]]
80+
end
81+
end
82+
83+
let(:response) {client.get("/?foo=bar")}
84+
85+
it "get valid REQUEST_URI" do
86+
expect(response.read).to be == "REQUEST_URI: /?foo=bar"
87+
end
88+
end
89+
90+
with "streaming response" do
91+
let(:app) do
92+
lambda do |env|
93+
body = lambda do |stream|
94+
stream.write("Hello Streaming World")
95+
stream.close
96+
end
97+
98+
[200, {}, body]
99+
end
100+
end
101+
102+
let(:response) {client.get("/")}
103+
104+
it "can read streaming response" do
105+
expect(response.read).to be == "Hello Streaming World"
106+
end
107+
end
108+
end
109+
110+
[
111+
Async::HTTP::Protocol::HTTP10,
112+
Async::HTTP::Protocol::HTTP11,
113+
Async::HTTP::Protocol::HTTP2,
114+
].each do |klass|
115+
describe(klass, unique: klass.name) do
116+
it_behaves_like AServer
117+
end
118+
end
119+
120+
with "error handling" do
121+
with "nil response" do
122+
let(:app) {->(env) {nil}}
123+
124+
it "raises an error" do
125+
expect(response.status).to be == 500
126+
expect(response.read).to be == "ArgumentError: Status must be an integer!"
127+
end
128+
end
129+
130+
with "nil headers" do
131+
let(:app) {->(env) {[200, nil, []]}}
132+
133+
it "raises an error" do
134+
expect(response.status).to be == 500
135+
expect(response.read).to be == "ArgumentError: Headers must not be nil!"
136+
end
137+
end
138+
end
139+
end
140+
end
141+
end
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
# frozen_string_literal: true
2+
3+
# Released under the MIT License.
4+
# Copyright, 2022-2024, by Samuel Williams.
5+
6+
require "sus/fixtures/async/http/server_context"
7+
8+
module Protocol
9+
module Rack
10+
module ServerContext
11+
include Sus::Fixtures::Async::HTTP::ServerContext
12+
13+
def app
14+
->(env){[200, {}, ["Hello World!"]]}
15+
end
16+
17+
def middleware
18+
Protocol::Rack::Adapter.new(app)
19+
end
20+
end
21+
end
22+
end

fixtures/server_context.rb

Lines changed: 0 additions & 18 deletions
This file was deleted.

gems.rb

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@
2323

2424
gem "sus-fixtures-async"
2525
gem "sus-fixtures-async-http"
26+
gem "sus-fixtures-console"
2627

2728
gem "bake-test"
2829
gem "bake-test-external"

lib/protocol/rack/adapter/rack2.rb

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,20 @@ def call(request)
8080

8181
status, headers, body = @app.call(env)
8282

83+
if status
84+
status = status.to_i
85+
else
86+
raise ArgumentError, "Status must be an integer!"
87+
end
88+
89+
unless headers
90+
raise ArgumentError, "Headers must not be nil!"
91+
end
92+
93+
unless body.respond_to?(:each)
94+
raise ArgumentError, "Body must respond to #each!"
95+
end
96+
8397
headers, meta = self.wrap_headers(headers)
8498

8599
# Rack 2 spec does not allow only partial hijacking.

lib/protocol/rack/body.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
# frozen_string_literal: true
22

33
# Released under the MIT License.
4-
# Copyright, 2022-2024, by Samuel Williams.
4+
# Copyright, 2022-2025, by Samuel Williams.
55

66
require_relative "body/streaming"
77
require_relative "body/enumerable"

test/protocol/rack/adapter.rb

Lines changed: 0 additions & 143 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,7 @@
33
# Released under the MIT License.
44
# Copyright, 2022-2024, by Samuel Williams.
55

6-
require "rack/lint"
7-
86
require "protocol/rack/adapter"
9-
require "disable_console_context"
10-
require "server_context"
117

128
describe Protocol::Rack::Adapter do
139
let(:rackup_path) {File.expand_path(".adapter/config.ru", __dir__)}
@@ -16,142 +12,3 @@
1612
expect(subject.parse_file(rackup_path)).to be_a(Proc)
1713
end
1814
end
19-
20-
describe Protocol::Rack::Adapter::Generic do
21-
let(:adapter) {subject.new(lambda{})}
22-
23-
with "#unwrap_headers" do
24-
with "cookie header" do
25-
let(:fields) {[["cookie", "a=b"], ["cookie", "x=y"]]}
26-
let(:env) {Hash.new}
27-
28-
it "should merge duplicate headers" do
29-
adapter.unwrap_headers(fields, env)
30-
31-
# I'm not convinced this is standard behaviour:
32-
expect(env).to be == {"HTTP_COOKIE" => "a=b;x=y"}
33-
end
34-
end
35-
36-
with "multiple accept headers" do
37-
let(:fields) {[["accept", "text/html"], ["accept", "application/json"]]}
38-
let(:env) {Hash.new}
39-
40-
it "should merge duplicate headers" do
41-
adapter.unwrap_headers(fields, env)
42-
43-
expect(env).to be == {"HTTP_ACCEPT" => "text/html,application/json"}
44-
end
45-
end
46-
end
47-
end
48-
49-
Adapter = Sus::Shared("an adapter") do
50-
include ServerContext
51-
52-
let(:protocol) {subject}
53-
54-
with "successful response" do
55-
let(:app) do
56-
Rack::Lint.new(
57-
lambda do |env|
58-
[200, {}, ["Hello World!"]]
59-
end
60-
)
61-
end
62-
63-
let(:response) {client.get("/")}
64-
65-
it "get valid HTTP_HOST" do
66-
expect(response.read).to be == "Hello World!"
67-
end
68-
end
69-
70-
with "HTTP_HOST" do
71-
let(:app) do
72-
lambda do |env|
73-
[200, {}, ["HTTP_HOST: #{env['HTTP_HOST']}"]]
74-
end
75-
end
76-
77-
let(:response) {client.get("/")}
78-
79-
it "get valid HTTP_HOST" do
80-
expect(response.read).to be =~ /HTTP_HOST: (.*?):(\d+)+/
81-
end
82-
end
83-
84-
with "connection: close", timeout: 1 do
85-
include DisableConsoleContext
86-
87-
let(:app) do
88-
lambda do |env|
89-
[200, {"connection" => "close"}, ["Hello World!"]]
90-
end
91-
end
92-
93-
let(:response) {client.get("/")}
94-
95-
it "get valid response" do
96-
expect(response.read).to be == "Hello World!"
97-
end
98-
end
99-
100-
with "non-string header value" do
101-
let(:app) do
102-
lambda do |env|
103-
[200, {"x-custom" => 123}, ["Hello World!"]]
104-
end
105-
end
106-
107-
let(:response) {client.get("/")}
108-
109-
it "get valid response" do
110-
expect(response.read).to be == "Hello World!"
111-
expect(response.headers["x-custom"]).to be == ["123"]
112-
end
113-
end
114-
115-
with "REQUEST_URI", timeout: 1 do
116-
let(:app) do
117-
lambda do |env|
118-
[200, {}, ["REQUEST_URI: #{env['REQUEST_URI']}"]]
119-
end
120-
end
121-
122-
let(:response) {client.get("/?foo=bar")}
123-
124-
it "get valid REQUEST_URI" do
125-
expect(response.read).to be == "REQUEST_URI: /?foo=bar"
126-
end
127-
end
128-
129-
with "streaming response" do
130-
let(:app) do
131-
lambda do |env|
132-
body = lambda do |stream|
133-
stream.write("Hello Streaming World")
134-
stream.close
135-
end
136-
137-
[200, {}, body]
138-
end
139-
end
140-
141-
let(:response) {client.get("/")}
142-
143-
it "can read streaming response" do
144-
expect(response.read).to be == "Hello Streaming World"
145-
end
146-
end
147-
end
148-
149-
[
150-
Async::HTTP::Protocol::HTTP10,
151-
Async::HTTP::Protocol::HTTP11,
152-
Async::HTTP::Protocol::HTTP2,
153-
].each do |klass|
154-
describe(klass, unique: klass.name) do
155-
it_behaves_like Adapter
156-
end
157-
end

0 commit comments

Comments
 (0)