From 905423e6dabb3b2c778ae46dd767f1baaf7ad8ba Mon Sep 17 00:00:00 2001 From: Devin Bayer Date: Wed, 29 Jun 2016 20:05:47 +0200 Subject: [PATCH] add exec_inspect() info to exec_command return --- dockerpty/__init__.py | 6 ++++-- features/exec_non_interactive.feature | 8 ++++++++ features/steps/step_definitions.py | 14 ++++++++++++-- 3 files changed, 24 insertions(+), 4 deletions(-) diff --git a/dockerpty/__init__.py b/dockerpty/__init__.py index 1dba089..c7cb342 100644 --- a/dockerpty/__init__.py +++ b/dockerpty/__init__.py @@ -32,16 +32,18 @@ def start(client, container, interactive=True, stdout=None, stderr=None, stdin=N def exec_command( client, container, command, interactive=True, stdout=None, stderr=None, stdin=None): - """ - Run provided command via exec API in provided container. + """Run provided command via exec API in provided container. This is just a wrapper for PseudoTerminal(client, container).exec_command() + + Returns a dictionary that allows you to fetch the exit code with exec_command(..)['ExitCode'] """ exec_id = exec_create(client, container, command, interactive=interactive) operation = ExecOperation(client, exec_id, interactive=interactive, stdout=stdout, stderr=stderr, stdin=stdin) PseudoTerminal(client, operation).start() + return client.exec_inspect(exec_id) def start_exec(client, exec_id, interactive=True, stdout=None, stderr=None, stdin=None): diff --git a/features/exec_non_interactive.feature b/features/exec_non_interactive.feature index 766321d..72fe985 100644 --- a/features/exec_non_interactive.feature +++ b/features/exec_non_interactive.feature @@ -53,3 +53,11 @@ Feature: Executing command in a running docker container non-interactively nobody:x:99:99:nobody:/home:/bin/false """ And The container will still be running + + + Scenario: Getting the exit code + Given I am using a TTY + And I run "cat" in a docker container with stdin open + And I start the container + When I exec "sh -c 'exit 4'" in a running docker container + Then the exit code is 4 diff --git a/features/steps/step_definitions.py b/features/steps/step_definitions.py index 2ac575f..47b4ed2 100644 --- a/features/steps/step_definitions.py +++ b/features/steps/step_definitions.py @@ -26,9 +26,10 @@ import time from utils import get_client - +from multiprocessing.queues import SimpleQueue def alloc_pty(ctx, f, *args, **kwargs): + queue = SimpleQueue() pid, fd = pty.fork() if pid == pty.CHILD: @@ -45,7 +46,8 @@ def alloc_pty(ctx, f, *args, **kwargs): # Create a new client for the child process to avoid concurrency issues client = get_client() - f(client, *args, **kwargs) + ret = f(client, *args, **kwargs) + queue.put(ret) sys.exit(0) else: ctx.pty = fd @@ -62,6 +64,9 @@ def alloc_pty(ctx, f, *args, **kwargs): if ctx.exit_code != 0: raise Exception("child process did not finish correctly") + if not queue.empty(): + ctx.return_value = queue.get() + @given('I am using a TTY') def step_impl(ctx): @@ -197,6 +202,11 @@ def step_impl(ctx): expect(actual[-len(wanted):]).to(equal(wanted)) +@then('The exit code is {value}') +def step_impl(ctx, value): + expect(ctx.return_value['ExitCode']).to(equal(int(value))) + + @then('The PTY will be closed cleanly') def step_impl(ctx): if not hasattr(ctx, "exit_code"):