Introduction

Kompozit is a tool inspired by Kustomize. While Kustomize simplifies Kubernetes configurations, Kompozit does the same for docker-compose. It enables you to customize and patch docker-compose.yaml files efficiently, reducing redundancy and improving maintainability.

Why Kompozit? ๐Ÿค”

Managing multiple docker-compose configurations can be cumbersome. For instance:

โ€ข You have a docker-compose-traefik.yaml for a Traefik reverse proxy.

โ€ข You need different setups for:

  1. A simple home server (docker-compose-traefik-simple.yaml).

  2. A public website with additional security (docker-compose-traefik-secured.yaml).

These configurations share most content, but a few details differ. This leads to duplication and makes updates tedious. ๐Ÿ˜ตโ€๐Ÿ’ซ

Enter Kompozit! ๐ŸŽ‰

Kompozit lets you:

1. ๐Ÿ“‚ Store your base configurations in a reusable โ€œbaseโ€ folder.

2. โœ๏ธ Define overlays for different setups (e.g., โ€œhome serverโ€ or โ€œpublic websiteโ€).

3. ๐Ÿ”„ Apply patches to the base configuration without modifying it directly.

Example Use Case ๐Ÿ’ก

Base Configuration ๐Ÿ—๏ธ

Start with a base folder containing your generic docker-compose setup.

$ tree base/
base/
โ”œโ”€โ”€ docker-compose-traefik.yml
โ””โ”€โ”€ kompozition.yml

โ€ข docker-compose-traefik.yml: The base Traefik configuration. ๐Ÿ›ณ๏ธ

โ€ข kompozition.yml: Declares resources for Kompozit to process. ๐Ÿ“œ

kompozition.yml:

resources:
  - docker-compose-traefik.yml

docker-compose-traefik.yml:

networks:
  public:
    attachable: true
    internal: false
  private:
    attachable: true
    internal: true

volumes:
  acme:

services:
  traefik:
    image: traefik:latest
    hostname: traefik
    container_name: traefik
    restart: unless-stopped
    environment:
      DUCKDNS_TOKEN: "${DUCKDNS_TOKEN}"
      CLOUDFLARE_DNS_API_TOKEN: "${CLOUDFLARE_DNS_API_TOKEN}"
    ports:
      - 80:80/tcp
      - 443:443/tcp
    networks:
      - public
      - private
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock
      - acme:/letsencrypt

This setup is the reusable core of your configuration. ๐Ÿ”ง

Overlay Customization ๐Ÿ–๏ธ

Now, create overlays for specific use cases. ๐Ÿ—‚๏ธ

$ tree overlay/
overlay/
โ”œโ”€โ”€ homeserver
โ”‚ย ย  โ”œโ”€โ”€ docker-compose-traefik-patch.yml
โ”‚ย ย  โ””โ”€โ”€ kompozition.yaml
โ””โ”€โ”€ public_wordpress
    โ”œโ”€โ”€ docker-compose-traefik-patch.yml
    โ””โ”€โ”€ kompozition.yaml

Each overlay:

1. References the base configuration. ๐Ÿ—บ๏ธ

2. Applies patches specific to the use case. ๐Ÿ› ๏ธ

overlay/homeserver/kompozition.yaml:

resources:
  - ../../base

patchesStrategicMerge:
  - path: docker-compose-traefik-patch.yml

overlay/homeserver/docker-compose-traefik-patch.yml:

services:
  traefik:
    command:
      - "--log.level=INFO"
      - "--api.insecure=false"
      - "--api.dashboard=true"
      - "--providers.docker=true"
      - "--providers.docker.exposedByDefault=false"
      - "--global.sendAnonymousUsage=false"
      - "--global.checkNewVersion=false"
    labels:
      - com.centurylinklabs.watchtower.enable=true

Run Kompozit ๐Ÿƒโ€โ™‚๏ธ

Use Kompozit to generate the final patched configuration. ๐Ÿงฉ

$ kompozit -b overlay/homeserver/
networks:
  public:
    attachable: true
    internal: false
  private:
    attachable: true
    internal: true

volumes:
  acme: null

services:
  traefik:
    image: traefik:latest
    hostname: traefik
    container_name: traefik
    restart: unless-stopped
    labels:
      - com.centurylinklabs.watchtower.enable=true
    environment:
      DUCKDNS_TOKEN: ${DUCKDNS_TOKEN}
      CLOUDFLARE_DNS_API_TOKEN: ${CLOUDFLARE_DNS_API_TOKEN}
    ports:
      - 80:80/tcp
      - 443:443/tcp
    networks:
      - public
      - private
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock
      - acme:/letsencrypt
    command:
      - --log.level=INFO
      - --api.insecure=false
      - --api.dashboard=true
      - --providers.docker=true
      - --providers.docker.exposedByDefault=false
      - --global.sendAnonymousUsage=false
      - --global.checkNewVersion=false

Deploy the Final Configuration ๐Ÿšข

Redirect the output to a file and deploy it using Docker Compose. ๐ŸŽฏ

$ kompozit -b overlay/homeserver/ > final-docker-compose.yml
$ docker-compose -f final-docker-compose.yml up -d

Last updated