Gantry automatically updates selected docker swarm services to newer images with the same tag. It is inspired by but enhanced Shepherd.
Gantry is released as a container image. You can create a docker service and run it on a swarm manager node.
docker service create \
--name gantry \
--mode replicated-job \
--constraint "node.role==manager" \
--mount type=bind,source=/var/run/docker.sock,target=/var/run/docker.sock \
shizunge/gantry
The examples folder contains example docker compose files, and more methods to launch Gantry, like at a specific time and via webhook.
You can also run Gantry as a script directly on the host outside the container
./src/entrypoint.sh
Gantry is written to work with busybox ash
(v1.35+) as well as bash
.
You can configure the most behaviors of Gantry via environment variables.
Environment Variable | Default | Description |
---|---|---|
GANTRY_LOG_LEVEL | INFO | Control how many logs generated by Gantry. Valid values are NONE , ERROR , WARN , INFO , DEBUG . |
GANTRY_NODE_NAME | Add node name to logs. If not set, Gantry will use the host name of the Docker Swarm's manager, which is read from either the Docker daemon socket of current node or DOCKER_HOST . |
|
GANTRY_POST_RUN_CMD | Command(s) to eval after each updating iteration. For example, you can use this to remove unused containers, networks and images and update standalone docker containers. |
|
GANTRY_PRE_RUN_CMD | Command(s) to eval before each updating iteration. For example, you can use this to remove unused containers, networks and images and update standalone docker containers. |
|
GANTRY_SLEEP_SECONDS | 0 | Interval between two updates. Set it to 0 to run Gantry once and then exit. When this is a non-zero value, after an updating, Gantry will sleep until the next scheduled update. The actual sleep time is this value minus time spent on updating services. |
TZ | Set timezone for time in logs. |
Gantry bases on Docker command line, environment variables for Docker command line also works for Gantry.
Environment Variable | Default | Description |
---|---|---|
DOCKER_CONFIG | The location of the client configuration files where authentication stores. It applys to all Docker commands, i.e. to all services. See Authentication. You can apply a different value to a particular service via labels. | |
GANTRY_REGISTRY_CONFIG | See Authentication. | |
GANTRY_REGISTRY_CONFIG_FILE | See Authentication. | |
GANTRY_REGISTRY_CONFIGS_FILE | See Authentication. | |
GANTRY_REGISTRY_HOST | See Authentication. | |
GANTRY_REGISTRY_HOST_FILE | See Authentication. | |
GANTRY_REGISTRY_PASSWORD | See Authentication. | |
GANTRY_REGISTRY_PASSWORD_FILE | See Authentication. | |
GANTRY_REGISTRY_USER | See Authentication. | |
GANTRY_REGISTRY_USER_FILE | See Authentication. |
Environment Variable | Default | Description |
---|---|---|
GANTRY_SERVICES_EXCLUDED | A space separated list of services names that are excluded from updating. | |
GANTRY_SERVICES_EXCLUDED_FILTERS | label=gantry.services.excluded=true |
A space separated list of filters, e.g. label=project=project-a . Exclude services which match the given filters from updating. The default value allows you to add label gantry.services.excluded=true to services to exclude them from updating. Note that multiple filters will be logical ANDED. |
GANTRY_SERVICES_FILTERS | A space separated list of filters that are accepted by docker service ls --filter to select services to update, e.g. label=project=project-a . Note that multiple filters will be logical ANDED. Also see How to filters multiple services by name. |
Environment Variable | Default | Description |
---|---|---|
GANTRY_MANIFEST_CMD | buildx | Valid values are buildx , manifest , and none .Set which command for manifest inspection.Set to none to skip checking the manifest. As a result of skipping, docker service update always runs. Also see FAQ which GANTRY_MANIFEST_CMD to use. You can apply a different value to a particular service via labels. |
GANTRY_MANIFEST_NUM_WORKERS | 1 | The maximum number of GANTRY_MANIFEST_CMD that can run in parallel. |
GANTRY_MANIFEST_OPTIONS | Options added to the docker buildx imagetools inspect or options to docker manifest inspect , depending on GANTRY_MANIFEST_CMD value, for all services. You can apply a different value to a particular service via labels. |
Environment Variable | Default | Description |
---|---|---|
GANTRY_ROLLBACK_ON_FAILURE | true | Set to true to enable rollback when updating fails. Set to false to disable the rollback. You can apply a different value to a particular service via labels. |
GANTRY_ROLLBACK_OPTIONS | Options added to the docker service update --rollback command for all services. You can apply a different value to a particular service via labels. |
|
GANTRY_UPDATE_JOBS | false | Set to true to update replicated-job or global-job . Set to false to disable updating jobs. Gantry adds additional options to docker service update when there is no running tasks. You can apply a different value to a particular service via labels. |
GANTRY_UPDATE_NUM_WORKERS | 1 | The maximum number of updates that can run in parallel. |
GANTRY_UPDATE_OPTIONS | Options added to the docker service update command for all services. You can apply a different value to a particular service via labels. |
|
GANTRY_UPDATE_TIMEOUT_SECONDS | 0 | Error out if updating of a single service takes longer than the given time. Set to 0 to disable timeout. You can apply a different value to a particular service via labels. |
Environment Variable | Default | Description |
---|---|---|
GANTRY_CLEANUP_IMAGES | true | Set to true to clean up the updated images on all hosts. Set to false to disable the cleanup. Before cleaning up, Gantry will try to remove any exited and dead containers that are using the images. |
GANTRY_CLEANUP_IMAGES_OPTIONS | Options added to the docker service create command to create a global job for images removal. You can use this to add a label to the service or the containers. |
|
GANTRY_NOTIFICATION_APPRISE_URL | Enable notifications on service update with Apprise. This must point to the notification endpoint (e.g. http://apprise:8000/notify ) |
|
GANTRY_NOTIFICATION_CONDITION | all | Valid values are all and on-change . Specifies the conditions under which notifications are sent. Set to all to send notifications every run. Set to on-change to send notifications only when there are updates or errors. |
GANTRY_NOTIFICATION_TITLE | Add an additional message to the notification title. |
Labels can be added to services to modify the behavior of Gantry for particular services. When Gantry sees the following labels on a service, it will modify the Docker command line only for that service. The value on the label overrides the global environment variables.
Label | Description |
---|---|
gantry.auth.config=<configuration> |
Override DOCKER_CONFIG . See Authentication. |
gantry.services.excluded=true |
Exclude the services from updating if you are using the default GANTRY_SERVICES_EXCLUDED_FILTERS . |
gantry.manifest.cmd=<command> |
Override GANTRY_MANIFEST_CMD . |
gantry.manifest.options=<string> |
Override GANTRY_MANIFEST_OPTIONS . |
gantry.rollback.on_failure=<boolean> |
Override GANTRY_ROLLBACK_ON_FAILURE . |
gantry.rollback.options=<string> |
Override GANTRY_ROLLBACK_OPTIONS . |
gantry.update.jobs=<boolean> |
Override GANTRY_UPDATE_JOBS . |
gantry.update.options=<string> |
Override GANTRY_UPDATE_OPTIONS . |
gantry.update.timeout_seconds=<number> |
Override GANTRY_UPDATE_TIMEOUT_SECONDS . |
Gantry is written to work with busybox ash
(v1.35+), thus it could run easily in an alpine-based container without additional packages installed. One exception is that the notification feature requires curl
. Gantry is also tested in bash
.
shellcheck will run on push to enforce the best practices of writing shell scripts. Some checks are disabled thanks to busybox ash
supports more features than POSIX sh
. You can find the list of disabled checks in .shellcheckrc.
To run shellcheck
locally:
shellcheck src/*.sh tests/*.sh
The tests folder contains end-to-end tests, which cover the majority of the configuration options.
If you have any problems or questions, please contact me through a GitHub issue.