Code Monkey home page Code Monkey logo

docker-manifest-create-action's Introduction

docker-manifest-create-action ts

This is an action to create a multi-architecture Docker image in GitHub Actions. It is interoperable with docker/build-push-action and docker/metadata-action.

Purpose

When we build a multi-architecture image using docker/build-push-action, it takes a long time to build all platforms in a single job. It would be nice to build images in parallel and finally create a multi-architecture image from them.

graph LR
  m[Image ghcr.io/owner/repo:tag]
  amd64[Image ghcr.io/owner/repo:tag-linux-amd64] --> m
  arm64[Image ghcr.io/owner/repo:tag-linux-arm64] --> m
  ppc64le[Image ghcr.io/owner/repo:tag-linux-ppc64le] --> m
Loading

We can create a multi-architecture image by the following commands:

This action depends on the commands. For example, if it is called with the following inputs,

      - uses: int128/docker-manifest-create-action@v1
        with:
          tags: ghcr.io/owner/repo:tag
          suffixes: |
            -linux-amd64
            -linux-arm64
            -linux-ppc64le

it executes the following commands:

# create a manifest of multi-architecture image
docker manifest create ghcr.io/owner/repo:tag \
  ghcr.io/owner/repo:tag-linux-amd64 \
  ghcr.io/owner/repo:tag-linux-arm64 \
  ghcr.io/owner/repo:tag-linux-ppc64le

# push the manifest to the remote repository
docker manifest push owner/repo:tag

# verify the manifest
docker manifest inspect owner/repo:tag

See also the following docs:

Getting Started

Here is an example workflow to build a multi-architecture image for amd64 and arm64.

jobs:
  build:
    strategy:
      fail-fast: false
      matrix:
        platform:
          - linux/amd64
          - linux/arm64
    runs-on: ubuntu-latest
    timeout-minutes: 10
    steps:
      - uses: docker/login-action@v2
        with:
          registry: ghcr.io
          username: ${{ github.actor }}
          password: ${{ secrets.GITHUB_TOKEN }}
      - uses: docker/metadata-action@v4
        id: metadata
        with:
          images: ghcr.io/${{ github.repository }}
          # avoid overwriting the latest tag because metadata-action does not add a suffix to it
          flavor: latest=false,suffix=-${{ matrix.platform }}
      - uses: docker/setup-buildx-action@v2
      - uses: docker/build-push-action@v3
        with:
          push: true
          tags: ${{ steps.metadata.outputs.tags }}
          labels: ${{ steps.metadata.outputs.labels }}
          platforms: ${{ matrix.platform }}

  build-multi-architecture:
    needs:
      - build
    runs-on: ubuntu-latest
    timeout-minutes: 10
    steps:
      - uses: docker/login-action@v2
        with:
          registry: ghcr.io
          username: ${{ github.actor }}
          password: ${{ secrets.GITHUB_TOKEN }}
      - uses: docker/metadata-action@v4
        id: metadata
        with:
          images: ghcr.io/${{ github.repository }}
      - uses: int128/docker-manifest-create-action@v1
        with:
          tags: ${{ steps.metadata.outputs.tags }}
          suffixes: |
            -linux-amd64
            -linux-arm64

Here is a diagram of this workflow:

graph TB
  subgraph Workflow
    amd64[build linux/amd64] --> build-multi-architecture
    arm64[build linux/arm64] --> build-multi-architecture
    build-multi-architecture
  end
Loading

See also the full example of e2e-test with cache options.

For branches

When main branch is pushed, build job creates the following images by default of docker/metadata-action:

  • ghcr.io/owner/repo:main-linux-amd64
  • ghcr.io/owner/repo:main-linux-arm64

Then, build-multi-architecture job creates the following image:

  • ghcr.io/owner/repo:main

For tags

When v1.0.0 tag is pushed, build job creates the following images by default of docker/metadata-action:

  • ghcr.io/owner/repo:v1.0.0-linux-amd64
  • ghcr.io/owner/repo:v1.0.0-linux-arm64

Because docker/metadata-action does not add a suffix to latest tag, it needs to set latest=false to avoid overwriting latest tag for each build.

Finally, build-multi-architecture job creates the following images:

  • ghcr.io/owner/repo:v1.0.0
  • ghcr.io/owner/repo:latest

If latest tag is given, this action pushes it from the non-latest tag.

Native build on self-hosted runners

If you are using the self-hosted runners, you can build an image faster. For example, you can natively build an arm64 image on AWS Graviton 2.

Here is an example workflow.

jobs:
  build:
    strategy:
      fail-fast: false
      matrix:
        platform:
          - amd64
          - arm64
    runs-on:
      - self-hosted
      - ubuntu-${{ matrix.platform }}
    permissions:
      id-token: write
      contents: read
    steps:
      - uses: aws-actions/configure-aws-credentials@v1
        with:
          role-to-assume: arn:aws:iam::ACCOUNT:role/ROLE
      - uses: aws-actions/amazon-ecr-login@v1
        id: ecr
      - uses: docker/metadata-action@v4
        id: metadata
        with:
          images: ${{ steps.ecr.outputs.registry }}/${{ github.repository }}
          flavor: suffix=-${{ matrix.platform }}
      - uses: docker/build-push-action@v3
        with:
          push: true
          tags: ${{ steps.metadata.outputs.tags }}
          labels: ${{ steps.metadata.outputs.labels }}

  build-multi-architecture:
    needs:
      - build
    runs-on: ubuntu-latest
    permissions:
      id-token: write
      contents: read
    steps:
      - uses: aws-actions/configure-aws-credentials@v1
        with:
          role-to-assume: arn:aws:iam::ACCOUNT:role/ROLE
      - uses: aws-actions/amazon-ecr-login@v1
        id: ecr
      - uses: docker/metadata-action@v4
        id: metadata
        with:
          images: ${{ steps.ecr.outputs.registry }}/${{ github.repository }}
      - uses: int128/docker-manifest-create-action@v1
        with:
          tags: ${{ steps.metadata.outputs.tags }}
          suffixes: |
            -amd64
            -arm64

Specification

Inputs

Name Default Description
tags (required) tags of destination images (multi-line string)
suffixes (required) suffixes of source images (multi-line string)

Outputs

Nothing.

Behavior

This action runs the following commands for each tag.

docker manifest create {tag} {tag}{suffix}...
docker manifest push {tag}
docker manifest inspect {tag}

docker-manifest-create-action's People

Contributors

fdkevin0 avatar github-actions[bot] avatar int128 avatar renovate[bot] avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.