def run_singularity_container_executable(container_image, executable_path, args_dict): """Launch an executable within a Singularity container. Args: container_image: A string containing the name of the container to pull. executable_path: A string containing the path of the executable to execute within the container. args_dict: A dictionary containing arguments and corresponding values. """ # Import Singularity library from spython.main import Client as client # Pull the specified container. This pull in the latest version of # the container (with the specified tag if provided). singularity_image = client.pull(container_image) # Run the executable with the arguments # TODO how do we get logs? client.run( singularity_image, [executable_path, json.dumps(args_dict)], ) # TODO give a real return value return "FINISHED"
def singularity_run(image_path, path_bind, args_list, container_dir='/tmp', return_results=True, use_ephemeral_space=False, dry_run=False): ''' A wrapper module for running singularity based containers :param image_path: Singularrity image path :param path_bind: Path to bind to singularity /tmp dir :param args_list: List of args for singulatiy run :param return_results: Return singulatiy run results, default True :param use_ephemeral_space: Toggle for using ephemeral space for temp dir, default False :param dry_run: Return the singularity command without run, default False :returns: A response from container run and a string containing singularity command line ''' try: check_file_path(image_path) check_file_path(path_bind) temp_dir = get_temp_dir(use_ephemeral_space=use_ephemeral_space) res = None temp_image_path = \ os.path.join( temp_dir, os.path.basename(image_path)) copy_local_file(image_path, temp_image_path) # copy image to tmp dir if not isinstance(args_list,list) and \ len(args_list) > 0: raise ValueError( 'No args provided for singularity run') # safemode args = ' '.join(args_list) # flatten args singularity_run_cmd = \ 'singularity run {0} --bind {1}:{2} {3}'.\ format( temp_image_path, path_bind, container_dir, args) if dry_run: return res, singularity_run_cmd else: res = \ Client.run( image=temp_image_path, bind='{0}:{1}'.format(path_bind,container_dir), args=args, return_result=return_results) remove_dir(temp_dir) # remove copied image after run return res, singularity_run_cmd except Exception as e: raise ValueError( 'Failed to run image {0}, error: {1}'.\ format(image_path,e))
def test_pull_and_run(tmp_path): image = Client.pull("shub://vsoch/singularity-images", pull_folder=str(tmp_path)) print(image) assert os.path.exists(image) ext = 'sif' if Client.version_info().major >= 3 else 'simg' assert image == str(tmp_path / ('singularity-images.' + ext)) result = Client.run(image) print(result) assert 'You say please, but all I see is pizza..' in result
def _try_to_stream(self, args, stream_command='run'): self._bindings_as_option() try: if stream_command == 'run': for line in Client.run(Client.instance(self.image), args=args, options=self.options, stream=True, return_result=True): yield line elif stream_command == 'execute': for line in Client.execute(self.image, command=args['command'].split(' '), options=self.options, stream=True, quiet=False): yield line except CalledProcessError: # pragma: no cover return
def _run(self, *args, **kwargs): # This function should run in a background thread kwargs = kwargs.copy() kwargs['image'] = self.image # Always stream kwargs['stream'] = True # spython will error if we don't return the result... kwargs['return_result'] = True self._stream_command = client.run(**kwargs) # Write logs as they come in for output in self._stream_command: with self._logs_lock: self._logs.append(output) self._stream_command = None
def singularity_start(self, image): """Starts a singularity instance based on the image. """ env_vars = self.action.get('env', {}) for s in self.action.get('secrets', []): env_vars.update({s: os.environ[s]}) for e, v in self.env.items(): env_vars.update({e: v}) env_vars.update({'HOME': os.environ['HOME']}) # sets the env variables for k, v in env_vars.items(): Client.setenv(k, v) e = Client.run(image=self.generate_image_name(image), args=' '.join(self.action.get('args', '')), return_result=True) return e['return_code']