summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaniil Sigalov <asterite@seclab.cs.msu.ru>2020-12-20 15:44:01 +0300
committerDaniil Sigalov <asterite@seclab.cs.msu.ru>2020-12-20 15:58:58 +0300
commit1b5278f977cef828546e00a49c2d1687ca0532aa (patch)
tree83ab78fbd3522a3b6f20d0b08718c94b26082b9f
parent8034bc3bd6849e28bdb9823a2feb3b3f8fc07c40 (diff)
Only attach services we'll read logs from in up
When 'up' is run with explicit list of services, compose will start them together with their dependencies. It will attach to all started services, but won't read output from dependencies (their logs are not printed by 'up') - so the receive buffer of dependencies will fill and at some point will start blocking those services. Fix that by only attaching to services given in the list. To do that, move logic of choosing which services to attach from cli/main.py to utils.py and use it from project.py to decide if service should be attached. Fixes #6018 Signed-off-by: Daniil Sigalov <asterite@seclab.cs.msu.ru>
-rw-r--r--compose/cli/main.py14
-rw-r--r--compose/project.py11
-rw-r--r--compose/utils.py15
3 files changed, 31 insertions, 9 deletions
diff --git a/compose/cli/main.py b/compose/cli/main.py
index 9b2a5d0b..c0fe3bb4 100644
--- a/compose/cli/main.py
+++ b/compose/cli/main.py
@@ -38,6 +38,7 @@ from ..service import ConvergenceStrategy
from ..service import ImageType
from ..service import NeedsBuildError
from ..service import OperationFailedError
+from ..utils import filter_attached_for_up
from .command import get_config_from_options
from .command import get_project_dir
from .command import project_from_options
@@ -1071,6 +1072,7 @@ class TopLevelCommand:
renew_anonymous_volumes=options.get('--renew-anon-volumes'),
silent=options.get('--quiet-pull'),
cli=native_builder,
+ attach_dependencies=attach_dependencies,
)
try:
@@ -1401,13 +1403,11 @@ def log_printer_from_project(
def filter_attached_containers(containers, service_names, attach_dependencies=False):
- if attach_dependencies or not service_names:
- return containers
-
- return [
- container
- for container in containers if container.service in service_names
- ]
+ return filter_attached_for_up(
+ containers,
+ service_names,
+ attach_dependencies,
+ lambda container: container.service)
@contextlib.contextmanager
diff --git a/compose/project.py b/compose/project.py
index 9b21e1cd..3bc73828 100644
--- a/compose/project.py
+++ b/compose/project.py
@@ -39,6 +39,7 @@ from .service import Service
from .service import ServiceIpcMode
from .service import ServiceNetworkMode
from .service import ServicePidMode
+from .utils import filter_attached_for_up
from .utils import microseconds_from_time_nano
from .utils import truncate_string
from .volume import ProjectVolumes
@@ -645,6 +646,7 @@ class Project:
silent=False,
cli=False,
one_off=False,
+ attach_dependencies=False,
override_options=None,
):
@@ -671,12 +673,17 @@ class Project:
one_off=service_names if one_off else [],
)
- def do(service):
+ services_to_attach = filter_attached_for_up(
+ services,
+ service_names,
+ attach_dependencies,
+ lambda service: service.name)
+ def do(service):
return service.execute_convergence_plan(
plans[service.name],
timeout=timeout,
- detached=detached,
+ detached=detached or (service not in services_to_attach),
scale_override=scale_override.get(service.name),
rescale=rescale,
start=start,
diff --git a/compose/utils.py b/compose/utils.py
index 060ba50c..86af8f88 100644
--- a/compose/utils.py
+++ b/compose/utils.py
@@ -174,3 +174,18 @@ def truncate_string(s, max_chars=35):
if len(s) > max_chars:
return s[:max_chars - 2] + '...'
return s
+
+
+def filter_attached_for_up(items, service_names, attach_dependencies=False,
+ item_to_service_name=lambda x: x):
+ """This function contains the logic of choosing which services to
+ attach when doing docker-compose up. It may be used both with containers
+ and services, and any other entities that map to service names -
+ this mapping is provided by item_to_service_name."""
+ if attach_dependencies or not service_names:
+ return items
+
+ return [
+ item
+ for item in items if item_to_service_name(item) in service_names
+ ]