Skip to content

Latest commit

 

History

History
130 lines (101 loc) · 4.75 KB

README.md

File metadata and controls

130 lines (101 loc) · 4.75 KB

CLade

test Go Report Card codebeat badge codecov

Keep your container images up to date.

CLade allows you to manage multiple Dockerfiles as a dependency tree and list images older than the upstream image.

Installation

$ go install github.com/lesomnus/clade/cmd/clade@latest

Usage

Command clade reads Port files named port.yaml in the directories of ports directory to construct a dependency tree. Port file describes what an image's tag is and which image that tag depends on.

$ mkdir -p ports/my-gcc
$ code ports/my-gcc/port.yaml
# ports/my-gcc/port.yaml
name: ghcr.io/my_name/my-gcc

images:
  - tags: ['my-tag']
    from: registry.hub.docker.com/library/gcc:latest

The above Port file describes that ghcr.io/my_name/my-gcc:my-tag is built from the registry.hub.docker.com/library/gcc:latest. Let's see if this parses well:

$ clade tree
registry.hub.docker.com/library/gcc:latest
        ghcr.io/my_name/my-gcc:my-tag

This is the most basic usage of CLade. How can we create a new image with that version name whenever a new version of GCC is updated? Probably the simplest way would be to populate a list of images for all versions. Alternatively, there is a way to have CLade fetch tags from the remote repository. Updates our Port file as:

# ports/my-gcc/port.yaml
name: ghcr.io/my_name/my-gcc

images:
  - tags: ( printf "%d.%d" $.Major $.Minor )
    from:
      name: registry.hub.docker.com/library/gcc
      tagd: ( tags | semverLatest )
$ clade tree
registry.hub.docker.com/library/gcc:12.2
        ghcr.io/my_name/my-gcc:12.2

What happened? Where did 12.2 come from? Let's find out one by one. First, what ( remoteTags | semverLatest ) is? This is pipeline expression. The result of the previous function becomes the argument of the next function. So it means, fetch the tags from registry.hub.docker.com, then take the latest semver. That would be 12.2 at this point. The result of the pipeline is Semver type and it is passed to pipeline in tags as a data and the result of the pipeline become result tags.

If there is more than one result of the from pipeline, CLade generates that many images. Let's create my-gcc:12.X for all gcc 12 versions using semverMajorN which filters last N major versions. Also if there are more than one tag or tag pipeline is provided, multiple tags will be created from the same image.

# ports/my-gcc/port.yaml
name: ghcr.io/my_name/my-gcc

images:
  - tags:
      - ( printf "%d.%d" $.Major $.Minor )
      - ( printf "%d"    $.Major         )
    from:
      name: registry.hub.docker.com/library/gcc
      tags: ( tags | semverMajorN 1 )
$ clade tree
registry.hub.docker.com/library/gcc:12
        ghcr.io/my_name/my-gcc:12.0
registry.hub.docker.com/library/gcc:12.1
        ghcr.io/my_name/my-gcc:12.1
registry.hub.docker.com/library/gcc:12.2
        ghcr.io/my_name/my-gcc:12.2
        ghcr.io/my_name/my-gcc:12

You can now track upstream container images. To build, you can use the clade build command. Before that, let's create a Dockerfile first.

code ports/my-gcc/Dockerfile
# ports/my-gcc/Dockerfile
ARG BASE
FROM ${BASE}

ARG USERNAME=my_name
ARG USER_UID=${UID:-1000}
ARG USER_GID=${GID:-${USER_UID}}
RUN groupadd ${USER_GID} --gid ${USER_GID} \
	&& useradd \
		--create-home ${USERNAME} \
		--shell /bin/bash \
		--uid ${USER_UID} \
		--gid ${USER_GID}

WORKDIR /home/${USERNAME}

USER ${USERNAME}

Note that argument BASE is remote container image reference. The command for the default option, clade build simply spawns docker command with proper arguments. Let's see what CLade runs:

$ clade build --dry-run ghcr.io/my_name/my-gcc:12
[/usr/bin/docker build --file /path/to/ports/my-gcc/port.yaml/Dockerfile --tag ghcr.io/my_name/my-gcc:12.2 --tag ghcr.io/my_name/my-gcc:12 --build-arg BASE=registry.hub.docker.com/library/gcc@sha256:9c9194913f48efd4c74ad2cd669b843bdea6325df71f6a32ac04fdd343bec0e0 /path/to/ports/my-gcc]

Materials