Skip to content

Commit 8d18a9d

Browse files
committed
try pushing image
1 parent 61fa254 commit 8d18a9d

File tree

3 files changed

+227
-110
lines changed

3 files changed

+227
-110
lines changed

.github/workflows/pull_request.yml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,8 +32,11 @@ jobs:
3232
needs: [get_asdf_version]
3333
with:
3434
asdfVersion: ${{ needs.get_asdf_version.outputs.asdf_version }}
35+
dev_container_ecr: dev-container-quality-checks
36+
dev_container_image_tag: latest
3537
secrets:
3638
SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }}
39+
CLOUD_FORMATION_DEPLOY_ROLE: ${{ secrets.CLOUD_FORMATION_DEPLOY_ROLE }}
3740
tag_release:
3841
needs: [quality_checks, get_asdf_version]
3942
uses: NHSDigital/eps-workflow-semantic-release/.github/workflows/tag-release.yml@f80157cecce288dd175e61b477a1d2dbe9c88b99

.github/workflows/quality-checks.yml

Lines changed: 101 additions & 110 deletions
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,6 @@ jobs:
4646
- name: Checkout code
4747
uses: actions/checkout@v5
4848
with:
49-
ref: ${{ env.BRANCH_NAME }}
5049
fetch-depth: 0
5150

5251
# Must be done before anything installs, or it will check dependencies for secrets too.
@@ -367,137 +366,129 @@ jobs:
367366
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
368367
SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }}
369368

370-
build_dev_container_cross_compile:
369+
build_dev_container_x64:
371370
runs-on: ubuntu-22.04
371+
if: ${{ inputs.dev_container_ecr != '' && inputs.dev_container_image_tag != '' }}
372372
steps:
373373
- name: Checkout code
374374
uses: actions/checkout@v5
375375
with:
376-
ref: ${{ env.BRANCH_NAME }}
377376
fetch-depth: 0
378377

379378
- name: Build dev container
380379
run: |
381-
docker buildx create --use
382-
docker buildx build --platform linux/amd64,linux/arm64 -f .devcontainer/Dockerfile -t dev-container-image .
383-
# - name: Configure AWS Credentials
384-
# uses: aws-actions/configure-aws-credentials@v5
385-
# id: connect-aws-deploy
386-
# with:
387-
# aws-region: eu-west-2
388-
# role-to-assume: ${{ secrets.CLOUD_FORMATION_DEPLOY_ROLE }}
389-
# role-session-name: dev-container-build
390-
# output-credentials: true
391-
392-
# - name: Retrieve AWS Account ID
393-
# id: retrieve-deploy-account-id
394-
# run: echo "ACCOUNT_ID=$(aws sts get-caller-identity --query Account --output text)" >> "$GITHUB_ENV"
395-
396-
# - name: Login to Amazon ECR
397-
# id: login-ecr-push-image
398-
# run: |
399-
# aws ecr get-login-password --region eu-west-2 | docker login --username AWS --password-stdin ${{ env.ACCOUNT_ID }}.dkr.ecr.eu-west-2.amazonaws.com
400-
401-
# - name: Push FHIR Facade image to Amazon ECR
402-
# run: |
403-
# docker tag "dev-container-image" "${{ env.ACCOUNT_ID }}.dkr.ecr.eu-west-2.amazonaws.com/${{inputs.DEV_CONTAINER_ECR}}:${{ inputs.DEV_CONTAINER_IMAGE_TAG }}"
404-
# docker push "${{ env.ACCOUNT_ID }}.dkr.ecr.eu-west-2.amazonaws.com/${{inputs.DEV_CONTAINER_ECR}}:${{ inputs.DEV_CONTAINER_IMAGE_TAG }}"
405-
406-
# - name: Check dev container scan results
407-
# env:
408-
# REPOSITORY_NAME: ${{inputs.DEV_CONTAINER_ECR}}
409-
# IMAGE_TAG: ${{ inputs.DEV_CONTAINER_IMAGE_TAG }}
410-
# working-directory: .github/scripts
411-
# run: |
412-
# ./check_ecr_image_scan_results.sh
413-
build_dev_container_x64:
414-
runs-on: ubuntu-22.04
415-
steps:
416-
- name: Checkout code
417-
uses: actions/checkout@v5
380+
docker build -f .devcontainer/Dockerfile -t dev-container-image .
381+
382+
- name: Configure AWS Credentials
383+
uses: aws-actions/configure-aws-credentials@v5
384+
id: connect-aws-deploy
418385
with:
419-
ref: ${{ env.BRANCH_NAME }}
420-
fetch-depth: 0
386+
aws-region: eu-west-2
387+
role-to-assume: ${{ secrets.CLOUD_FORMATION_DEPLOY_ROLE }}
388+
role-session-name: dev-container-build-x64
389+
output-credentials: true
421390

422-
- name: Build dev container
391+
- name: Retrieve AWS Account ID
392+
id: retrieve-deploy-account-id
423393
run: |
424-
docker build -f .devcontainer/Dockerfile -t dev-container-image .
425-
# - name: Configure AWS Credentials
426-
# uses: aws-actions/configure-aws-credentials@v5
427-
# id: connect-aws-deploy
428-
# with:
429-
# aws-region: eu-west-2
430-
# role-to-assume: ${{ secrets.CLOUD_FORMATION_DEPLOY_ROLE }}
431-
# role-session-name: dev-container-build
432-
# output-credentials: true
433-
434-
# - name: Retrieve AWS Account ID
435-
# id: retrieve-deploy-account-id
436-
# run: echo "ACCOUNT_ID=$(aws sts get-caller-identity --query Account --output text)" >> "$GITHUB_ENV"
437-
438-
# - name: Login to Amazon ECR
439-
# id: login-ecr-push-image
440-
# run: |
441-
# aws ecr get-login-password --region eu-west-2 | docker login --username AWS --password-stdin ${{ env.ACCOUNT_ID }}.dkr.ecr.eu-west-2.amazonaws.com
442-
443-
# - name: Push FHIR Facade image to Amazon ECR
444-
# run: |
445-
# docker tag "dev-container-image" "${{ env.ACCOUNT_ID }}.dkr.ecr.eu-west-2.amazonaws.com/${{inputs.DEV_CONTAINER_ECR}}:${{ inputs.DEV_CONTAINER_IMAGE_TAG }}"
446-
# docker push "${{ env.ACCOUNT_ID }}.dkr.ecr.eu-west-2.amazonaws.com/${{inputs.DEV_CONTAINER_ECR}}:${{ inputs.DEV_CONTAINER_IMAGE_TAG }}"
447-
448-
# - name: Check dev container scan results
449-
# env:
450-
# REPOSITORY_NAME: ${{inputs.DEV_CONTAINER_ECR}}
451-
# IMAGE_TAG: ${{ inputs.DEV_CONTAINER_IMAGE_TAG }}
452-
# working-directory: .github/scripts
453-
# run: |
454-
# ./check_ecr_image_scan_results.sh
394+
ACCOUNT_ID=$(aws sts get-caller-identity --query Account --output text)
395+
echo "account_id=$ACCOUNT_ID" >> "$GITHUB_OUTPUT"
396+
397+
- name: Login to Amazon ECR
398+
run: |
399+
aws ecr get-login-password --region eu-west-2 | docker login --username AWS --password-stdin ${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com
400+
401+
- name: Push x64 image to Amazon ECR
402+
run: |
403+
docker tag "dev-container-image" "${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }}-amd64"
404+
docker push "${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }}-amd64"
455405
456406
build_dev_container_arm64:
457407
runs-on: ubuntu-22.04-arm
408+
if: ${{ inputs.dev_container_ecr != '' && inputs.dev_container_image_tag != '' }}
458409
steps:
459410
- name: Checkout code
460411
uses: actions/checkout@v5
461412
with:
462-
ref: ${{ env.BRANCH_NAME }}
463413
fetch-depth: 0
464414

465415
- name: Build dev container
466416
run: |
467417
docker build -f .devcontainer/Dockerfile -t dev-container-image-arm .
468-
docker save "dev-container-image-arm" -o dev-container-image-arm.img
469-
- uses: actions/upload-artifact@v4
470-
name: upload build artifact
418+
419+
- name: Configure AWS Credentials
420+
uses: aws-actions/configure-aws-credentials@v5
421+
id: connect-aws-deploy
471422
with:
472-
name: dev-container-image-arm
473-
path: dev-container-image-arm.img
474-
# - name: Configure AWS Credentials
475-
# uses: aws-actions/configure-aws-credentials@v5
476-
# id: connect-aws-deploy
477-
# with:
478-
# aws-region: eu-west-2
479-
# role-to-assume: ${{ secrets.CLOUD_FORMATION_DEPLOY_ROLE }}
480-
# role-session-name: dev-container-build
481-
# output-credentials: true
482-
483-
# - name: Retrieve AWS Account ID
484-
# id: retrieve-deploy-account-id
485-
# run: echo "ACCOUNT_ID=$(aws sts get-caller-identity --query Account --output text)" >> "$GITHUB_ENV"
486-
487-
# - name: Login to Amazon ECR
488-
# id: login-ecr-push-image
489-
# run: |
490-
# aws ecr get-login-password --region eu-west-2 | docker login --username AWS --password-stdin ${{ env.ACCOUNT_ID }}.dkr.ecr.eu-west-2.amazonaws.com
491-
492-
# - name: Push FHIR Facade image to Amazon ECR
493-
# run: |
494-
# docker tag "dev-container-image" "${{ env.ACCOUNT_ID }}.dkr.ecr.eu-west-2.amazonaws.com/${{inputs.DEV_CONTAINER_ECR}}:${{ inputs.DEV_CONTAINER_IMAGE_TAG }}"
495-
# docker push "${{ env.ACCOUNT_ID }}.dkr.ecr.eu-west-2.amazonaws.com/${{inputs.DEV_CONTAINER_ECR}}:${{ inputs.DEV_CONTAINER_IMAGE_TAG }}"
496-
497-
# - name: Check dev container scan results
498-
# env:
499-
# REPOSITORY_NAME: ${{inputs.DEV_CONTAINER_ECR}}
500-
# IMAGE_TAG: ${{ inputs.DEV_CONTAINER_IMAGE_TAG }}
501-
# working-directory: .github/scripts
502-
# run: |
503-
# ./check_ecr_image_scan_results.sh
423+
aws-region: eu-west-2
424+
role-to-assume: ${{ secrets.CLOUD_FORMATION_DEPLOY_ROLE }}
425+
role-session-name: dev-container-build-arm64
426+
output-credentials: true
427+
428+
- name: Retrieve AWS Account ID
429+
id: retrieve-deploy-account-id
430+
run: |
431+
ACCOUNT_ID=$(aws sts get-caller-identity --query Account --output text)
432+
echo "account_id=$ACCOUNT_ID" >> "$GITHUB_OUTPUT"
433+
434+
- name: Login to Amazon ECR
435+
run: |
436+
aws ecr get-login-password --region eu-west-2 | docker login --username AWS --password-stdin ${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com
437+
438+
- name: Push ARM64 image to Amazon ECR
439+
run: |
440+
docker tag "dev-container-image-arm" "${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }}-arm64"
441+
docker push "${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }}-arm64"
442+
443+
create_multi_arch_manifest:
444+
runs-on: ubuntu-22.04
445+
needs: [build_dev_container_x64, build_dev_container_arm64]
446+
if: ${{ inputs.dev_container_ecr != '' && inputs.dev_container_image_tag != '' }}
447+
steps:
448+
- name: Set up Docker Buildx
449+
uses: docker/setup-buildx-action@v3
450+
451+
- name: Configure AWS Credentials
452+
uses: aws-actions/configure-aws-credentials@v5
453+
with:
454+
aws-region: eu-west-2
455+
role-to-assume: ${{ secrets.CLOUD_FORMATION_DEPLOY_ROLE }}
456+
role-session-name: multi-arch-manifest
457+
output-credentials: true
458+
459+
- name: Retrieve AWS Account ID
460+
id: retrieve-deploy-account-id
461+
run: |
462+
ACCOUNT_ID=$(aws sts get-caller-identity --query Account --output text)
463+
echo "account_id=$ACCOUNT_ID" >> "$GITHUB_OUTPUT"
464+
465+
- name: Login to Amazon ECR
466+
run: |
467+
aws ecr get-login-password --region eu-west-2 | docker login --username AWS --password-stdin ${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com
468+
469+
- name: Create and push multi-architecture manifest
470+
run: |
471+
# Create manifest list combining both architectures
472+
docker buildx imagetools create -t ${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }} \
473+
${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }}-amd64 \
474+
${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }}-arm64
475+
476+
# Also create latest tag
477+
docker buildx imagetools create -t ${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:latest \
478+
${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }}-amd64 \
479+
${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }}-arm64
480+
481+
- name: Verify multi-architecture manifest
482+
run: |
483+
echo "=== Verifying multi-architecture manifest ==="
484+
docker buildx imagetools inspect ${{ steps.retrieve-deploy-account-id.outputs.account_id }}.dkr.ecr.eu-west-2.amazonaws.com/${{ inputs.dev_container_ecr }}:${{ inputs.dev_container_image_tag }}
485+
486+
- name: Check dev container scan results
487+
env:
488+
REPOSITORY_NAME: ${{ inputs.dev_container_ecr }}
489+
IMAGE_TAG: ${{ inputs.dev_container_image_tag }}
490+
working-directory: .github/scripts
491+
run: |
492+
# Wait a moment for ECR to process the new manifest
493+
sleep 30
494+
./check_ecr_image_scan_results.sh

MULTI_ARCH_DOCKER.md

Lines changed: 123 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,123 @@
1+
# Multi-Architecture Docker Images (Separate Build Approach)
2+
3+
This workflow builds multi-architecture Docker images by combining separate architecture-specific builds. This approach is more efficient than cross-compilation when you have native runners for each architecture.
4+
5+
## How It Works
6+
7+
### 1. Separate Architecture Builds
8+
- **`build_dev_container_x64`**: Builds on `ubuntu-22.04` (native x64)
9+
- **`build_dev_container_arm64`**: Builds on `ubuntu-22.04-arm` (native ARM64)
10+
11+
Each job:
12+
1. Builds the Docker image natively for its architecture
13+
2. Pushes it to ECR with an architecture-specific tag (e.g., `:v1.0.0-amd64`, `:v1.0.0-arm64`)
14+
15+
### 2. Multi-Architecture Manifest Creation
16+
- **`create_multi_arch_manifest`**: Combines both images into a multi-arch manifest
17+
- Uses `docker buildx imagetools create` to create a manifest list
18+
- Creates both versioned tag (`:v1.0.0`) and `:latest` tag
19+
20+
## Usage
21+
22+
### To Build and Push Multi-Architecture Images
23+
24+
Call the workflow with both required inputs:
25+
26+
```yaml
27+
uses: ./.github/workflows/quality-checks.yml
28+
with:
29+
dev_container_ecr: "your-repo-name"
30+
dev_container_image_tag: "v1.0.0"
31+
asdfVersion: "v0.10.2"
32+
secrets:
33+
CLOUD_FORMATION_DEPLOY_ROLE: ${{ secrets.CLOUD_FORMATION_DEPLOY_ROLE }}
34+
```
35+
36+
This will:
37+
1. Build x64 image → push as `:v1.0.0-amd64`
38+
2. Build ARM64 image → push as `:v1.0.0-arm64`
39+
3. Create manifest combining both → available as `:v1.0.0` and `:latest`
40+
41+
### To Skip Multi-Architecture Build
42+
43+
Call without ECR inputs to skip the container builds entirely:
44+
45+
```yaml
46+
uses: ./.github/workflows/quality-checks.yml
47+
with:
48+
asdfVersion: "v0.10.2"
49+
```
50+
51+
## What Users Get
52+
53+
Users can pull with a single command:
54+
```bash
55+
docker pull 123456789012.dkr.ecr.eu-west-2.amazonaws.com/your-repo:v1.0.0
56+
```
57+
58+
Docker automatically serves:
59+
- `:v1.0.0-amd64` for Intel/AMD x64 systems
60+
- `:v1.0.0-arm64` for ARM64 systems (Apple Silicon, ARM servers)
61+
62+
## Benefits of This Approach
63+
64+
✅ **Faster builds**: Native compilation is much faster than cross-compilation
65+
✅ **Parallel execution**: Both architectures build simultaneously
66+
✅ **Automatic platform detection**: Users get the right architecture transparently
67+
✅ **Conditional execution**: Only runs when ECR inputs are provided
68+
✅ **Security scanning**: Includes ECR vulnerability scanning
69+
✅ **Verification**: Confirms multi-arch manifest was created correctly
70+
71+
## Architecture Flow
72+
73+
```
74+
┌─────────────────┐ ┌─────────────────┐
75+
│ build_x64 │ │ build_arm64 │
76+
│ (ubuntu-22.04) │ │ (ubuntu-22.04- │
77+
│ │ │ arm) │
78+
│ Build & Push │ │ Build & Push │
79+
:tag-amd64 │ │ :tag-arm64
80+
└─────────┬───────┘ └─────────┬───────┘
81+
│ │
82+
└──────────┬───────────┘
83+
84+
┌────────────▼────────────┐
85+
│ create_multi_arch_
86+
│ manifest │
87+
│ (ubuntu-22.04) │
88+
│ │
89+
│ Combine into: │
90+
:tag (multi-arch) │
91+
:latest (multi-arch) │
92+
└─────────────────────────┘
93+
```
94+
95+
## Verification
96+
97+
After the workflow completes, you can verify the multi-architecture manifest:
98+
99+
```bash
100+
# Check the manifest
101+
docker buildx imagetools inspect 123456789012.dkr.ecr.eu-west-2.amazonaws.com/your-repo:v1.0.0
102+
103+
# Should show both architectures:
104+
Name: 123456789012.dkr.ecr.eu-west-2.amazonaws.com/your-repo:v1.0.0
105+
MediaType: application/vnd.docker.distribution.manifest.list.v2+json
106+
107+
Manifests:
108+
Name: ...your-repo:v1.0.0@sha256:...
109+
MediaType: application/vnd.docker.distribution.manifest.v2+json
110+
Platform: linux/amd64
111+
112+
Name: ...your-repo:v1.0.0@sha256:...
113+
MediaType: application/vnd.docker.distribution.manifest.v2+json
114+
Platform: linux/arm64
115+
```
116+
117+
## Technical Details
118+
119+
- **Job Dependencies**: `create_multi_arch_manifest` waits for both build jobs via `needs:`
120+
- **Conditional Execution**: All container jobs only run when ECR inputs are provided
121+
- **AWS Authentication**: Each job authenticates separately to AWS
122+
- **Build Tools**: Uses Docker Buildx imagetools for manifest creation
123+
- **Security**: 30-second delay before scanning allows ECR to process new images

0 commit comments

Comments
 (0)