docker run, better
Finally good defaults to distribute docker images!
This was initially created for the October 2024 Docker Hackathon
Let’s imagine you want to show your container can run a specific action. For instance echo Hello
from alpine
image.
Create a runx.yaml
file with the following content:
actions:
- id: hello # required, the action identifier
type: run # required, the action type, only `run` is supported for now
env: # a list of environment variables that needs to be set
- USER
cmd: --rm echo hello # `.Ref` will be replaced by the reference the user provided
And let’s create a documentation file called README.md
:
# Hello!
Run the `hello` action with `docker runx` to display a message.
Now decorate the alpine
image and push it under NAMESPACE/REPOSITORY
:
$ docker runx decorate alpine --tag NAMESPACE/REPOSITORY
[!TIP]
runx.yaml
andREADME.md
are the default file names. You can specify the file names using--with-config
and--with-readme
flags. It’s intended to have both files, if you don’t want to provide one or the other, use--no-config
or--no-readme
flags.
You can then display the embedded readme:
$ docker runx NAMESPACE/REPOSITORY --help
Or run the hello
action:
$ docker runx NAMESPACE/REPOSITORY hello
See more examples in the examples directory.
docker runx IMAGE --help
Display the embedded documentation of an image and print the list of available actions.
docker runx IMAGE --list
Display the list of available actions for an image and let the user pick the one they want to run.
docker runx IMAGE ACTION
Run a specific action on an image.
docker runx IMAGE ACTION --help
Display a detailed documentation of a specific action. This will also display the list of available options, shell scripts, environment variables.
docker runx IMAGE ACTION --opt OPTION_NAME=VALUE
Run a specific action and use the value provided on the command line instead of asking to the user.
docker runx IMAGE
If a default action is defined in the image manifest, it will run it. If not it will list the available actions and let the user pick the one to run.
docker runx decorate SRC_IMAGE --tag DEST_IMAGE
Decorate an image by adding the
runx
manifest to it. Therunx.yaml
andREADME.md
files will be embedded in the image.If
scratch
is used as the source image, only therunx
files will be embedded.The image will be pushed automatically, the image doesn’t exist locally.
See the Docker RunX reference for more information.
All the possible actions are defined in a yaml file. The file is named runx.yaml
by default, but you can specify another name using the --with-config
flag when using the decorate
command.
# Optional.
# Define a default action to run if non is provided by the user.
default: ACTION_ID
# List of all the possible actions for this image.
actions:
# The action identifier the user can use to run it.
- id: ACTION_ID
# Optional.
# A description of the action, that will be displayed in the documentation or listing.
desc: DESCRIPTION
# The type of action to run.
# If set to `run`, the command will be a `docker run`.
# If set to `build`, the command will be a `docker buildx build`.
type: run|build
# Optional.
# A list of environment variables that needs to be set before running the command.
env:
- ENV_VAR
# Optional.
# A list of shell script commands. Their output can be used in the `cmd` field.
shell:
NAME: COMMAND
# Optional.
# Path to a dockerfile to use with an action of type `build`
Dockerfile: DOCKERFILE_PATH
# Optional.
# A list of options that can be provided by the user.
opts:
- name: OPTION_NAME # Name of the option. Also used in the local override or with `--opt` flag.
type: input|select|confirm # Type of the option.
desc: DESCRIPTION # Description, rendered in the documentation of the action.
prompt: PROMPT # A specific prompt to ask the user for the value.
no-prompt: true|false # If set to true, the option will not be prompted to the user.
required: true|false # If required, an empty value will not be accepted.
values: # A list of possible values for the option. If set, a select will be displayed to the user.
- VALUE
default: VALUE # The default value for the option.
# The command to run. It's defined as a Go template and can use the following variables:
# - `.Ref` will be replaced by the reference to the image the user provided.
# - `.IsTTY` indicates if the command is run in a TTY environment.
# Useful to add the `-t` flag to the `docker run` command: `-t`
# - `.Dockerfile` will be replaced by the path to the Dockerfile if one has been provided.
#
# In addition, the command can use the following functions:
# - `` will be replaced by the value of the environment variable `ENV_VAR`.
# The environment variable needs to be defined in the `env` section.
# - `` will be replaced by the value of the option `OPTION`.
# The value needs to be provided by the local configuration, on the command line or interactively.
# - `` is equivalent to `` but will return the value as a boolean.
# True values are `1`, `t`, `T`, `TRUE`, `true` and `True`. Everything else is considered as false.
# - `` will be replaced by the output of the shell command `COMMAND`.
# The command will be run using https://github.com/mvdan/sh without a standard input.
cmd: COMMAND
A local file .docker/runx.yaml
can be used to override the actions defined in the image manifest.
This is useful to configure some actions for a specific project for instance.
docker runx
will look for this file in the current directory and in all the parent directories. The different files will be merged together, the closer to the current directory will have the priority.
# Optional.
# If set to true, the user will not be prompted to check some security risks.
# If not set, the user will be prompted for confirmation based on flags like volume, mounts, privileged, etc.
accept-the-risk: true|false
# Optional.
# It allows to define a default reference to an image if none is provided by the user.
# with the ref set to IMAGE a `docker runx` is equivalent to `docker runx IMAGE`
ref: IMAGE
# Optional.
# Defines some override for one or more images
images:
# Reference of the image
IMAGE:
# Optional.
# Define a default action to run if none is provided by the user.
# This overrides the `default` action in the image `runx.yaml` configuration.
default: ACTION_ID
# Optional.
# Allow to define common options for all the actions of the image.
all-actions:
opts:
# Override the value of an option.
OPTION_NAME: OPTION_VALUE
# Optional.
actions:
# Specify the action to override.
ACTION_ID:
opts:
# Override the value of an option.
# If set, the option will not be prompt to the user, except if `--ask` flag is used.
# If `--opt OPTION_NAME=VALUE` is used, this will override the value from this file.
OPTION_NAME: OPTION_VALUE
The main idea behind docker runx
is to attach a specific image manifest to an existing image or image index. This manifest contains the runx.yaml
and README.md
files as layers.
When running docker runx
, the plugin will look for the image manifest and extract the files. It will then execute the action specified by the user or display the documentation.
The image manifest sets the platform as unkown and add a specific annotation to indicate this is a runx
manifest.
Here is an example of a runx
based image index:
{
"schemaVersion": 2,
"mediaType": "application/vnd.oci.image.index.v1+json",
"manifests": [
{},
{},
{
"mediaType": "application/vnd.oci.image.manifest.v1+json",
"size": 533,
"digest": "sha256:.....",
"platform": {
"architecture": "unknown",
"os": "unknown"
},
"annotations": {
"vnd.docker.reference.type": "runx-manifest"
}
}
]
}
The runx
image manifest will reference at max two layers, one for the runx.yaml
file and one for the README.md
file.
{
"schemaVersion": 2,
"mediaType": "application/vnd.oci.image.manifest.v1+json",
"config": {
"mediaType": "application/vnd.oci.image.config.v1+json",
"size": 356,
"digest": "sha256:..."
},
"layers": [
{
"mediaType": "application/vnd.runx.config+yaml",
"size": 3062,
"digest": "sha256:..."
},
{
"mediaType": "application/vnd.runx.readme+txt",
"size": 946,
"digest": "sha256:..."
}
]
}
Install the docker-runx
CLI plugin using the following command:
curl -sSfL https://raw.githubusercontent.com/eunomie/docker-runx/main/install.sh | sh -s --
You can also download the installation script and run it locally:
DOWNLOAD_TAG_INSTALL_SCRIPT=false sh install.sh
Please be sure to have the install.sh
script corresponding to the version you want to install.
To install it manually:
docker-runx
binary corresponding to your platform from the latest or other releases.docker-runx
on Linux and macOSdocker-runx.exe
on Windowsrunx
directory (you might need to create it)
$HOME/.docker/runx
on Linux and macOS%USERPROFILE%\.docker\runx
on Windowschmod +x $HOME/.docker/runx/docker-runx
xattr -d com.apple.quarantine $HOME/.docker/runx/docker-runx
runx
directory to your .docker/config.json
as a plugin directory
$HOME/.docker/config.json
on Linux and macOS%USERPROFILE%\.docker\config.json
on WindowscliPluginsExtraDirs
property to the config.json
file
{
...
"cliPluginsExtraDirs": [
"<full path to the .docker/runx folder>"
],
...
}
This project is not maintained by Docker but was a submission for the October 2024 Docker internal Hackathon.