From 3e504fb51171e017438fedc7c4699839d5a492df Mon Sep 17 00:00:00 2001 From: HoneyryderChuck Date: Thu, 31 Oct 2024 17:47:06 +0000 Subject: [PATCH] fix for webmock request body expecting a string when building the request signature, the body is preemptively converted to a string, which fulfills the expectation for webmock, despite it being a bit of a perf penalty if the request contains a multipart request body, as the body will be fully read to memory Closes #319 Closes https://github.com/HoneyryderChuck/httpx/issues/65 --- integration_tests/webmock_test.rb | 6 ++++++ lib/httpx/adapters/webmock.rb | 2 +- lib/httpx/transcoder/multipart/encoder.rb | 6 ++++++ sig/transcoder/multipart.rbs | 2 ++ 4 files changed, 15 insertions(+), 1 deletion(-) diff --git a/integration_tests/webmock_test.rb b/integration_tests/webmock_test.rb index 18d2a14b..15bd44a3 100644 --- a/integration_tests/webmock_test.rb +++ b/integration_tests/webmock_test.rb @@ -155,6 +155,12 @@ class WebmockTest < Minitest::Test assert_requested(:get, MOCK_URL_HTTP, query: hash_excluding("a" => %w[b c])) end + def test_verification_that_expected_request_with_hash_as_body + stub_request(:post, MOCK_URL_HTTP).with(body: { foo: "bar" }) + http_request(:post, MOCK_URL_HTTP, form: { foo: "bar" }) + assert_requested(:post, MOCK_URL_HTTP, body: { foo: "bar" }) + end + def test_verification_that_non_expected_request_didnt_occur expected_message = Regexp.new( "The request GET #{MOCK_URL_HTTP}/ was not expected to execute but it executed 1 time\n\n" \ diff --git a/lib/httpx/adapters/webmock.rb b/lib/httpx/adapters/webmock.rb index f347d846..bbb8a6fd 100644 --- a/lib/httpx/adapters/webmock.rb +++ b/lib/httpx/adapters/webmock.rb @@ -20,7 +20,7 @@ module WebMock WebMock::RequestSignature.new( request.verb.downcase.to_sym, uri.to_s, - body: request.body, + body: request.body.to_s, headers: request.headers.to_h ) end diff --git a/lib/httpx/transcoder/multipart/encoder.rb b/lib/httpx/transcoder/multipart/encoder.rb index 343bd41e..beeb49cf 100644 --- a/lib/httpx/transcoder/multipart/encoder.rb +++ b/lib/httpx/transcoder/multipart/encoder.rb @@ -18,6 +18,12 @@ module HTTPX "multipart/form-data; boundary=#{@boundary}" end + def to_s + read + ensure + rewind + end + def read(length = nil, outbuf = nil) data = String(outbuf).clear.force_encoding(Encoding::BINARY) if outbuf data ||= "".b diff --git a/sig/transcoder/multipart.rbs b/sig/transcoder/multipart.rbs index 7346f702..bd68d6d8 100644 --- a/sig/transcoder/multipart.rbs +++ b/sig/transcoder/multipart.rbs @@ -28,6 +28,8 @@ module HTTPX def content_type: () -> String + def to_s: () -> String + def read: (?int? length, ?string? buffer) -> String? def rewind: () -> void