Разобрать или запустить команду оболочки Docker в Python - PullRequest
0 голосов
/ 23 января 2019

Давайте возьмем следующий блестящий прокси yaml в качестве примера:

proxy:
  title: Open Analytics Shiny Proxy
  logo-url: http://www.openanalytics.eu/sites/www.openanalytics.eu/themes/oa/logo.png
  landing-page: /
  heartbeat-rate: 10000
  heartbeat-timeout: 60000
  port: 8080
  authentication: simple
  admin-groups: scientists
  # Example: 'simple' authentication configuration
  users:
  - name: jack
    password: password
    groups: scientists
  - name: jeff
    password: password
    groups: mathematicians
  # Example: 'ldap' authentication configuration
  ldap:
    url: ldap://ldap.forumsys.com:389/dc=example,dc=com
    user-dn-pattern: uid={0}
    group-search-base:
    group-search-filter: (uniqueMember={0})
    manager-dn: cn=read-only-admin,dc=example,dc=com
    manager-password: password
  # Docker configuration
  docker:
    cert-path: /home/none
    url: http://localhost:2375
    port-range-start: 20000
  specs:
  - id: 01_hello
    display-name: Hello Application
    description: Application which demonstrates the basics of a Shiny app
    container-cmd: ["R", "-e", "shinyproxy::run_01_hello()"]
    container-image: openanalytics/shinyproxy-demo
    access-groups: [scientists, mathematicians]
  - id: 06_tabsets
    container-cmd: ["R", "-e", "shinyproxy::run_06_tabsets()"]
    container-image: openanalytics/shinyproxy-demo
    access-groups: scientists

logging:
  file:
    shinyproxy.log

Как мне разобрать ["R", "-e", "shinyproxy::run_06_tabsets()"] в обычной форме exec или напрямую запустить эту команду без разбора в python? Есть ли какая-нибудь библиотека для этого?

EDIT:

Я хочу запустить эту команду в subprocess и завершить ее после истечения времени ожидания или возникновения ошибки при запуске приложения Shiny:

MWE:

from subprocess import Popen, PIPE
from threading import Timer

cmd_from_yaml = ['R', '-e', 'shinyproxy::run_06_tabsets()']
docker_cmd = "docker run -i {0} {1}".format(vol, img)
docker_cmd = docker_cmd.split()
docker_cmd.extend(cmd_from_yaml)
timeout_sec = 10
print("Running command: " + str(" ".join(docker_cmd)))
proc = Popen(docker_cmd, stdout=PIPE, stderr=PIPE, shell=False)

timer = Timer(timeout_sec, proc.kill)
try:
    timer.start()
    stdout, stderr = proc.communicate()
finally:
    timer.cancel()

if stderr:
    proc.kill()
    raise Exception("Error: " + str(stderr))

Терминальный выход:

>>> from subprocess import Popen, PIPE
... from threading import Timer
... 
... cmd_from_yaml = ['R', '-e', 'shinyproxy::run_06_tabsets()']
... docker_cmd = "docker run -i {0} {1}".format(vol, img)
... docker_cmd = docker_cmd.split()
... docker_cmd.extend(cmd_from_yaml)
... timeout_sec = 10
... print("Running command: " + str(" ".join(docker_cmd)))
... proc = Popen(docker_cmd, stdout=PIPE, stderr=PIPE, shell=False)
... 
... timer = Timer(timeout_sec, proc.kill)
... try:
...     timer.start()
...     stdout, stderr = proc.communicate()
... finally:
...     timer.cancel()
... 
... if stderr:
...     proc.kill()
...     raise Exception("Error: " + str(stderr))
... 
Running command: docker run -i openanalytics/shinyproxy-demo R -e shinyproxy::run_06_tabsets()
Traceback (most recent call last):
  File "<input>", line 21, in <module>
Exception: Error: b'Loading required package: shiny\n\nListening on http://0.0.0.0:3838\n'

Примечание. Команда docker run -i openanalytics/shinyproxy-demo R -e "shinyproxy::run_06_tabsets()" будет работать из-за добавления пропущенных цитат, но моя точка зрения в этом вопросе заключается в том, есть ли способ сделать это автоматически без добавления пропущенных цитат вручную, как это делается в docker compose.

...