bg-helper 0.1.24
CLI helpers for background tasks (shell), docker (databases), git, and SSH
License: MIT
Keywords: background, shell, git, ssh, docker, pyenv, redis, mongodb, postgres, postgresql, mysql, helper, kenjyco

``bg-helper`` is a Python library that provides production-ready shell
command orchestration, Docker service management, git repository
automation, and more. It offers three core execution primitives
(``run``, ``run_output``, ``run_or_die``) with universal timeout
protection and error handling, plus specialized tools for managing
Docker containers (PostgreSQL, MySQL, Redis, MongoDB), git operations
with automatic context management, and Python environment automation via
pyenv. Rather than hiding complexity behind abstractions, ``bg-helper``
provides powerful primitives for shell command orchestration, background
task management, and DevOps workflow automation. You can always pass
``show=True`` to see the actual commands being executed, learn the
underlying tools, and build transferable skills while providing
comprehensive error capture and background task management.

**Who benefits from this?** - **DevOps engineers** who need reliable
automation for git repositories, Docker containers, and development
environments - **Systems administrators** who want Python’s power while
preserving shell command fidelity - **Infrastructure teams** building
automation that must be debuggable, maintainable, and transparent -
**Library developers** who need robust local integration testing with
multiple database services and Python versions - **Anyone** who has been
burned by “magic” tools and wants infrastructure code that reveals
rather than conceals its operations

``bg-helper`` fits naturally into existing toolchains by wrapping and
enhancing familiar tools (git, docker, ssh) rather than replacing them.
It’s designed for REPL-driven exploration that gradually evolves into
production automation.

**Particularly useful for integration testing:** The Docker service
functions enable easy local testing across multiple database types
(PostgreSQL, MySQL, Redis, MongoDB), while the pyenv functions support
testing across Python versions. The
``pyenv_create_venvs_for_py_versions_and_dep_versions`` function is
especially powerful for creating test matrices across Python versions
and dependency combinations, as demonstrated in libraries like
sql-helper.

Install
-------

::

   pip install bg-helper

QuickStart
----------

.. code:: python

   import bg_helper as bh

   # Safe command execution with timeout protection and error capture
   result = bh.run_output('ls -la', show=True)  # Shows actual command executed
   print(result)

   # Comprehensive error handling for any function
   error_info = bh.call_func(lambda: 1/0)
   if error_info['status'] == 'error':
       print(f"Function failed: {error_info['error_type']}")
       print(f"Full traceback: {error_info['traceback_string']}")

   # Git operations with automatic repository context management
   branch = bh.tools.git_current_branch(show=True)  # Learn the actual git commands
   print(f"Current branch: {branch}")

   # Docker service management with intelligent fallback logic
   success = bh.tools.docker_postgres_start(
       name='dev-db',
       port=5432,
       show=True  # See exactly what Docker commands are executed
   )

   # Background task execution with comprehensive error logging
   task = bh.SimpleBackgroundTask('long-running-command --with-args')

**What you gain:** Reliable shell command orchestration with
production-grade error handling, automatic resource cleanup, timeout
protection, and complete operational transparency. Every operation can
show you the exact commands being executed, making debugging and
learning seamless.

API Overview
------------

Core Execution Primitives
~~~~~~~~~~~~~~~~~~~~~~~~~

These three functions form the foundation for all shell command
operations, providing graduated levels of strictness:

-  **``run(cmd, stderr_to_stdout=False, debug=False, timeout=None, exception=False, show=False)``**
   - Execute a shell command and return the exit status

   -  ``cmd``: Shell command string to execute
   -  ``stderr_to_stdout``: Redirect stderr to stdout if True
   -  ``debug``: Insert pdb breakpoint before execution if True
   -  ``timeout``: Seconds to wait before stopping command (prevents
      hanging)
   -  ``exception``: Raise exception on non-zero exit status if True
   -  ``show``: Display the actual command before execution if True
   -  Returns: Integer exit status
   -  Internal calls: None

-  **``run_output(cmd, strip=True, debug=False, timeout=None, exception=False, show=False)``**
   - Execute a shell command and return its output

   -  ``cmd``: Shell command string to execute
   -  ``strip``: Remove leading/trailing whitespace from output if True
   -  ``debug``: Insert pdb breakpoint before execution if True
   -  ``timeout``: Seconds to wait before stopping command
   -  ``exception``: Raise exception on command failure if True
   -  ``show``: Display the actual command before execution if True
   -  Returns: Command output as string
   -  Internal calls: None

-  **``run_or_die(cmd, stderr_to_stdout=False, debug=False, timeout=None, exception=True, show=False)``**
   - Execute a shell command with strict error handling—fail fast on any
   error

   -  ``cmd``: Shell command string to execute
   -  ``stderr_to_stdout``: Redirect stderr to stdout if True
   -  ``debug``: Insert pdb breakpoint before execution if True
   -  ``timeout``: Seconds to wait before stopping command
   -  ``exception``: If True (default), raise exception on failure; if
      False, exit process
   -  ``show``: Display the actual command before execution if True
   -  Returns: Integer exit status (only on success)
   -  Internal calls: None

Error Handling and Background Tasks
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

-  **``call_func(func, *args, **kwargs)``** - Execute any Python
   function with comprehensive error capture and forensic information

   -  ``func``: Python function to execute
   -  ``*args``: Arguments to pass to function
   -  ``**kwargs``: Keyword arguments (special kwargs: ``logger``,
      ``verbose``)
   -  Returns: Dictionary with keys: ``func_name``, ``args``,
      ``kwargs``, ``status`` (always present); ``value`` (on success);
      ``error_type``, ``error_value``, ``traceback_string``, ``fqdn``,
      ``time_epoch``, ``time_string``, ``func_doc``, ``func_module`` (on
      error)
   -  Internal calls: None

-  **``SimpleBackgroundTask(func, *args, **kwargs)``** - Execute a
   function or shell command in a background daemon thread with
   automatic error logging

   -  ``func``: Python callable or shell command string
   -  ``*args``: Arguments for callable (ignored for shell commands)
   -  ``**kwargs``: Keyword arguments for callable
   -  Returns: Background task object (daemon threads won’t prevent
      process exit)
   -  Internal calls: ``call_func()``

Git Operations (``bh.tools.*``)
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

Git functions provide repository automation with automatic context
management and state isolation.

-  **``ctx_repo_path_root(path, fetch=False, debug=False, timeout=None, exception=True, show=False)``**
   - Context manager that changes to the root directory of a git
   repository

   -  ``path``: Path to file or directory in git repository
   -  ``fetch``: Execute ``git fetch`` after changing directory if True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if path not in repo or fetch fails
      if True
   -  ``show``: Display directory change commands if True
   -  Returns: Context manager
   -  Internal calls: ``git_repo_path_root()``, ``git_fetch()``

-  **``git_repo_path_root(path='', exception=False)``** - Return git
   repo path root for path, or None

   -  ``path``: Relative or absolute path to file or directory (current
      working directory used if none specified)
   -  ``exception``: Raise ValueError if path is not in a repo if True
   -  Returns: String path to repo root or empty string
   -  Internal calls: ``fh.repopath()``

-  **``git_repo_update(path='', debug=False, timeout=None, exception=True, show=False)``**
   - Update a repo and return True if it was successful

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: Boolean success status
   -  Internal calls: ``ctx_repo_path_root()``,
      ``git_current_tracking_branch()``, ``git_current_branch()``,
      ``git_origin_url()``, ``git_fetch()``, ``bh.run_output()``,
      ``bh.run()``

-  **``git_clone(url, path='', name='', recursive=False, debug=False, timeout=None, exception=True, show=False)``**
   - Clone a repo

   -  ``url``: URL for a git repo
   -  ``path``: Path to clone git repo to, if not using current working
      directory
   -  ``name``: Name to clone the repo as, if not using the existing
      name
   -  ``recursive``: Pass –recursive to ``git clone`` if True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: Local path to cloned repo or None
   -  Internal calls: ``bh.run()``

-  **``git_fetch(path='', output=False, debug=False, timeout=None, exception=True, show=False)``**
   - Perform ``git fetch --all --prune``

   -  ``path``: Path to git repo, if not using current working directory
   -  ``output``: Return output of ``git fetch --all --prune`` if True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: Command output if output=True, otherwise None
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``

-  **``git_do(path='', fetch=False, cmd=None, output=False, debug=False, timeout=None, exception=True, show=False)``**
   - Run specified cmd and either return the output or the exit status

   -  ``path``: Path to git repo, if not using current working directory
   -  ``fetch``: Call git_fetch func before calling the generated
      ``git`` command if True
   -  ``cmd``: String with shell command (required)
   -  ``output``: Capture output of cmd and return it if True; otherwise
      return exit status of cmd
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: Command output or exit status depending on output
      parameter
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``bh.run()``

-  **``git_origin_url(path='')``** - Return url to remote origin (from
   .git/config file)

   -  ``path``: Path to git repo, if not using current working directory
   -  Returns: String URL or empty string
   -  Internal calls: ``git_repo_path_root()``, ``bh.run_output()``

-  **``git_current_branch(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Return current branch name

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: String branch name
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``

-  **``git_current_tracking_branch(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Return remote tracking branch for current branch

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: String tracking branch name or empty string
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``git_current_branch()``, ``bh.tools.grep_output()``

-  **``git_last_tag(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Return the most recent tag made

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: String tag name or empty string
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``

-  **``git_tag_message(path='', debug=False, tag='', timeout=None, exception=False, show=False)``**
   - Return the message for specified tag

   -  ``path``: Path to git repo, if not using current working directory
   -  ``tag``: Name of a tag that was made
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: String tag message
   -  Internal calls: ``ctx_repo_path_root()``, ``git_last_tag()``,
      ``bh.run_output()``

-  **``git_last_tag_message(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Return the message for the most recent tag made

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: String tag message
   -  Internal calls: ``ctx_repo_path_root()``, ``git_last_tag()``,
      ``git_tag_message()``

-  **``git_tags(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Return a list of all tags with most recent first

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of tag names
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``

-  **``git_first_commit_id(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Get the first commit id for the repo

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: String commit ID or empty string
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``

-  **``git_last_commit_id(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Get the last commit id for the repo

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: String commit ID or empty string
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``

-  **``git_commits_since_last_tag(path='', until='', debug=False, timeout=None, exception=False, show=False)``**
   - Return a list of commits made since last_tag

   -  ``path``: Path to git repo, if not using current working directory
   -  ``until``: A recent commit id to stop at (instead of last commit)
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of commit strings (if no tag, returns commits since
      first commit)
   -  Internal calls: ``ctx_repo_path_root()``, ``git_last_tag()``,
      ``git_first_commit_id()``, ``git_last_commit_id()``,
      ``bh.run_output()``, ``ih.splitlines()``

-  **``git_unpushed_commits(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Return a list of any local commits that have not been pushed

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of unpushed commit strings
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``ih.splitlines()``

-  **``git_untracked_files(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Return a list of any local files that are not tracked in the git
   repo

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of untracked file paths
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``ih.splitlines()``

-  **``git_stashlist(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Return a list of any local stashes

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of stash entries
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``ih.splitlines()``

-  **``git_status(path='', debug=False, timeout=None, exception=False, show=False)``**
   - Return a list of any modified or untracked files

   -  ``path``: Path to git repo, if not using current working directory
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of status entries
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``ih.splitlines_and_strip()``

-  **``git_info_dict(path='', fetch=False, debug=False, timeout=None, exception=False, show=False)``**
   - Return a dict of info about the repo

   -  ``path``: Path to git repo, if not using current working directory
   -  ``fetch``: Call git_fetch func before calling the generated
      ``git`` command if True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: Dictionary with keys: ``path_root``, ``url``, ``branch``,
      ``branch_date``, ``branch_tracking``, ``branch_tracking_date``,
      ``last_tag``, ``status``, ``stashes``, ``unpushed``,
      ``commits_since_last_tag``
   -  Internal calls: ``ctx_repo_path_root()``,
      ``git_repo_path_root()``, ``git_origin_url()``,
      ``git_current_branch()``, ``git_branch_date()``,
      ``git_current_tracking_branch()``, ``git_last_tag()``,
      ``git_status()``, ``git_stashlist()``, ``git_unpushed_commits()``,
      ``git_commits_since_last_tag()``

-  **``git_info_string(path='', fetch=False, debug=False, timeout=None, exception=False, show=False)``**
   - Build up a string of info from git_info_dict and return it

   -  ``path``: Path to git repo, if not using current working directory
   -  ``fetch``: Call git_fetch func before calling the generated
      ``git`` command if True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: Formatted string with git repository information
   -  Internal calls: ``ctx_repo_path_root()``, ``git_info_dict()``

-  **``git_branch_date(path='', branch='', fetch=False, debug=False, timeout=None, exception=False, show=False)``**
   - Return datetime string (and relative age) of branch

   -  ``path``: Path to git repo, if not using current working directory
   -  ``branch``: Name of branch (prefix with ‘origin/’ for remote
      branch)
   -  ``fetch``: Call git_fetch func before calling the generated
      ``git`` command if True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: String with date and relative time
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``

-  **``git_remote_branches(path='', fetch=False, grep='', include_times=False, debug=False, timeout=None, exception=False, show=False)``**
   - Return list of remote branch names or list of dicts (via
   ``git ls-remote --heads``)

   -  ``path``: Path to git repo, if not using current working directory
   -  ``fetch``: Call git_fetch func before calling the generated
      ``git`` command if True
   -  ``grep``: ``grep -iE`` pattern to filter branches by
      (case-insensitive)
   -  ``include_times``: Include info from git_branch_date in results if
      True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of branch names or list of dicts (alphabetized if
      include_times=False, otherwise ordered by most recent commit)
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``bh.tools.grep_output()``, ``_dates_for_branches()``

-  **``git_local_branches(path='', fetch=False, grep='', include_times=False, debug=False, timeout=None, exception=False, show=False)``**
   - Return list of local branch names or list of dicts (via
   ``git branch``)

   -  ``path``: Path to git repo, if not using current working directory
   -  ``fetch``: Call git_fetch func before calling the generated
      ``git`` command if True
   -  ``grep``: ``grep -iE`` pattern to filter branches by
      (case-insensitive)
   -  ``include_times``: Include info from git_branch_date in results if
      True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of branch names or list of dicts (alphabetized if
      include_times=False, otherwise ordered by most recent commit)
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``bh.tools.grep_output()``, ``_dates_for_branches()``

-  **``git_remote_branches_merged_with(path='', branch='develop', fetch=False, include_times=False, debug=False, timeout=None, exception=False, show=False)``**
   - Return a list of branches on origin that have been merged with
   branch

   -  ``path``: Path to git repo, if not using current working directory
   -  ``branch``: Remote branch name (without leading ‘origin/’)
   -  ``fetch``: Call git_fetch func before calling the generated
      ``git`` command if True
   -  ``include_times``: Include info from git_branch_date in results if
      True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of merged branch names or list of dicts
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``bh.tools.grep_output()``, ``_dates_for_branches()``

-  **``git_local_branches_merged_with(path='', branch='develop', fetch=False, include_times=False, debug=False, timeout=None, exception=False, show=False)``**
   - Return a list of local branches that have been merged with branch

   -  ``path``: Path to git repo, if not using current working directory
   -  ``branch``: Local branch name
   -  ``fetch``: Call git_fetch func before calling the generated
      ``git`` command if True
   -  ``include_times``: Include info from git_branch_date in results if
      True
   -  ``debug``: Insert breakpoint before subprocess calls if True
   -  ``timeout``: Seconds to wait before stopping commands
   -  ``exception``: Raise exception if git command has error if True
   -  ``show``: Display git commands before executing if True
   -  Returns: List of merged branch names or list of dicts
   -  Internal calls: ``ctx_repo_path_root()``, ``bh.run_output()``,
      ``bh.tools.grep_output()``, ``_dates_for_branches()``

Docker Operations (``bh.tools.*``)
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

Docker functions provide container lifecycle management with
service-specific shortcuts and platform adaptation.

-  **``docker_ok(exception=False)``** - Check if Docker daemon is
   available and running

   -  ``exception``: Raise exception if Docker unavailable and True
   -  Returns: Boolean indicating Docker availability
   -  Internal calls: ``bh.run_output()``

-  **``docker_stop(name, kill=False, signal='KILL', rm=False, exception=False, show=False)``**
   - Return True if successfully stopped

   -  ``name``: Name of the container
   -  ``kill``: Kill the container instead of stopping if True
   -  ``signal``: Signal to send to the container if kill is True
   -  ``rm``: Remove the container after stop/kill if True
   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker commands and output if True
   -  Returns: Boolean success status
   -  Internal calls: ``docker_ok()``, ``bh.run_output()``

-  **``docker_start_or_run(name, image='', command='', detach=True, rm=False, interactive=False, ports='', volumes='', platform='', env_vars={}, exception=False, show=False, force=False)``**
   - Start existing container or create/run container

   -  ``name``: Name for the container
   -  ``image``: Image to use (i.e. image:tag)
   -  ``command``: Command to run in the container
   -  ``detach``: Run container in the background if True (set to False
      if interactive is True)
   -  ``rm``: Automatically delete the container when it exits if True
   -  ``interactive``: Keep STDIN open and allocate pseudo-TTY if True
   -  ``ports``: String containing {host-port}:{container-port} pairs
      separated by , ; \|
   -  ``volumes``: String containing {host-path}:{container-path} pairs
      separated by , ; \|
   -  ``platform``: Platform to set if server is multi-platform capable
   -  ``env_vars``: Dict of environment variables and values to set
   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker commands and output if True
   -  ``force``: Stop the container and remove it before re-creating if
      True
   -  Returns: Boolean success status
   -  Internal calls: ``docker_ok()``, ``docker_stop()``,
      ``ih.string_to_list()``, ``bh.run()``, ``bh.run_output()``

-  **``docker_container_id(name)``** - Return the container ID for
   running container name

   -  ``name``: Name of the container
   -  Returns: String container ID or empty string
   -  Internal calls: ``docker_ok()``, ``bh.run_output()``

-  **``docker_container_inspect(name, exception=False, show=False)``** -
   Return detailed information on specified container as a list

   -  ``name``: Name of the container
   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker command and output if True
   -  Returns: List of container information dictionaries
   -  Internal calls: ``docker_ok()``, ``bh.run_output()``

-  **``docker_container_config(name, exception=False, show=False)``** -
   Return dict of config information for specified container (from
   inspect)

   -  ``name``: Name of the container
   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker command and output if True
   -  Returns: Dictionary of container configuration
   -  Internal calls: ``docker_container_inspect()``

-  **``docker_container_env_vars(name, exception=False, show=False)``**
   - Return dict of environment vars for specified container

   -  ``name``: Name of the container
   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker command and output if True
   -  Returns: Dictionary of environment variables
   -  Internal calls: ``docker_container_config()``

-  **``docker_logs(name, num_lines=None, follow=False, details=False, since='', until='', timestamps=False, show=False)``**
   - Show logs on an existing container

   -  ``name``: Name of the container
   -  ``num_lines``: Number of lines to show from the end of the logs
   -  ``follow``: Follow log output if True
   -  ``details``: Show extra details provided to logs if True
   -  ``since``: Show logs since timestamp (iso format or relative)
   -  ``until``: Show logs before timestamp (iso format or relative)
   -  ``timestamps``: Show timestamps if True
   -  ``show``: Show the docker command and output if True
   -  Returns: Exit code or log output
   -  Internal calls: ``docker_ok()``, ``bh.run()``, ``bh.run_output()``

-  **``docker_exec(name, command='pwd', output=False, env_vars={}, show=False)``**
   - Run shell command on an existing container (will be started if
   stopped)

   -  ``name``: Name of the container
   -  ``command``: Command to execute
   -  ``output``: Return output or error from command if True; otherwise
      return exit status
   -  ``env_vars``: Dict of environment variables and values to set
   -  ``show``: Show the docker command and output if True
   -  Returns: Command output or exit status
   -  Internal calls: ``docker_ok()``, ``docker_start_or_run()``,
      ``bh.run_output()``, ``bh.run()``

-  **``docker_exec_wait(name, command='pwd', sleeptime=2, env_vars={}, show=False)``**
   - Wait for a shell command to succeed in an existing container (will
   be started if stopped)

   -  ``name``: Name of the container
   -  ``command``: Command to execute
   -  ``sleeptime``: Time to sleep between checks
   -  ``env_vars``: Dict of environment variables and values to set
   -  ``show``: Show the docker command and output if True
   -  Returns: None (blocks until command succeeds)
   -  Internal calls: ``docker_exec()``

-  **``docker_shell(name, shell='sh', env_vars={}, show=False)``** -
   Start shell on an existing container (will be started if stopped)

   -  ``name``: Name of the container
   -  ``shell``: Name of shell to execute
   -  ``env_vars``: Dict of environment variables and values to set
   -  ``show``: Show the docker command and output if True
   -  Returns: Exit code
   -  Internal calls: ``docker_ok()``, ``docker_start_or_run()``,
      ``bh.run()``

-  **``docker_cleanup_volumes(exception=False, show=False)``** - Use
   this when creating a container fails with ‘No space left on device’

   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker command and output if True
   -  Returns: Boolean success status
   -  Internal calls: ``docker_start_or_run()``

Database Service Functions
^^^^^^^^^^^^^^^^^^^^^^^^^^

-  **``docker_redis_start(name, version='6-alpine', port=6300, data_dir=None, aof=True, interactive=False, rm=False, exception=False, show=False, force=False)``**
   - Start or create redis container

   -  ``name``: Name for the container
   -  ``version``: Redis image version
   -  ``port``: Port to map into the container
   -  ``data_dir``: Directory that will map to container’s /data
      (absolute path or subdirectory of current directory)
   -  ``aof``: Use appendonly.aof file if True
   -  ``interactive``: Keep STDIN open and allocate pseudo-TTY if True
   -  ``rm``: Automatically delete the container when it exits if True
   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker commands and output if True
   -  ``force``: Stop the container and remove it before re-creating if
      True
   -  Returns: Boolean success status
   -  Internal calls: ``docker_start_or_run()``

-  **``docker_redis_cli(name, show=False)``** - Start redis-cli on an
   existing container (will be started if stopped)

   -  ``name``: Name for the container
   -  ``show``: Show the docker command and output if True
   -  Returns: Exit code
   -  Internal calls: ``docker_shell()``

-  **``docker_mongo_start(name, version='4.4', port=27000, username='mongouser', password='some.pass', data_dir=None, interactive=False, rm=False, exception=False, show=False, force=False, wait=False, sleeptime=2)``**
   - Start or create mongo container

   -  ``name``: Name for the container
   -  ``version``: Mongo image version
   -  ``port``: Port to map into the container
   -  ``username``: Username to set for root user on first run
   -  ``password``: Password to set for root user on first run
   -  ``data_dir``: Directory that will map to container’s /data/db
      (absolute path or subdirectory of current directory)
   -  ``interactive``: Keep STDIN open and allocate pseudo-TTY if True
   -  ``rm``: Automatically delete the container when it exits if True
   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker commands and output if True
   -  ``force``: Stop the container and remove it before re-creating if
      True
   -  ``wait``: Don’t return until mongo is able to accept connections
      if True
   -  ``sleeptime``: If wait is True, sleep this number of seconds
      before checks
   -  Returns: Boolean success status
   -  Internal calls: ``docker_start_or_run()``

-  **``docker_mongo_cli(name, show=False)``** - Start mongo on an
   existing container (will be started if stopped)

   -  ``name``: Name for the container
   -  ``show``: Show the docker command and output if True
   -  Returns: Exit code
   -  Internal calls: ``docker_container_env_vars()``,
      ``docker_shell()``

-  **``docker_mongo_wait(name, sleeptime=2, show=False)``** - Wait for
   mongo on an existing container (will be started if stopped)

   -  ``name``: Name of the container
   -  ``sleeptime``: Time to sleep between checks
   -  ``show``: Show the docker command and output if True
   -  Returns: None (blocks until postgres is ready)
   -  Internal calls: ``docker_container_env_vars()``,
      ``docker_exec_wait()``

-  **``docker_postgres_start(name, version='13-alpine', port=5400, username='postgresuser', password='some.pass', db='postgresdb', data_dir=None, interactive=False, rm=False, exception=False, show=False, force=False, wait=False, sleeptime=2)``**
   - Start or create postgres container

   -  ``name``: Name for the container
   -  ``version``: Postgres image version
   -  ``port``: Port to map into the container
   -  ``username``: Username to set as superuser on first run
   -  ``password``: Password to set for superuser on first run
   -  ``db``: Name of default database
   -  ``data_dir``: Directory that will map to container’s
      /var/lib/postgresql/data (absolute path or subdirectory of current
      directory)
   -  ``interactive``: Keep STDIN open and allocate pseudo-TTY if True
   -  ``rm``: Automatically delete the container when it exits if True
   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker commands and output if True
   -  ``force``: Stop the container and remove it before re-creating if
      True
   -  ``wait``: Don’t return until postgres is able to accept
      connections if True
   -  ``sleeptime``: If wait is True, sleep this number of seconds
      before checks
   -  Returns: Boolean success status
   -  Internal calls: ``docker_start_or_run()``,
      ``docker_postgres_wait()``

-  **``docker_postgres_cli(name, show=False)``** - Start psql on an
   existing container (will be started if stopped)

   -  ``name``: Name for the container
   -  ``show``: Show the docker command and output if True
   -  Returns: Exit code
   -  Internal calls: ``docker_container_env_vars()``,
      ``docker_shell()``

-  **``docker_postgres_wait(name, sleeptime=2, show=False)``** - Wait
   for psql on an existing container (will be started if stopped)

   -  ``name``: Name of the container
   -  ``sleeptime``: Time to sleep between checks
   -  ``show``: Show the docker command and output if True
   -  Returns: None (blocks until postgres is ready)
   -  Internal calls: ``docker_container_env_vars()``,
      ``docker_exec_wait()``

-  **``docker_mysql_start(name, version='8.0', port=3300, root_password='root.pass', username='mysqluser', password='some.pass', db='mysqldb', data_dir=None, interactive=False, rm=False, exception=False, show=False, force=False, wait=False, sleeptime=2)``**
   - Start or create mysql container

   -  ``name``: Name for the container
   -  ``version``: MySQL image version (or mysql/mysql-server for Mac
      M1)
   -  ``port``: Port to map into the container
   -  ``root_password``: Password to set for the root superuser account
   -  ``username``: Username to set as superuser on first run
   -  ``password``: Password to set for superuser on first run
   -  ``db``: Name of default database
   -  ``data_dir``: Directory that will map to container’s
      /var/lib/mysql (absolute path or subdirectory of current
      directory)
   -  ``interactive``: Keep STDIN open and allocate pseudo-TTY if True
   -  ``rm``: Automatically delete the container when it exits if True
   -  ``exception``: Raise exception if docker has error response and
      True
   -  ``show``: Show the docker commands and output if True
   -  ``force``: Stop the container and remove it before re-creating if
      True
   -  ``wait``: Don’t return until mysql is able to accept connections
      if True
   -  ``sleeptime``: If wait is True, sleep this number of seconds
      before checks
   -  Returns: Boolean success status
   -  Internal calls: ``bh.run_output()``, ``docker_start_or_run()``,
      ``docker_mysql_wait()``

-  **``docker_mysql_cli(