Skip to content

Commit 94a63d6

Browse files
Merge pull request #337 from backmarket-oss/master
feat(compose): allow running specific services in compose
2 parents c8d0ea6 + f4c3ce4 commit 94a63d6

File tree

2 files changed

+43
-4
lines changed

2 files changed

+43
-4
lines changed

compose/testcontainers/compose/__init__.py

+11-3
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
1-
import requests
21
import subprocess
32
from typing import Iterable, List, Optional, Tuple, Union
43

5-
from testcontainers.core.waiting_utils import wait_container_is_ready
4+
import requests
5+
66
from testcontainers.core.exceptions import NoSuchPortExposed
7+
from testcontainers.core.waiting_utils import wait_container_is_ready
78

89

910
class DockerCompose:
@@ -16,6 +17,7 @@ class DockerCompose:
1617
pull: Pull images before launching environment.
1718
build: Build images referenced in the configuration file.
1819
env_file: Path to an env file containing environment variables to pass to docker compose.
20+
services: List of services to start.
1921
2022
Example:
2123
@@ -38,19 +40,23 @@ class DockerCompose:
3840
hello-world:
3941
image: "hello-world"
4042
"""
43+
4144
def __init__(
4245
self,
4346
filepath: str,
4447
compose_file_name: Union[str, Iterable] = "docker-compose.yml",
4548
pull: bool = False,
4649
build: bool = False,
47-
env_file: Optional[str] = None) -> None:
50+
env_file: Optional[str] = None,
51+
services: Optional[List[str]] = None
52+
) -> None:
4853
self.filepath = filepath
4954
self.compose_file_names = [compose_file_name] if isinstance(compose_file_name, str) else \
5055
list(compose_file_name)
5156
self.pull = pull
5257
self.build = build
5358
self.env_file = env_file
59+
self.services = services
5460

5561
def __enter__(self) -> "DockerCompose":
5662
self.start()
@@ -84,6 +90,8 @@ def start(self) -> None:
8490
up_cmd = self.docker_compose_command() + ['up', '-d']
8591
if self.build:
8692
up_cmd.append('--build')
93+
if self.services:
94+
up_cmd.extend(self.services)
8795

8896
self._call_command(cmd=up_cmd)
8997

compose/tests/test_docker_compose.py

+32-1
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88
from testcontainers.core.exceptions import NoSuchPortExposed
99
from testcontainers.core.waiting_utils import wait_for_logs
1010

11-
1211
ROOT = os.path.dirname(__file__)
1312

1413

@@ -40,6 +39,38 @@ def test_can_build_images_before_spawning_service_via_compose():
4039
assert "--build" in docker_compose_cmd
4140

4241

42+
def test_can_specify_services():
43+
with patch.object(DockerCompose, "_call_command") as call_mock:
44+
with DockerCompose(ROOT, services=["hub", "firefox"]) as compose:
45+
...
46+
47+
assert compose.services
48+
docker_compose_cmd = call_mock.call_args_list[0][1]["cmd"]
49+
services_at_the_end = docker_compose_cmd[-2:]
50+
assert "firefox" in services_at_the_end
51+
assert "hub" in services_at_the_end
52+
assert "chrome" not in docker_compose_cmd
53+
54+
55+
@pytest.mark.parametrize("should_run_hub", [
56+
[True],
57+
[False],
58+
])
59+
def test_can_run_specific_services(should_run_hub: bool):
60+
# compose V2 will improve this test by being able to assert that "firefox" also started/exited
61+
services = ["firefox"]
62+
if should_run_hub:
63+
services.append("hub")
64+
65+
with DockerCompose(ROOT, services=services) as compose:
66+
if should_run_hub:
67+
assert compose.get_service_host("hub", 4444)
68+
assert compose.get_service_port("hub", 4444)
69+
else:
70+
with pytest.raises(NoSuchPortExposed):
71+
assert compose.get_service_host("hub", 4444)
72+
73+
4374
def test_can_throw_exception_if_no_port_exposed():
4475
with DockerCompose(ROOT) as compose:
4576
with pytest.raises(NoSuchPortExposed):

0 commit comments

Comments
 (0)