Repository: PrefectHQ/prefect

Issue:
Improve error message when Docker is not running and Prefect tries to build a Docker image
### First check

- [X] I added a descriptive title to this issue.
- [X] I used the GitHub search to find a similar request and didn't find it.
- [X] I searched the Prefect documentation for this feature.

### Prefect Version

2.x

### Describe the current behavior

Trying to rund `flow.deploy` to build an image results in the following error if Docker is not running:

```bash
Traceback (most recent call last):
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/urllib3/connectionpool.py", line 793, in urlopen
    response = self._make_request(
               ^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/urllib3/connectionpool.py", line 496, in _make_request
    conn.request(
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/urllib3/connection.py", line 400, in request
    self.endheaders()
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/http/client.py", line 1289, in endheaders
    self._send_output(message_body, encode_chunked=encode_chunked)
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/http/client.py", line 1048, in _send_output
    self.send(msg)
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/http/client.py", line 986, in send
    self.connect()
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/transport/unixconn.py", line 27, in connect
    sock.connect(self.unix_socket)
FileNotFoundError: [Errno 2] No such file or directory

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/requests/adapters.py", line 486, in send
    resp = conn.urlopen(
           ^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/urllib3/connectionpool.py", line 847, in urlopen
    retries = retries.increment(
              ^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/urllib3/util/retry.py", line 470, in increment
    raise reraise(type(error), error, _stacktrace)
          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/urllib3/util/util.py", line 38, in reraise
    raise value.with_traceback(tb)
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/urllib3/connectionpool.py", line 793, in urlopen
    response = self._make_request(
               ^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/urllib3/connectionpool.py", line 496, in _make_request
    conn.request(
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/urllib3/connection.py", line 400, in request
    self.endheaders()
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/http/client.py", line 1289, in endheaders
    self._send_output(message_body, encode_chunked=encode_chunked)
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/http/client.py", line 1048, in _send_output
    self.send(msg)
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/http/client.py", line 986, in send
    self.connect()
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/transport/unixconn.py", line 27, in connect
    sock.connect(self.unix_socket)
urllib3.exceptions.ProtocolError: ('Connection aborted.', FileNotFoundError(2, 'No such file or directory'))

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/api/client.py", line 214, in _retrieve_server_version
    return self.version(api_version=False)["ApiVersion"]
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/api/daemon.py", line 181, in version
    return self._result(self._get(url), json=True)
                        ^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/utils/decorators.py", line 46, in inner
    return f(self, *args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/api/client.py", line 237, in _get
    return self.get(url, **self._set_request_timeout(kwargs))
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/requests/sessions.py", line 602, in get
    return self.request("GET", url, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/requests/sessions.py", line 589, in request
    resp = self.send(prep, **send_kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/requests/sessions.py", line 703, in send
    r = adapter.send(request, **kwargs)
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/requests/adapters.py", line 501, in send
    raise ConnectionError(err, request=request)
requests.exceptions.ConnectionError: ('Connection aborted.', FileNotFoundError(2, 'No such file or directory'))

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/Users/jeffhale/Desktop/prefect/demos/deploy_demo/get_weather.py", line 17, in <module>
    fetch_weather.deploy(
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/utilities/asyncutils.py", line 255, in coroutine_wrapper
    return call()
           ^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/_internal/concurrency/calls.py", line 398, in __call__
    return self.result()
           ^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/_internal/concurrency/calls.py", line 284, in result
    return self.future.result(timeout=timeout)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/_internal/concurrency/calls.py", line 168, in result
    return self.__get_result()
           ^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/concurrent/futures/_base.py", line 401, in __get_result
    raise self._exception
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/_internal/concurrency/calls.py", line 355, in _run_async
    result = await coro
             ^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/flows.py", line 1001, in deploy
    deployment_ids = await deploy(
                     ^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/deployments/runner.py", line 831, in deploy
    image.build()
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/deployments/runner.py", line 698, in build
    build_image(**build_kwargs)
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/contextlib.py", line 81, in inner
    return func(*args, **kwds)
           ^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/utilities/dockerutils.py", line 159, in build_image
    with docker_client() as client:
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/contextlib.py", line 137, in __enter__
    return next(self.gen)
           ^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/prefect/utilities/dockerutils.py", line 108, in docker_client
    client = docker.DockerClient.from_env()
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/client.py", line 96, in from_env
    return cls(
           ^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/client.py", line 45, in __init__
    self.api = APIClient(*args, **kwargs)
               ^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/api/client.py", line 197, in __init__
    self._version = self._retrieve_server_version()
                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/opt/homebrew/Caskroom/miniforge/base/lib/python3.11/site-packages/docker/api/client.py", line 221, in _retrieve_server_version
    raise DockerException(
docker.errors.DockerException: Error while fetching server API version: ('Connection aborted.', FileNotFoundError(2, 'No such file or directory'))
```

### Describe the proposed behavior

Catch the exception and return a more human-readable error that suggests the user check whether Docker is running.

### Example Use

_No response_

### Additional context

We observed several users encounter this error and get confused about its meaning at a PACC. I have also stumbled over it in the past. 

Might want to do something similar for the exception discussed in [issue #9337](https://github.com/PrefectHQ/prefect/issues/9337).


Discussion:
@serinamarie can you assign it to me? would love to take it as a first issue.
@discdiver can you assign this issue to me?

Assigned. Thank you @eladm26! You can check out the contributor docs[ here](https://docs.prefect.io/latest/contributing/overview/). Please let us know if you encounter any issues or anything in the docs could be improved.
This is how the new error will look, I added the error:  `Docker is not running. please run docker and try again`
```
Running deployment build steps...
 > Running build_docker_image step...
Traceback (most recent call last):
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/urllib3/connectionpool.py", line 791, in urlopen
    response = self._make_request(
               ^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/urllib3/connectionpool.py", line 497, in _make_request
    conn.request(
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/urllib3/connection.py", line 395, in request
    self.endheaders()
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/lib/python3.11/http/client.py", line 1277, in endheaders
    self._send_output(message_body, encode_chunked=encode_chunked)
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/lib/python3.11/http/client.py", line 1037, in _send_output
    self.send(msg)
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/lib/python3.11/http/client.py", line 975, in send
    self.connect()
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/transport/unixconn.py", line 27, in connect
    sock.connect(self.unix_socket)
ConnectionRefusedError: [Errno 61] Connection refused

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/requests/adapters.py", line 486, in send
    resp = conn.urlopen(
           ^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/urllib3/connectionpool.py", line 845, in urlopen
    retries = retries.increment(
              ^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/urllib3/util/retry.py", line 470, in increment
    raise reraise(type(error), error, _stacktrace)
          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/urllib3/util/util.py", line 38, in reraise
    raise value.with_traceback(tb)
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/urllib3/connectionpool.py", line 791, in urlopen
    response = self._make_request(
               ^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/urllib3/connectionpool.py", line 497, in _make_request
    conn.request(
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/urllib3/connection.py", line 395, in request
    self.endheaders()
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/lib/python3.11/http/client.py", line 1277, in endheaders
    self._send_output(message_body, encode_chunked=encode_chunked)
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/lib/python3.11/http/client.py", line 1037, in _send_output
    self.send(msg)
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/lib/python3.11/http/client.py", line 975, in send
    self.connect()
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/transport/unixconn.py", line 27, in connect
    sock.connect(self.unix_socket)
urllib3.exceptions.ProtocolError: ('Connection aborted.', ConnectionRefusedError(61, 'Connection refused'))

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/api/client.py", line 214, in _retrieve_server_version
    return self.version(api_version=False)["ApiVersion"]
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/api/daemon.py", line 181, in version
    return self._result(self._get(url), json=True)
                        ^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/utils/decorators.py", line 46, in inner
    return f(self, *args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/api/client.py", line 237, in _get
    return self.get(url, **self._set_request_timeout(kwargs))
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/requests/sessions.py", line 602, in get
    return self.request("GET", url, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/requests/sessions.py", line 589, in request
    resp = self.send(prep, **send_kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/requests/sessions.py", line 703, in send
    r = adapter.send(request, **kwargs)
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/requests/adapters.py", line 501, in send
    raise ConnectionError(err, request=request)
requests.exceptions.ConnectionError: ('Connection aborted.', ConnectionRefusedError(61, 'Connection refused'))

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/Users/eladmoshe/Projects/prefect/src/prefect/utilities/dockerutils.py", line 110, in docker_client
    client = docker.DockerClient.from_env()
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/client.py", line 96, in from_env
    return cls(
           ^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/client.py", line 45, in __init__
    self.api = APIClient(*args, **kwargs)
               ^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/api/client.py", line 197, in __init__
    self._version = self._retrieve_server_version()
                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/docker/api/client.py", line 221, in _retrieve_server_version
    raise DockerException(
docker.errors.DockerException: Error while fetching server API version: ('Connection aborted.', ConnectionRefusedError(61, 'Connection refused'))

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/Users/eladmoshe/Projects/prefect/src/prefect/deployments/steps/core.py", line 154, in run_steps
    step_output = await run_step(step, upstream_outputs)
                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/deployments/steps/core.py", line 125, in run_step
    result = await from_async.call_soon_in_new_thread(
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/_internal/concurrency/calls.py", line 294, in aresult
    return await asyncio.wrap_future(self.future)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/greenback/_impl.py", line 211, in _greenback_shim
    next_send = outcome.Value((yield next_yield))
                               ^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/_internal/concurrency/calls.py", line 319, in _run_sync
    result = self.fn(*self.args, **self.kwargs)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/_internal/compatibility/deprecated.py", line 155, in wrapper
    return fn(*args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/envs/prefect/lib/python3.11/site-packages/prefect_docker/deployments/steps.py", line 200, in build_docker_image
    with docker_client() as client:
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/lib/python3.11/contextlib.py", line 137, in __enter__
    return next(self.gen)
           ^^^^^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/utilities/dockerutils.py", line 114, in docker_client
    raise RuntimeError("Docker is not running. please run docker and try again")
**RuntimeError: Docker is not running. please run docker and try again**

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "/Users/eladmoshe/Projects/prefect/src/prefect/cli/_utilities.py", line 41, in wrapper
    return fn(*args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/utilities/asyncutils.py", line 259, in coroutine_wrapper
    return call()
           ^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/_internal/concurrency/calls.py", line 407, in __call__
    return self.result()
           ^^^^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/_internal/concurrency/calls.py", line 285, in result
    return self.future.result(timeout=timeout)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/_internal/concurrency/calls.py", line 169, in result
    return self.__get_result()
           ^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/.pyenv/versions/3.11.0/lib/python3.11/concurrent/futures/_base.py", line 401, in __get_result
    raise self._exception
  File "/Users/eladmoshe/Projects/prefect/src/prefect/_internal/concurrency/calls.py", line 364, in _run_async
    result = await coro
             ^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/cli/deploy.py", line 293, in deploy
    await _run_multi_deploy(
  File "/Users/eladmoshe/Projects/prefect/src/prefect/cli/deploy.py", line 800, in _run_multi_deploy
    await _run_single_deploy(
  File "/Users/eladmoshe/Projects/prefect/src/prefect/client/utilities.py", line 51, in with_injected_client
    return await fn(*args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/eladmoshe/Projects/prefect/src/prefect/cli/deploy.py", line 619, in _run_single_deploy
    await run_steps(build_steps, step_outputs, print_function=app.console.print)
  File "/Users/eladmoshe/Projects/prefect/src/prefect/deployments/steps/core.py", line 182, in run_steps
    raise StepExecutionError(f"Encountered error while running {fqn}") from exc
prefect.deployments.steps.core.StepExecutionError: Encountered error while running prefect_docker.deployments.steps.build_docker_image

```

Resolving patch:
diff --git a/src/prefect/utilities/dockerutils.py b/src/prefect/utilities/dockerutils.py
--- a/src/prefect/utilities/dockerutils.py
+++ b/src/prefect/utilities/dockerutils.py
@@ -104,13 +104,18 @@ def silence_docker_warnings() -> Generator[None, None, None]:
 @contextmanager
 def docker_client() -> Generator["DockerClient", None, None]:
     """Get the environmentally-configured Docker client"""
-    with silence_docker_warnings():
-        client = docker.DockerClient.from_env()
-
+    client = None
     try:
-        yield client
+        with silence_docker_warnings():
+            client = docker.DockerClient.from_env()
+
+            yield client
+    except docker.errors.DockerException as exc:
+        raise RuntimeError(
+            "This error is often thrown because Docker is not running. Please ensure Docker is running."
+        ) from exc
     finally:
-        client.close()
+        client is not None and client.close()
 
 
 class BuildError(Exception):


Test patch:
diff --git a/tests/utilities/test_importtools.py b/tests/utilities/test_importtools.py
--- a/tests/utilities/test_importtools.py
+++ b/tests/utilities/test_importtools.py
@@ -3,6 +3,7 @@
 import sys
 from pathlib import Path
 from types import ModuleType
+from unittest.mock import MagicMock
 from uuid import uuid4
 
 import pytest
@@ -71,6 +72,19 @@ def test_lazy_import():
     assert callable(docker.from_env)
 
 
+@pytest.mark.service("docker")
+def test_cant_find_docker_error(monkeypatch):
+    docker = lazy_import("docker")
+    docker.errors = lazy_import("docker.errors")
+    monkeypatch.setattr(
+        "docker.DockerClient.from_env",
+        MagicMock(side_effect=docker.errors.DockerException),
+    )
+    with pytest.raises(RuntimeError, match="Docker is not running"):
+        with docker_client() as _:
+            return None
+
+
 @pytest.mark.service("docker")
 def test_lazy_import_does_not_break_type_comparisons():
     docker = lazy_import("docker")