# Copyright (C) 2017-2022 Vanessa Sochat.
# This Source Code Form is subject to the terms of the
# Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed
# with this file, You can obtain one at http://mozilla.org/MPL/2.0/.
from spython.logger import bot
from spython.utils import stream_command, which
import os
[docs]def execute(
self,
image=None,
command=None,
app=None,
writable=False,
contain=False,
bind=None,
stream=False,
nv=False,
return_result=False,
options=None,
singularity_options=None,
sudo=False,
sudo_options=None,
quiet=True,
environ=None,
):
"""execute: send a command to a container
Parameters
==========
image: full path to singularity image
command: command to send to container
app: if not None, execute a command in context of an app
writable: This option makes the file system accessible as read/write
contain: This option disables the automatic sharing of writable
filesystems on your host
options: an optional list of options to provide to execute.
singularity_options: a list of options to provide to the singularity client
bind: list or single string of bind paths.
This option allows you to map directories on your host system to
directories within your container using bind mounts
nv: if True, load Nvidia Drivers in runtime (default False)
return_result: if True, return entire json object with return code
and message result not (default)
quiet: Do not print verbose output.
environ: extra environment to add.
"""
from spython.utils import check_install
check_install()
cmd = self._init_command("exec", singularity_options)
# nv option leverages any GPU cards
if nv:
cmd += ["--nv"]
# If the image is given as a list, it's probably the command
if isinstance(image, list):
command = image
image = None
if command is not None:
# No image provided, default to use the client's loaded image
if image is None:
image = self._get_uri()
self.quiet = True
# If an instance is provided, grab it's name
if isinstance(image, self.instance):
image = image.get_uri()
# If image is still None, not defined by user or previously with client
if image is None:
bot.exit("Please load or provide an image.")
# Does the user want to use bind paths option?
if bind is not None:
cmd += self._generate_bind_list(bind)
# Does the user want to run an app?
if app is not None:
cmd = cmd + ["--app", app]
if writable:
cmd.append("--writable")
# Add additional options
if options is not None:
cmd = cmd + options
if not isinstance(command, list):
command = command.split(" ")
cmd = cmd + [image] + command
# Does the user want to see the command printed?
if not (quiet or self.quiet):
bot.info(" ".join(cmd))
if not stream:
return self._run_command(
cmd,
sudo=sudo,
sudo_options=sudo_options,
return_result=return_result,
quiet=quiet,
environ=environ,
)
return stream_command(cmd, sudo=sudo, sudo_options=sudo_options)
bot.exit("Please include a command (list) to execute.")
[docs]def shell(
self,
image,
app=None,
writable=False,
contain=False,
bind=None,
nv=False,
options=None,
singularity_options=None,
sudo=False,
quiet=True,
):
"""shell into a container. A user is advised to use singularity to do
this directly, however this function is useful for supporting tools.
Parameters
==========
image: full path to singularity image
app: if not None, execute a shell in context of an app
writable: This option makes the file system accessible as read/write
contain: This option disables the automatic sharing of writable
filesystems on your host
options: an optional list of options to provide to shell.
singularity_options: a list of options to provide to the singularity client
bind: list or single string of bind paths.
This option allows you to map directories on your host system to
directories within your container using bind mounts
nv: if True, load Nvidia Drivers in runtime (default False)
"""
from spython.utils import check_install
check_install()
cmd = self._init_command("shell", singularity_options)
# nv option leverages any GPU cards
if nv:
cmd += ["--nv"]
# Does the user want to use bind paths option?
if bind is not None:
cmd += self._generate_bind_list(bind)
# Does the user want to run an app?
if app is not None:
cmd = cmd + ["--app", app]
# Add additional options
if options is not None:
cmd = cmd + options
if writable:
cmd.append("--writable")
# Finally, add the image or uri
cmd.append(image)
singularity = which("singularity")
# Does the user want to see the command printed?
if not (quiet or self.quiet):
bot.info(" ".join(cmd))
if writable or sudo:
os.execvp("sudo", ["sudo"] + cmd)
else:
os.execvp(singularity, cmd)