Skip to content

The Docker client object

DockerClient

Creates a Docker client

Note that

from python_on_whales import docker
print(docker.run("hello-world"))

is equivalent to

from python_on_whales import DockerClient
docker = DockerClient()
print(docker.run("hello-world")
PARAMETER DESCRIPTION
config

Location of client config files (default "~/.docker")

TYPE: Optional[ValidPath] DEFAULT: None

context

Name of the context to use to connect to the daemon (overrides DOCKER_HOST env var and default context set with "docker context use")

TYPE: Optional[str] DEFAULT: None

debug

Enable debug mode

TYPE: Optional[bool] DEFAULT: None

host

Daemon socket(s) to connect to

TYPE: Optional[str] DEFAULT: None

log_level

Set the logging level ("debug"|"info"|"warn"|"error"|"fatal") (default "info")

TYPE: Optional[str] DEFAULT: None

tls

Use TLS; implied by tlsverify

TYPE: Optional[bool] DEFAULT: None

tlscacert

Trust certs signed only by this CA (default "~/.docker/ca.pem")

TYPE: Optional[ValidPath] DEFAULT: None

compose_files

Docker compose yaml file

TYPE: List[ValidPath] DEFAULT: []

compose_profiles

List of compose profiles to use. Take a look at the documentation for profiles.

TYPE: List[str] DEFAULT: []

compose_env_file

.env file containing the environments variables to inject into the compose project. By default, it uses ./.env.

TYPE: Optional[ValidPath] DEFAULT: None

compose_project_name

The name of the compose project. It will be prefixed to networks, volumes and containers created by compose.

TYPE: Optional[str] DEFAULT: None

compose_project_directory

Use an alternate working directory. By default, it uses the path of the compose file.

TYPE: Optional[ValidPath] DEFAULT: None

compose_compatibility

Use docker compose in compatibility mode.

TYPE: Optional[bool] DEFAULT: None

client_call

Client binary to use and how to call it. Default is ["docker"]. You can try with for example ["podman"] or ["nerdctl"]. The client must have the same commands and outputs as Docker to work. Some best effort support is done in case of divergences, meaning you can report issues occuring on some other binary than Docker, but we don't guarantee that it will be fixed. This option is a list because you can provide a list of command line arguments to be placed after "docker". For exemple host="ssh://my_user@host.com" is equivalent to client_call=["docker", "--host=ssh://my_user@host.com"]. This will allow you to use some exotic options that are not explicitly supported by Python-on-whales. Let's say you want to use estargz to run a container immediately, without waiting for the "pull" to finish (yes it's possible!), you can do nerdctl = DockerClient(client_call=["nerdctl", "--snapshotter=stargz"]) and then nerdctl.run("ghcr.io/stargz-containers/python:3.7-org", ["-c", "print('hi')"]). You can also use this system to call Docker with sudo with client_call=["sudo", "docker"] (note that it won't ask for your password, so sudo should be passwordless during the python program execution).

TYPE: List[str] DEFAULT: ['docker']

client_binary

Deprecated, use client_call. If you used before client_binary="podman", now use client_call=["podman"].

TYPE: str DEFAULT: 'docker'

client_type

The kind of client that is called by the Python process. It allows Python-on-whales to adapt to the client's behavior if two client have a different behavior. The client_call is not enough for Python-on-whales to know what kind of client you're using. For example, if you use a symlink to call Docker, Python-on-whales will not know that you're using Docker. Default is "unknown". If at some point, Python-on-whales has to choose a behavior and client_type is "unknown", it will raise an exception and ask you to specify what kind of client you're working with. Valid values are "docker", "podman", "nerdctl" and "unknown".

TYPE: Literal['docker', 'podman', 'nerdctl', 'unknown'] DEFAULT: 'unknown'

login

login(server=None, username=None, password=None)

Log in to a Docker registry.

If no server is specified, the default is defined by the daemon.

PARAMETER DESCRIPTION
server

The server to log into. For example, with a self-hosted registry it might be something like server="192.168.0.10:5000"

TYPE: Optional[str] DEFAULT: None

username

The username

TYPE: Optional[str] DEFAULT: None

password

The password

TYPE: Optional[str] DEFAULT: None

login_ecr

login_ecr(aws_access_key_id=None, aws_secret_access_key=None, region_name=None, registry=None)

Login to the aws ECR registry. Credentials are taken from the environment variables as defined in the aws docs.

If you don't have a profile or your environment variables configured, you can also use the function arguments aws_access_key_id, aws_secret_access_key, region_name.

Behind the scenes, those arguments are passed directly to

botocore.session.get_session().create_client(...)

You need botocore to run this function. Use pip install botocore to install it.

The registry parameter can be used to override the registry that is guessed from the authorization token request's response. In other words: If the registry is None (the default) then it will be assumed that it's the ECR registry linked to the credentials provided. It is especially useful if the aws account you use can access several repositories and you need to explicitly define the one you want to use

logout

logout(server=None)

Logout from a Docker registry

PARAMETER DESCRIPTION
server

The server to logout from. For example, with a self-hosted registry it might be something like server="192.168.0.10:5000"

TYPE: Optional[str] DEFAULT: None

version

version()

Get version information about the container client and server.

Returns

A `python_on_whales.Version` object

As an example:

from python_on_whales import docker

version_info = docker.version()
print(version_info.client.version)
# 3.4.2
print(version_info.server.kernel_version)
# 5.15.133.1-microsoft-standard-WSL2
...

Sub-commands

Other commands

They're actually aliases

About multithreading and multiprocessing

Behind the scenes, Python on whales calls the Docker command line interface with subprocess. The Python on whales client does not store any intermediate state so it's safe to use with multithreading.

The Docker objects store some intermediate states (the attributes that you would normally get with docker ... inspectbut no logic in the codebase depends on those attributes. They're just here so that users can look at them. So you can share them between process/threads and pickle containers, images, networks...

The Docker daemon works with its own objects internally and handles concurrent and conflicting requests. For example, if you create two containers with the same name from different threads, only one will succeed. If you pull the same docker image from multiple processes/threads, the Docker daemon will only pull the image and layers once.

Just be careful with some scenario similar to this one

Thread 1: my_container = docker.run(..., detach=True)
...
# my_container finishes
...
Thread 2: docker.container.prune()
...
Thread 1: docker.logs(my_container)  # will fail because the container was removed by thread 2

In the end, unless you use this type of logic in your code, Python-on-whales is safe to use with multithreading and multiprocessing.

The Docker/Podman CLI

Python-on-whales needs the Docker or Podman CLI to work (unlike docker-py). Most of the time, users already have the CLI installed on their machines. It's possible to verify that the CLI is there by doing docker --help (or podman --help) in the command line.

Sometimes, the CLI might not be available on the system, it can happen if you want to control Docker from within a container with -v /var/run/docker.sock:/var/run/docker.sock, or if you want to connect to a remote daemon with the host argument.

Instructions for installing Docker can be found at https://docs.docker.com/engine/install/, and Podman at https://podman.io/docs/installation/. Note that if connecting to Docker/Podman remotely then the Docker daemon (dockerd) is not needed, and similarly for Podman it is possible to use podman-remote (available as a static binary from https://github.com/containers/podman/releases/latest).

Previously, when using python-on-whales, the Docker CLI was downloaded automatically, but this functionality was removed under https://github.com/gabrieldemarmiesse/python-on-whales/pull/633.

Handling an unavailable client

Trying to use Python-on-whales when it cannot find or download a Docker client binary will trigger a python_on_whales.ClientNotFoundError. You can use a try-except around a first docker.ps() call to handle the case when Python-on-whales won't work.