From 5e1337e52440c2be059e37c57e62711900b48523 Mon Sep 17 00:00:00 2001 From: emil Date: Fri, 14 Aug 2026 20:30:58 +0200 Subject: [PATCH] DEVX-155: fix: use /dev/shm/docker.sock socket for local dockerd The existing dockerd holds /var/run/docker.sock and can't be killed from inside the container (different PID namespace). Use a new socket path /dev/shm/docker.sock and data root /dev/shm/docker (16G tmpfs). Generated with [Devin](https://devin.ai) Co-Authored-By: Devin <158243242+devin-ai-integration[bot]@users.noreply.github.com> --- src/devx/molecule/start_docker.py | 26 +++++++++++++------------- tests/unit/test_start_docker.py | 4 ++-- 2 files changed, 15 insertions(+), 15 deletions(-) diff --git a/src/devx/molecule/start_docker.py b/src/devx/molecule/start_docker.py index 9913177..dcba628 100644 --- a/src/devx/molecule/start_docker.py +++ b/src/devx/molecule/start_docker.py @@ -23,6 +23,7 @@ Usage:: from __future__ import annotations +import contextlib import glob import os import shutil @@ -223,24 +224,23 @@ def start_docker_daemon(timeout: int = DEFAULT_TIMEOUT) -> bool: click.echo(_("Host Docker not available, starting local dockerd...")) - # Kill any existing dockerd that's using the default data root on the - # CI container's overlay (38G, often 100% full). The new dockerd will - # use /dev/shm/docker (16G tmpfs) which has plenty of space. - subprocess.run( # nosec B603 B607 - ["pkill", "-f", "dockerd"], - capture_output=True, - check=False, - ) - time.sleep(2) + # The existing dockerd (started by the CI image) uses the default data + # root on the CI container's overlay (38G, often 100% full). We can't + # kill it (different PID namespace) or bind to the same socket. Use a + # new socket path and data root on /dev/shm (16G tmpfs). + local_sock = "/dev/shm/docker.sock" # nosec B108 + docker_data_root = "/dev/shm/docker" # nosec B108 - # Reset DOCKER_HOST to host socket for local dockerd - os.environ["DOCKER_HOST"] = f"unix://{DOCKER_SOCK}" + # Remove stale socket if present + with contextlib.suppress(OSError): + os.unlink(local_sock) + + os.environ["DOCKER_HOST"] = f"unix://{local_sock}" # Start local dockerd (requires privileged container) # Use /dev/shm/docker as data root — the CI container's overlay (38G) # is often 100% full, causing image pull failures. /dev/shm is a 16G # tmpfs with plenty of space for molecule test images. - docker_data_root = "/dev/shm/docker" # nosec B108 log_file = tempfile.NamedTemporaryFile( # noqa: SIM115 mode="w", suffix="dockerd.log", delete=False ) @@ -253,7 +253,7 @@ def start_docker_daemon(timeout: int = DEFAULT_TIMEOUT) -> bool: "--data-root", docker_data_root, "-H", - f"unix://{DOCKER_SOCK}", + f"unix://{local_sock}", ], stdout=log_file, stderr=subprocess.STDOUT, diff --git a/tests/unit/test_start_docker.py b/tests/unit/test_start_docker.py index 72be872..e2f4a18 100644 --- a/tests/unit/test_start_docker.py +++ b/tests/unit/test_start_docker.py @@ -257,7 +257,7 @@ class TestStartDockerDaemon: with patch("builtins.open", mock_open(read_data="dockerd error log")): assert start_docker_daemon(timeout=3) is False mock_popen.assert_called_once() - assert mock_sleep.call_count == 4 # 1 pkill + 3 timeout + assert mock_sleep.call_count == 3 @patch("devx.molecule.start_docker.glob.glob", return_value=[]) @patch("devx.molecule.start_docker._diagnose_socket") @@ -311,7 +311,7 @@ class TestStartDockerDaemon: mock_ready.side_effect = [False, False, True] assert start_docker_daemon(timeout=5) is True assert mock_popen.call_count == 1 - assert mock_sleep.call_count == 2 # 1 pkill + 1 timeout + assert mock_sleep.call_count == 1 @patch("devx.molecule.start_docker._diagnose_socket") @patch("devx.molecule.start_docker._get_docker_free_bytes", return_value=100 * 1024**3)