You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I think this is maybe a feature request. WebMock matchers do not work with forking. This makes sense logically given that a web request will change the stub object and trigger copy-on-write. It would be great if there was a way to have the copied stub in the fork send back the recorded requests to the main process stub though.
Ruby 3.3.3
WebMock 3.23.1
require 'webmock'
require 'webmock/rspec'
def fork_code
3.times {
fork do
Net::HTTP.get(URI.parse('http://localhost'))
end
}
Process.waitall
end
def thread_code
3.times {
Thread.new do
Net::HTTP.get(URI.parse('http://localhost'))
end
}
Process.waitall
end
# test
WebMock.enable!
WebMock.disable_net_connect!
stub = WebMock.stub_request(:get, 'localhost').and_return(body: ->(_) { printf 'Called! '; ''} )
fork_code
matcher = WebMock::RequestPatternMatcher.new.times(3)
puts "Does the main process count forked requests? #{matcher.matches?(stub)}"
puts
puts matcher.failure_message
thread_code
matcher = WebMock::RequestPatternMatcher.new.times(3)
puts "Does the main process count threaded requests? #{matcher.matches?(stub)}"
puts
puts matcher.failure_message
~ $ ruby /tmp/fork_spec.rb
Called! Called! Called! Does the main process count forked requests? false
The request GET http://localhost/ was expected to execute 3 times but it executed 0 times
The following requests were made:
No requests were made.
============================================================
Called! Called! Called! Does the main process count threaded requests? true
The request GET http://localhost/ was expected to execute 3 times but it executed 3 times
The following requests were made:
GET http://localhost/ with headers {'Accept'=>'*/*', 'Accept-Encoding'=>'gzip;q=1.0,deflate;q=0.6,identity;q=0.3', 'Host'=>'localhost', 'User-Agent'=>'Ruby'} was made 3 times
============================================================
The text was updated successfully, but these errors were encountered:
@kwstannard I understand the issue and what you're trying to achieve. However, this isn't something WebMock is designed to handle. WebMock uses global registries in the current process's memory and doesn't differentiate between main and subprocesses. The behaviour you're seeing is correct given how forking works.
Here are some ideas on how you could solve that:
Using Inter-Process Communication (IPC) to send WebMock registry data from subprocesses to the main process.
Implementing a shared storage solution (like a database or file) that all processes can access and overwrite WebMock registries to use that storage instead of the default memory storage.
Creating some kind of wrapper around WebMock that's aware of forking, though I'm not sure how this would work.
I think this is maybe a feature request. WebMock matchers do not work with forking. This makes sense logically given that a web request will change the stub object and trigger copy-on-write. It would be great if there was a way to have the copied stub in the fork send back the recorded requests to the main process stub though.
Ruby 3.3.3
WebMock 3.23.1
The text was updated successfully, but these errors were encountered: