Skip to content

Commit f5b5038

Browse files
authored
Merge pull request #695 from ConsortiumGARR/main
feat: publish container images to GHCR
2 parents 55a5fd8 + c34d974 commit f5b5038

1 file changed

Lines changed: 173 additions & 0 deletions

File tree

.github/workflows/docker-image.yml

Lines changed: 173 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,173 @@
1+
# Inspired by https://github.com/sredevopsorg/multi-arch-docker-github-workflow
2+
name: Docker Image CI
3+
4+
on:
5+
push:
6+
tags:
7+
- "v[0-9]+.[0-9]+.[0-9]+"
8+
workflow_dispatch:
9+
inputs:
10+
upstream_tag:
11+
description: "Upstream tag of nextcloud/notify_push to build"
12+
required: false
13+
14+
jobs:
15+
build:
16+
runs-on: ${{ matrix.runner }}
17+
18+
permissions:
19+
contents: read
20+
packages: write
21+
22+
strategy:
23+
fail-fast: false
24+
matrix:
25+
include:
26+
- platform: linux/amd64
27+
runner: ubuntu-latest
28+
- platform: linux/arm64
29+
runner: ubuntu-24.04-arm
30+
31+
steps:
32+
- name: Checkout code
33+
uses: actions/checkout@v6
34+
with:
35+
repository: ${{ inputs.upstream_tag && 'nextcloud/notify_push' || github.repository }}
36+
ref: ${{ inputs.upstream_tag || github.ref_name }}
37+
38+
- name: Log in to GitHub Packages
39+
uses: docker/login-action@v4
40+
with:
41+
registry: ghcr.io
42+
username: ${{ github.actor }}
43+
password: ${{ secrets.GITHUB_TOKEN }}
44+
45+
- name: Set up Docker Buildx
46+
uses: docker/setup-buildx-action@v4
47+
48+
- name: Lower case docker image name
49+
id: image
50+
uses: ASzc/change-string-case-action@v8
51+
with:
52+
string: ${{ github.repository }}
53+
54+
- name: Sanitize upstream tag
55+
if: inputs.upstream_tag != ''
56+
id: tag
57+
run: echo "value=${INPUT_TAG#v}" >> $GITHUB_OUTPUT
58+
env:
59+
INPUT_TAG: ${{ inputs.upstream_tag }}
60+
61+
- name: Extract metadata
62+
id: meta
63+
uses: docker/metadata-action@v6
64+
with:
65+
images: ghcr.io/${{ github.repository }}
66+
tags: |
67+
type=ref,event=tag
68+
type=raw,value=latest
69+
type=raw,value=${{ steps.tag.outputs.value }},enable=${{ inputs.upstream_tag != '' }}
70+
71+
- name: Build and push by digest
72+
id: build
73+
uses: docker/build-push-action@v7
74+
with:
75+
context: .
76+
platforms: ${{ matrix.platform }}
77+
labels: ${{ steps.meta.outputs.labels }}
78+
outputs: type=image,name=ghcr.io/${{ steps.image.outputs.lowercase }},push-by-digest=true,name-canonical=true,push=true
79+
cache-from: type=gha,scope=${{ matrix.platform }}
80+
cache-to: type=gha,mode=max,scope=${{ matrix.platform }}
81+
82+
- name: Export digest
83+
run: |
84+
mkdir -p /tmp/digests
85+
touch "/tmp/digests/${DIGEST#sha256:}"
86+
env:
87+
DIGEST: ${{ steps.build.outputs.digest }}
88+
89+
- name: Upload digest
90+
uses: actions/upload-artifact@v7
91+
with:
92+
name: digests-${{ matrix.platform == 'linux/amd64' && 'amd64' || 'arm64' }}
93+
path: /tmp/digests/*
94+
if-no-files-found: error
95+
retention-days: 1
96+
97+
merge:
98+
runs-on: ubuntu-latest
99+
needs: build
100+
101+
permissions:
102+
contents: read
103+
packages: write
104+
105+
steps:
106+
- name: Download digests
107+
uses: actions/download-artifact@v8
108+
with:
109+
path: /tmp/digests
110+
pattern: digests-*
111+
merge-multiple: true
112+
113+
- name: Log in to GitHub Packages
114+
uses: docker/login-action@v4
115+
with:
116+
registry: ghcr.io
117+
username: ${{ github.actor }}
118+
password: ${{ secrets.GITHUB_TOKEN }}
119+
120+
- name: Set up Docker Buildx
121+
uses: docker/setup-buildx-action@v4
122+
123+
- name: Lower case docker image name
124+
id: image
125+
uses: ASzc/change-string-case-action@v8
126+
with:
127+
string: ${{ github.repository }}
128+
129+
- name: Sanitize upstream tag
130+
if: inputs.upstream_tag != ''
131+
id: tag
132+
run: echo "value=${INPUT_TAG#v}" >> $GITHUB_OUTPUT
133+
env:
134+
INPUT_TAG: ${{ inputs.upstream_tag }}
135+
136+
- name: Extract metadata
137+
id: meta
138+
uses: docker/metadata-action@v6
139+
with:
140+
images: ghcr.io/${{ github.repository }}
141+
tags: |
142+
type=ref,event=tag
143+
type=raw,value=latest
144+
type=raw,value=${{ steps.tag.outputs.value }},enable=${{ inputs.upstream_tag != '' }}
145+
146+
- name: Get timestamp
147+
id: timestamp
148+
run: echo "timestamp=$(date -u +"%Y-%m-%dT%H:%M:%SZ")" >> $GITHUB_OUTPUT
149+
150+
- name: Create and push manifest
151+
id: manifest
152+
working-directory: /tmp/digests
153+
continue-on-error: true
154+
run: |
155+
docker buildx imagetools create \
156+
$(jq -cr '.tags | map("-t " + .) | join(" ")' <<< "$DOCKER_METADATA_OUTPUT_JSON") \
157+
--annotation='index:org.opencontainers.image.description=${{ github.event.repository.description }}' \
158+
--annotation='index:org.opencontainers.image.created=${{ steps.timestamp.outputs.timestamp }}' \
159+
--annotation='index:org.opencontainers.image.url=${{ github.event.repository.url }}' \
160+
--annotation='index:org.opencontainers.image.source=${{ github.event.repository.url }}' \
161+
$(printf 'ghcr.io/${{ steps.image.outputs.lowercase }}@sha256:%s ' *)
162+
163+
- name: Create and push manifest (without annotations)
164+
if: steps.manifest.outcome == 'failure'
165+
working-directory: /tmp/digests
166+
run: |
167+
docker buildx imagetools create \
168+
$(jq -cr '.tags | map("-t " + .) | join(" ")' <<< "$DOCKER_METADATA_OUTPUT_JSON") \
169+
$(printf 'ghcr.io/${{ steps.image.outputs.lowercase }}@sha256:%s ' *)
170+
171+
- name: Inspect manifest
172+
run: |
173+
docker buildx imagetools inspect 'ghcr.io/${{ steps.image.outputs.lowercase }}:${{ steps.meta.outputs.version }}'

0 commit comments

Comments
 (0)