feat: add multiprocess support to local mocking #654
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Not sure whether this might interest you ...
This PR enables local mock adapters to be "seen" not just within the ExUnit test process, but also within processes spawned by the ExUnit test process. No code changes are required within tests that use
Tesla.Mock
.This is accomplished by adding the ProcessTree library to mix.exs, and invoking
ProcessTree.get/1
from withinTesla.Mock.pdict_get/0
.Via ProcessTree, code running in child processes can access data stored in the process dictionaries of parent processes, in most circumstances (as discussed further below).
As used here, the result is that processes spawned by the ExUnit test pid can "see" the local mock adapter, but other tests and their child processes cannot.
async: true
is preserved.Limitations
ProcessTree is able to return a meaningful answer in most real-world circumstances. For example, when the processes in question are running in a supervision tree, ProcessTree will always be able to return an answer. Beyond that, things depend on factors including:
Further discussion can be found here: https://saltycrackers.dev/posts/how-to-get-the-parent-of-an-elixir-process/
Detection/messaging of error circumstances
Helpful error messaging is the trickiest part of this PR.
As was the case prior to this PR, if
Mock.call()
fails to find an adapter when the code is running within the ExUnit test process, we display the same error message as before:If, however, the code calling
Mock.call()
is not running within the ExUnit test process, that can mean one of three things:Mock.call()
has been called within such a process.Mock.call()
has been called within a process not spawned by the ExUnit test pid.We're unable to distinguish between these situations, so the error messaging is a bit awkward - I've given it my best shot for your review.