funnel_http 0.3.0 → 0.3.2
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.
- checksums.yaml +4 -4
- data/.golangci.yml +0 -3
- data/CHANGELOG.md +16 -1
- data/README.md +1 -1
- data/ext/funnel_http/go.mod +5 -3
- data/ext/funnel_http/go.sum +4 -6
- data/lib/funnel_http/version.rb +1 -1
- data/rbs_collection.lock.yaml +10 -14
- data/sig/funnel_http.rbs +2 -1
- metadata +4 -24
- data/benchmark/README.md +0 -32
- data/benchmark/benchmark.rb +0 -61
- data/benchmark/compose.yml +0 -8
- data/benchmark/html/index.html +0 -4
- data/benchmark/nginx.conf +0 -25
- data/ext/funnel_http/run_requests_test.go +0 -204
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 44a84685adf7f414a48d3b4db7a56192a6172874629529922b8bc937c5b0db9f
|
4
|
+
data.tar.gz: d0b7baca3c2947aa1b9b724915d598d9f702c6c7a45fcef1a0323fdae67cb845
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 1e47ca273145f8a5cf96d357d128d9a208fb50d23c9315f43b3bda8698cf7bbf4ddb4bcf3148fd01fec82a5c8e91aea9808423b430d9a26cf81ae2d1962e9c67
|
7
|
+
data.tar.gz: 97d7ace5558bbd6e3f7e09901660e58db6e2dbe7fd57cc7b9a9777ea8915f2dc4d3db47517234ab7d625e15f2522fc0483ca975becde55b53bf80c2c80bde766
|
data/.golangci.yml
CHANGED
data/CHANGELOG.md
CHANGED
@@ -1,5 +1,20 @@
|
|
1
1
|
## [Unreleased]
|
2
|
-
[full changelog](http://github.com/sue445/funnel_http/compare/v0.3.
|
2
|
+
[full changelog](http://github.com/sue445/funnel_http/compare/v0.3.2...main)
|
3
|
+
|
4
|
+
## [0.3.1](https://github.com/sue445/funnel_http/releases/tag/v0.3.2) - 2025-03-22
|
5
|
+
[full changelog](http://github.com/sue445/funnel_http/compare/v0.3.1...v0.3.2)
|
6
|
+
|
7
|
+
* Fix `Ruby::BlockBodyTypeMismatch` in rbs
|
8
|
+
* https://github.com/sue445/funnel_http/pull/71
|
9
|
+
|
10
|
+
## [0.3.1](https://github.com/sue445/funnel_http/releases/tag/v0.3.1) - 2025-03-12
|
11
|
+
[full changelog](http://github.com/sue445/funnel_http/compare/v0.3.0...v0.3.1)
|
12
|
+
|
13
|
+
* Diet gem
|
14
|
+
* https://github.com/sue445/funnel_http/pull/66
|
15
|
+
* Tweak gem description
|
16
|
+
* https://github.com/sue445/funnel_http/pull/68
|
17
|
+
* Update Go dependencies
|
3
18
|
|
4
19
|
## [0.3.0](https://github.com/sue445/funnel_http/releases/tag/v0.3.0) - 2025-01-12
|
5
20
|
[full changelog](http://github.com/sue445/funnel_http/compare/v0.2.0...v0.3.0)
|
data/README.md
CHANGED
@@ -1,5 +1,5 @@
|
|
1
1
|
# FunnelHttp
|
2
|
-
Perform HTTP requests in parallel
|
2
|
+
Perform HTTP requests in parallel with goroutine
|
3
3
|
|
4
4
|
[](https://badge.fury.io/rb/funnel_http)
|
5
5
|
[](https://github.com/sue445/funnel_http/actions/workflows/build.yml)
|
data/ext/funnel_http/go.mod
CHANGED
@@ -1,13 +1,15 @@
|
|
1
1
|
module github.com/sue445/funnel_http
|
2
2
|
|
3
|
-
go 1.23
|
3
|
+
go 1.23.0
|
4
|
+
|
5
|
+
toolchain go1.24.0
|
4
6
|
|
5
7
|
require (
|
6
8
|
github.com/cockroachdb/errors v1.11.3
|
7
9
|
github.com/jarcoal/httpmock v1.3.1
|
8
|
-
github.com/ruby-go-gem/go-gem-wrapper v0.
|
10
|
+
github.com/ruby-go-gem/go-gem-wrapper v0.7.2
|
9
11
|
github.com/stretchr/testify v1.10.0
|
10
|
-
golang.org/x/sync v0.
|
12
|
+
golang.org/x/sync v0.12.0
|
11
13
|
)
|
12
14
|
|
13
15
|
require (
|
data/ext/funnel_http/go.sum
CHANGED
@@ -34,10 +34,8 @@ github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZb
|
|
34
34
|
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
35
35
|
github.com/rogpeppe/go-internal v1.9.0 h1:73kH8U+JUqXU8lRuOHeVHaa/SZPifC7BkcraZVejAe8=
|
36
36
|
github.com/rogpeppe/go-internal v1.9.0/go.mod h1:WtVeX8xhTBvf0smdhujwtBcq4Qrzq/fJaraNFVN+nFs=
|
37
|
-
github.com/ruby-go-gem/go-gem-wrapper v0.
|
38
|
-
github.com/ruby-go-gem/go-gem-wrapper v0.
|
39
|
-
github.com/ruby-go-gem/go-gem-wrapper v0.6.0 h1:WFu2Cj/uzKAOemsrCo4P6vsdOgB5yesrrJtAqvLkAso=
|
40
|
-
github.com/ruby-go-gem/go-gem-wrapper v0.6.0/go.mod h1:k2k+LziSCMxNYP4J9/9v90xdU6zlU1DJpJDTU6oJhHE=
|
37
|
+
github.com/ruby-go-gem/go-gem-wrapper v0.7.2 h1:Hf7bA5TD/UjJTccTwsbBJWnjpBvcQWAzX50tv9++4+o=
|
38
|
+
github.com/ruby-go-gem/go-gem-wrapper v0.7.2/go.mod h1:k2k+LziSCMxNYP4J9/9v90xdU6zlU1DJpJDTU6oJhHE=
|
41
39
|
github.com/stretchr/testify v1.10.0 h1:Xv5erBjTwe/5IxqUQTdXv5kgmIvbHo3QQyRwhJsOfJA=
|
42
40
|
github.com/stretchr/testify v1.10.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY=
|
43
41
|
github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
|
@@ -54,8 +52,8 @@ golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwY
|
|
54
52
|
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
55
53
|
golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
56
54
|
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
57
|
-
golang.org/x/sync v0.
|
58
|
-
golang.org/x/sync v0.
|
55
|
+
golang.org/x/sync v0.12.0 h1:MHc5BpPuC30uJk597Ri8TV3CNZcTLu6B6z4lJy+g6Jw=
|
56
|
+
golang.org/x/sync v0.12.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA=
|
59
57
|
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
60
58
|
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
61
59
|
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
data/lib/funnel_http/version.rb
CHANGED
data/rbs_collection.lock.yaml
CHANGED
@@ -2,9 +2,13 @@
|
|
2
2
|
path: ".gem_rbs_collection"
|
3
3
|
gems:
|
4
4
|
- name: base64
|
5
|
-
version: '0'
|
5
|
+
version: '0.1'
|
6
6
|
source:
|
7
|
-
type:
|
7
|
+
type: git
|
8
|
+
name: ruby/gem_rbs_collection
|
9
|
+
revision: a8dd6bcebdae31ce6adc8887ef16c7ee6e1b9a6d
|
10
|
+
remote: https://github.com/ruby/gem_rbs_collection.git
|
11
|
+
repo_dir: gems
|
8
12
|
- name: cgi
|
9
13
|
version: '0'
|
10
14
|
source:
|
@@ -14,7 +18,7 @@ gems:
|
|
14
18
|
source:
|
15
19
|
type: git
|
16
20
|
name: ruby/gem_rbs_collection
|
17
|
-
revision:
|
21
|
+
revision: a8dd6bcebdae31ce6adc8887ef16c7ee6e1b9a6d
|
18
22
|
remote: https://github.com/ruby/gem_rbs_collection.git
|
19
23
|
repo_dir: gems
|
20
24
|
- name: fileutils
|
@@ -29,20 +33,12 @@ gems:
|
|
29
33
|
version: '0'
|
30
34
|
source:
|
31
35
|
type: stdlib
|
32
|
-
- name: parallel
|
33
|
-
version: '1.20'
|
34
|
-
source:
|
35
|
-
type: git
|
36
|
-
name: ruby/gem_rbs_collection
|
37
|
-
revision: 7ff8cf6ab2759cb1d0fb2ca8d6c1f8ccab2c605c
|
38
|
-
remote: https://github.com/ruby/gem_rbs_collection.git
|
39
|
-
repo_dir: gems
|
40
36
|
- name: rack
|
41
37
|
version: '2.2'
|
42
38
|
source:
|
43
39
|
type: git
|
44
40
|
name: ruby/gem_rbs_collection
|
45
|
-
revision:
|
41
|
+
revision: a8dd6bcebdae31ce6adc8887ef16c7ee6e1b9a6d
|
46
42
|
remote: https://github.com/ruby/gem_rbs_collection.git
|
47
43
|
repo_dir: gems
|
48
44
|
- name: rake
|
@@ -50,7 +46,7 @@ gems:
|
|
50
46
|
source:
|
51
47
|
type: git
|
52
48
|
name: ruby/gem_rbs_collection
|
53
|
-
revision:
|
49
|
+
revision: a8dd6bcebdae31ce6adc8887ef16c7ee6e1b9a6d
|
54
50
|
remote: https://github.com/ruby/gem_rbs_collection.git
|
55
51
|
repo_dir: gems
|
56
52
|
- name: sinatra
|
@@ -58,7 +54,7 @@ gems:
|
|
58
54
|
source:
|
59
55
|
type: git
|
60
56
|
name: ruby/gem_rbs_collection
|
61
|
-
revision:
|
57
|
+
revision: a8dd6bcebdae31ce6adc8887ef16c7ee6e1b9a6d
|
62
58
|
remote: https://github.com/ruby/gem_rbs_collection.git
|
63
59
|
repo_dir: gems
|
64
60
|
- name: stringio
|
data/sig/funnel_http.rbs
CHANGED
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: funnel_http
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.3.
|
4
|
+
version: 0.3.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- sue445
|
8
8
|
bindir: exe
|
9
9
|
cert_chain: []
|
10
|
-
date: 2025-
|
10
|
+
date: 2025-03-21 00:00:00.000000000 Z
|
11
11
|
dependencies:
|
12
12
|
- !ruby/object:Gem::Dependency
|
13
13
|
name: go_gem
|
@@ -177,21 +177,7 @@ dependencies:
|
|
177
177
|
- - ">="
|
178
178
|
- !ruby/object:Gem::Version
|
179
179
|
version: '0'
|
180
|
-
|
181
|
-
name: parallel
|
182
|
-
requirement: !ruby/object:Gem::Requirement
|
183
|
-
requirements:
|
184
|
-
- - ">="
|
185
|
-
- !ruby/object:Gem::Version
|
186
|
-
version: '0'
|
187
|
-
type: :development
|
188
|
-
prerelease: false
|
189
|
-
version_requirements: !ruby/object:Gem::Requirement
|
190
|
-
requirements:
|
191
|
-
- - ">="
|
192
|
-
- !ruby/object:Gem::Version
|
193
|
-
version: '0'
|
194
|
-
description: Perform HTTP requests in parallel
|
180
|
+
description: Perform HTTP requests in parallel with goroutine
|
195
181
|
email:
|
196
182
|
- sue445@sue445.net
|
197
183
|
executables: []
|
@@ -207,11 +193,6 @@ files:
|
|
207
193
|
- README.md
|
208
194
|
- Rakefile
|
209
195
|
- Steepfile
|
210
|
-
- benchmark/README.md
|
211
|
-
- benchmark/benchmark.rb
|
212
|
-
- benchmark/compose.yml
|
213
|
-
- benchmark/html/index.html
|
214
|
-
- benchmark/nginx.conf
|
215
196
|
- ext/funnel_http/extconf.rb
|
216
197
|
- ext/funnel_http/funnel_http.c
|
217
198
|
- ext/funnel_http/funnel_http.go
|
@@ -219,7 +200,6 @@ files:
|
|
219
200
|
- ext/funnel_http/go.mod
|
220
201
|
- ext/funnel_http/go.sum
|
221
202
|
- ext/funnel_http/run_requests.go
|
222
|
-
- ext/funnel_http/run_requests_test.go
|
223
203
|
- lib/funnel_http.rb
|
224
204
|
- lib/funnel_http/client.rb
|
225
205
|
- lib/funnel_http/ext.rb
|
@@ -254,5 +234,5 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
254
234
|
requirements: []
|
255
235
|
rubygems_version: 3.6.2
|
256
236
|
specification_version: 4
|
257
|
-
summary: Perform HTTP requests in parallel
|
237
|
+
summary: Perform HTTP requests in parallel with goroutine
|
258
238
|
test_files: []
|
data/benchmark/README.md
DELETED
@@ -1,32 +0,0 @@
|
|
1
|
-
# benchmark for funnel_http
|
2
|
-
## Usage
|
3
|
-
```bash
|
4
|
-
docker compose up --build
|
5
|
-
```
|
6
|
-
|
7
|
-
```bash
|
8
|
-
bundle exec ruby benchmark.rb
|
9
|
-
```
|
10
|
-
|
11
|
-
## Report
|
12
|
-
```
|
13
|
-
Warming up --------------------------------------
|
14
|
-
FunnelHttp::Client#perform
|
15
|
-
2.000 i/100ms
|
16
|
-
Parallel with 4 processes
|
17
|
-
1.000 i/100ms
|
18
|
-
Parallel with 4 threads
|
19
|
-
1.000 i/100ms
|
20
|
-
Calculating -------------------------------------
|
21
|
-
FunnelHttp::Client#perform
|
22
|
-
21.816 (± 4.6%) i/s (45.84 ms/i) - 44.000 in 2.026960s
|
23
|
-
Parallel with 4 processes
|
24
|
-
15.785 (± 6.3%) i/s (63.35 ms/i) - 32.000 in 2.035628s
|
25
|
-
Parallel with 4 threads
|
26
|
-
18.570 (±10.8%) i/s (53.85 ms/i) - 37.000 in 2.008485s
|
27
|
-
|
28
|
-
Comparison:
|
29
|
-
FunnelHttp::Client#perform: 21.8 i/s
|
30
|
-
Parallel with 4 threads: 18.6 i/s - 1.17x slower
|
31
|
-
Parallel with 4 processes: 15.8 i/s - 1.38x slower
|
32
|
-
```
|
data/benchmark/benchmark.rb
DELETED
@@ -1,61 +0,0 @@
|
|
1
|
-
require "benchmark/ips"
|
2
|
-
require "open-uri"
|
3
|
-
require "parallel"
|
4
|
-
require "etc"
|
5
|
-
|
6
|
-
ROOT_DIR = File.expand_path("..", __dir__)
|
7
|
-
|
8
|
-
TEST_SERVER_URL = ENV.fetch("TEST_SERVER_URL") { "http://localhost:8080/" }
|
9
|
-
|
10
|
-
REQUEST_COUNT = 100
|
11
|
-
|
12
|
-
BENCHMARK_CONCURRENCY = (ENV.fetch("BENCHMARK_CONCURRENCY") { 4 }).to_i
|
13
|
-
|
14
|
-
# Build native extension before running benchmark
|
15
|
-
Dir.chdir(ROOT_DIR) do
|
16
|
-
system("bundle config set --local path 'vendor/bundle'", exception: true)
|
17
|
-
system("bundle install", exception: true)
|
18
|
-
system("bundle exec rake clobber compile", exception: true)
|
19
|
-
end
|
20
|
-
|
21
|
-
require_relative "../lib/funnel_http"
|
22
|
-
|
23
|
-
# Suppress Ractor warning
|
24
|
-
$VERBOSE = nil
|
25
|
-
|
26
|
-
system("go version", exception: true)
|
27
|
-
|
28
|
-
requests = Array.new(REQUEST_COUNT, { method: :get, url: TEST_SERVER_URL })
|
29
|
-
|
30
|
-
def fetch_server
|
31
|
-
URI.parse(TEST_SERVER_URL).open(open_timeout: 90, read_timeout: 90).read
|
32
|
-
end
|
33
|
-
|
34
|
-
Benchmark.ips do |x|
|
35
|
-
# x.config(warmup: 1, time: 2)
|
36
|
-
|
37
|
-
x.report("FunnelHttp::Client#perform") do
|
38
|
-
FunnelHttp::Client.new.perform(requests)
|
39
|
-
end
|
40
|
-
|
41
|
-
x.report("Parallel with #{BENCHMARK_CONCURRENCY} processes") do
|
42
|
-
Parallel.each(requests, in_processes: BENCHMARK_CONCURRENCY) do
|
43
|
-
fetch_server
|
44
|
-
end
|
45
|
-
end
|
46
|
-
|
47
|
-
x.report("Parallel with #{BENCHMARK_CONCURRENCY} threads") do
|
48
|
-
Parallel.each(requests, in_threads: BENCHMARK_CONCURRENCY) do
|
49
|
-
fetch_server
|
50
|
-
end
|
51
|
-
end
|
52
|
-
|
53
|
-
# FIXME: open-uri doesn't work in Ractor
|
54
|
-
# x.report("Parallel with Ractor") do
|
55
|
-
# REQUEST_COUNT.times.map do
|
56
|
-
# Ractor.new { URI.parse("http://localhost:8080/").read }
|
57
|
-
# end.each(&:take)
|
58
|
-
# end
|
59
|
-
|
60
|
-
x.compare!
|
61
|
-
end
|
data/benchmark/compose.yml
DELETED
data/benchmark/html/index.html
DELETED
data/benchmark/nginx.conf
DELETED
@@ -1,25 +0,0 @@
|
|
1
|
-
worker_processes auto;
|
2
|
-
worker_rlimit_nofile 12288;
|
3
|
-
|
4
|
-
events {
|
5
|
-
worker_connections 4096;
|
6
|
-
}
|
7
|
-
|
8
|
-
http {
|
9
|
-
include mime.types;
|
10
|
-
default_type application/octet-stream;
|
11
|
-
|
12
|
-
sendfile on;
|
13
|
-
keepalive_timeout 65;
|
14
|
-
access_log off;
|
15
|
-
|
16
|
-
server {
|
17
|
-
listen 80;
|
18
|
-
server_name localhost;
|
19
|
-
|
20
|
-
location / {
|
21
|
-
root /usr/share/nginx/html;
|
22
|
-
index index.html;
|
23
|
-
}
|
24
|
-
}
|
25
|
-
}
|
@@ -1,204 +0,0 @@
|
|
1
|
-
package main_test
|
2
|
-
|
3
|
-
import (
|
4
|
-
"github.com/cockroachdb/errors"
|
5
|
-
"github.com/jarcoal/httpmock"
|
6
|
-
"github.com/stretchr/testify/assert"
|
7
|
-
"github.com/sue445/funnel_http"
|
8
|
-
"io"
|
9
|
-
"net/http"
|
10
|
-
"testing"
|
11
|
-
)
|
12
|
-
|
13
|
-
func TestRunRequests(t *testing.T) {
|
14
|
-
httpmock.Activate()
|
15
|
-
t.Cleanup(httpmock.DeactivateAndReset)
|
16
|
-
|
17
|
-
httpmock.RegisterResponder("GET", "http://example.com/1",
|
18
|
-
func(req *http.Request) (*http.Response, error) {
|
19
|
-
resp := httpmock.NewStringResponse(200, "GET http://example.com/1")
|
20
|
-
|
21
|
-
resp.Header.Set("Content-Type", "text/plain")
|
22
|
-
|
23
|
-
for key, values := range req.Header {
|
24
|
-
for _, value := range values {
|
25
|
-
resp.Header.Add(key, value)
|
26
|
-
}
|
27
|
-
}
|
28
|
-
|
29
|
-
return resp, nil
|
30
|
-
})
|
31
|
-
|
32
|
-
httpmock.RegisterResponder("GET", "http://example.com/2",
|
33
|
-
func(req *http.Request) (*http.Response, error) {
|
34
|
-
resp := httpmock.NewStringResponse(200, "GET http://example.com/2")
|
35
|
-
|
36
|
-
resp.Header.Set("Content-Type", "text/plain")
|
37
|
-
|
38
|
-
for key, values := range req.Header {
|
39
|
-
for _, value := range values {
|
40
|
-
resp.Header.Add(key, value)
|
41
|
-
}
|
42
|
-
}
|
43
|
-
|
44
|
-
return resp, nil
|
45
|
-
})
|
46
|
-
|
47
|
-
httpmock.RegisterResponder("POST", "http://example.com/1",
|
48
|
-
func(req *http.Request) (*http.Response, error) {
|
49
|
-
payload, err := io.ReadAll(req.Body)
|
50
|
-
if err != nil {
|
51
|
-
return nil, errors.WithStack(err)
|
52
|
-
}
|
53
|
-
|
54
|
-
resp := httpmock.NewStringResponse(200, string(payload))
|
55
|
-
|
56
|
-
resp.Header.Set("Content-Type", "text/plain")
|
57
|
-
|
58
|
-
for key, values := range req.Header {
|
59
|
-
for _, value := range values {
|
60
|
-
resp.Header.Add(key, value)
|
61
|
-
}
|
62
|
-
}
|
63
|
-
|
64
|
-
return resp, nil
|
65
|
-
})
|
66
|
-
|
67
|
-
tests := []struct {
|
68
|
-
name string
|
69
|
-
requests []main.Request
|
70
|
-
expected []main.Response
|
71
|
-
}{
|
72
|
-
{
|
73
|
-
name: "GET 1 request",
|
74
|
-
requests: []main.Request{
|
75
|
-
{
|
76
|
-
Method: "GET",
|
77
|
-
URL: "http://example.com/1",
|
78
|
-
Header: map[string][]string{
|
79
|
-
"X-My-Request-Header": {"a", "b"},
|
80
|
-
},
|
81
|
-
},
|
82
|
-
},
|
83
|
-
expected: []main.Response{
|
84
|
-
{
|
85
|
-
StatusCode: 200,
|
86
|
-
Body: []byte("GET http://example.com/1"),
|
87
|
-
Header: map[string][]string{
|
88
|
-
"Content-Type": {"text/plain"},
|
89
|
-
"X-My-Request-Header": {"a", "b"},
|
90
|
-
},
|
91
|
-
},
|
92
|
-
},
|
93
|
-
},
|
94
|
-
{
|
95
|
-
name: "GET multiple requests",
|
96
|
-
requests: []main.Request{
|
97
|
-
{
|
98
|
-
Method: "GET",
|
99
|
-
URL: "http://example.com/1",
|
100
|
-
Header: map[string][]string{
|
101
|
-
"X-My-Request-Header": {"a", "b"},
|
102
|
-
},
|
103
|
-
},
|
104
|
-
{
|
105
|
-
Method: "GET",
|
106
|
-
URL: "http://example.com/2",
|
107
|
-
Header: map[string][]string{
|
108
|
-
"X-My-Request-Header": {"c", "d"},
|
109
|
-
},
|
110
|
-
},
|
111
|
-
},
|
112
|
-
expected: []main.Response{
|
113
|
-
{
|
114
|
-
StatusCode: 200,
|
115
|
-
Body: []byte("GET http://example.com/1"),
|
116
|
-
Header: map[string][]string{
|
117
|
-
"Content-Type": {"text/plain"},
|
118
|
-
"X-My-Request-Header": {"a", "b"},
|
119
|
-
},
|
120
|
-
},
|
121
|
-
{
|
122
|
-
StatusCode: 200,
|
123
|
-
Body: []byte("GET http://example.com/2"),
|
124
|
-
Header: map[string][]string{
|
125
|
-
"Content-Type": {"text/plain"},
|
126
|
-
"X-My-Request-Header": {"c", "d"},
|
127
|
-
},
|
128
|
-
},
|
129
|
-
},
|
130
|
-
},
|
131
|
-
{
|
132
|
-
name: "POST 1 request",
|
133
|
-
requests: []main.Request{
|
134
|
-
{
|
135
|
-
Method: "POST",
|
136
|
-
URL: "http://example.com/1",
|
137
|
-
Header: map[string][]string{
|
138
|
-
"X-My-Request-Header": {"a", "b"},
|
139
|
-
},
|
140
|
-
Body: []byte("111"),
|
141
|
-
},
|
142
|
-
},
|
143
|
-
expected: []main.Response{
|
144
|
-
{
|
145
|
-
StatusCode: 200,
|
146
|
-
Body: []byte("111"),
|
147
|
-
Header: map[string][]string{
|
148
|
-
"Content-Type": {"text/plain"},
|
149
|
-
"X-My-Request-Header": {"a", "b"},
|
150
|
-
},
|
151
|
-
},
|
152
|
-
},
|
153
|
-
},
|
154
|
-
{
|
155
|
-
name: "POST multiple requests",
|
156
|
-
requests: []main.Request{
|
157
|
-
{
|
158
|
-
Method: "POST",
|
159
|
-
URL: "http://example.com/1",
|
160
|
-
Header: map[string][]string{
|
161
|
-
"X-My-Request-Header": {"a", "b"},
|
162
|
-
},
|
163
|
-
Body: []byte("111"),
|
164
|
-
},
|
165
|
-
{
|
166
|
-
Method: "POST",
|
167
|
-
URL: "http://example.com/1",
|
168
|
-
Header: map[string][]string{
|
169
|
-
"X-My-Request-Header": {"c", "d"},
|
170
|
-
},
|
171
|
-
Body: []byte("222"),
|
172
|
-
},
|
173
|
-
},
|
174
|
-
expected: []main.Response{
|
175
|
-
{
|
176
|
-
StatusCode: 200,
|
177
|
-
Body: []byte("111"),
|
178
|
-
Header: map[string][]string{
|
179
|
-
"Content-Type": {"text/plain"},
|
180
|
-
"X-My-Request-Header": {"a", "b"},
|
181
|
-
},
|
182
|
-
},
|
183
|
-
{
|
184
|
-
StatusCode: 200,
|
185
|
-
Body: []byte("222"),
|
186
|
-
Header: map[string][]string{
|
187
|
-
"Content-Type": {"text/plain"},
|
188
|
-
"X-My-Request-Header": {"c", "d"},
|
189
|
-
},
|
190
|
-
},
|
191
|
-
},
|
192
|
-
},
|
193
|
-
}
|
194
|
-
|
195
|
-
httpClient := http.Client{}
|
196
|
-
for _, tt := range tests {
|
197
|
-
t.Run(tt.name, func(t *testing.T) {
|
198
|
-
actual, err := main.RunRequests(&httpClient, tt.requests)
|
199
|
-
if assert.NoError(t, err) {
|
200
|
-
assert.Equal(t, tt.expected, actual)
|
201
|
-
}
|
202
|
-
})
|
203
|
-
}
|
204
|
-
}
|