Skip to content

Add Docker build workflow#98

Merged
jack-arturo merged 14 commits into
verygoodplugins:mainfrom
sakullla:main
Mar 7, 2026
Merged

Add Docker build workflow#98
jack-arturo merged 14 commits into
verygoodplugins:mainfrom
sakullla:main

Conversation

@sakullla

Copy link
Copy Markdown
Contributor

Add Docker build workflow

@coderabbitai

coderabbitai Bot commented Feb 26, 2026

Copy link
Copy Markdown
Contributor

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Adds three new GitHub Actions workflows (.github/workflows/docker-build.yml, .github/workflows/docker-build-mcp-sse-server.yml, .github/workflows/docker-build-mcp-sse-server-tags.yml) to build multi-arch Docker images with Buildx, compute tag metadata, conditionally log into ghcr.io, push non-PR builds, and generate provenance attestations; triggers include pushes to main, v* tags, PRs to main, and manual dispatch.

Changes

Cohort / File(s) Summary
General Docker Build Workflow
.github/workflows/docker-build.yml
New workflow: sets up Docker Buildx, extracts tag metadata (branch/PR, semver variants, short SHA, latest, optional manual tag), conditionally logs into ghcr.io (skips for PRs), builds multi-arch images (linux/amd64, linux/arm64) with buildx cache, pushes images for non-PR runs, generates provenance attestations, and prints digest/tags.
MCP SSE Server Docker Workflow (build & publish)
.github/workflows/docker-build-mcp-sse-server.yml
New two-job workflow that separates build (no push) and publish (push + attestation). Computes metadata, builds multi-arch images, and publishes on non-PR runs; outputs tags, labels, and digest.
MCP SSE Server Tags-only Workflow
.github/workflows/docker-build-mcp-sse-server-tags.yml
New tags-triggered workflow: runs on v* tags, logs into ghcr.io, computes semver/sha metadata, builds and pushes image tags and labels, generates and pushes provenance attestations, and prints digest/tags.

Sequence Diagram(s)

sequenceDiagram
  participant Dev as Developer
  participant GH as GitHub Actions
  participant Runner as Runner / Buildx
  participant Registry as ghcr.io

  Dev->>GH: push to main / push v* tag / open PR / workflow_dispatch
  GH->>Runner: checkout repo & setup buildx
  Runner->>Runner: compute tag metadata (branch/PR/semver/sha/latest/custom)
  alt PR run
    Runner->>Runner: build image (no push), output digest/tags
    Runner-->>GH: emit build outputs
  else non-PR run (branch or manual)
    Runner->>Registry: login to ghcr.io
    Runner->>Runner: build multi-arch images with cache (linux/amd64, linux/arm64)
    Runner->>Registry: push images & manifest
    Runner->>Runner: create provenance attestation
    Runner-->>GH: emit image digest and computed tags
  end
  alt tag push (v* tag)
    Runner->>Registry: login to ghcr.io
    Runner->>Runner: build & push semver-derived tags and labels
    Runner->>Runner: generate and push attestation
    Runner-->>GH: emit digest and tags
  end
Loading

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~10 minutes

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately describes the main change in the pull request, which is adding Docker build workflows to the repository.
Description check ✅ Passed The description matches the pull request title and is related to the changeset, though it is minimal and repeats the title without additional context.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (2)
.github/workflows/docker-build.yml (2)

52-57: Consider conditionalizing the login step for efficiency.

The login step runs unconditionally, but it's not needed for PRs since push is disabled. While not a security concern, adding a condition would avoid unnecessary authentication attempts on PR builds.

💡 Proposed improvement
             - name: Log in to Container Registry
+              if: github.event_name != 'pull_request'
               uses: docker/login-action@v3
               with:
                   registry: ${{ env.REGISTRY }}
                   username: ${{ github.actor }}
                   password: ${{ secrets.GITHUB_TOKEN }}
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.github/workflows/docker-build.yml around lines 52 - 57, The "Log in to
Container Registry" step (uses: docker/login-action@v3) runs on every workflow
run but isn't needed for PRs; add a conditional to that step (e.g., set an if
condition such as github.event_name != 'pull_request' or github.event_name ==
'push') so the docker/login-action only executes for non-PR runs (pushs or
dispatches), preventing unnecessary authentication attempts.

74-84: Consider adding linux/arm64 platform support if targeting ARM-based systems.

The build configuration is correct using docker/build-push-action@v6 (current as of Feb 2026) with proper push conditions and GHA caching. If this image will run on ARM systems (e.g., Apple Silicon, ARM servers), add linux/arm64 to the platforms list for broader compatibility.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.github/workflows/docker-build.yml around lines 74 - 84, The Docker build
step (step name "Build and push Docker image", id "push" using
docker/build-push-action@v6) currently sets platforms: linux/amd64 only; update
the step's with: platforms value to include linux/arm64 (e.g.,
"linux/amd64,linux/arm64") so the action builds multi-arch images for ARM-based
systems and AMD64, keeping existing push, tags, labels, and cache settings
unchanged.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In @.github/workflows/docker-build.yml:
- Around line 52-57: The "Log in to Container Registry" step (uses:
docker/login-action@v3) runs on every workflow run but isn't needed for PRs; add
a conditional to that step (e.g., set an if condition such as github.event_name
!= 'pull_request' or github.event_name == 'push') so the docker/login-action
only executes for non-PR runs (pushs or dispatches), preventing unnecessary
authentication attempts.
- Around line 74-84: The Docker build step (step name "Build and push Docker
image", id "push" using docker/build-push-action@v6) currently sets platforms:
linux/amd64 only; update the step's with: platforms value to include linux/arm64
(e.g., "linux/amd64,linux/arm64") so the action builds multi-arch images for
ARM-based systems and AMD64, keeping existing push, tags, labels, and cache
settings unchanged.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 958da72 and 1f17273.

📒 Files selected for processing (1)
  • .github/workflows/docker-build.yml

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (2)
.github/workflows/docker-build.yml (2)

19-24: Consider adding the workflow file to the path filter for self-testing.

When this workflow file itself is modified in a PR, the workflow won't trigger since .github/workflows/docker-build.yml isn't in the paths filter. Adding it would allow validating workflow syntax changes in PRs.

💡 Suggested change
     pull_request:
         branches: [main]
         paths:
             - Dockerfile
             - requirements.txt
             - "**.py"
+            - ".github/workflows/docker-build.yml"
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.github/workflows/docker-build.yml around lines 19 - 24, Update the
pull_request paths filter so the workflow triggers when its own file changes:
inside the pull_request block update the paths array (the current paths list
under pull_request) to include ".github/workflows/docker-build.yml" in addition
to "Dockerfile", "requirements.txt", and "**.py" so edits to the workflow file
itself will run the workflow for PR validation.

71-71: Consider adding a prefix to the SHA tag for clarity.

The SHA tag is generated without a prefix, resulting in tags like abc1234. Adding a sha- prefix (e.g., sha-abc1234) would make it clearer that this is a commit reference rather than a version number.

💡 Suggested change
-                      type=sha,prefix=,suffix=,format=short
+                      type=sha,prefix=sha-,suffix=,format=short
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.github/workflows/docker-build.yml at line 71, Update the tag generation
line that currently reads "type=sha,prefix=,suffix=,format=short" to include a
meaningful prefix so SHA tags become "sha-<sha>"; specifically change the prefix
value to "sha-" (i.e., "type=sha,prefix=sha-,suffix=,format=short") so that the
generated tag clearly indicates a commit SHA.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In @.github/workflows/docker-build.yml:
- Around line 19-24: Update the pull_request paths filter so the workflow
triggers when its own file changes: inside the pull_request block update the
paths array (the current paths list under pull_request) to include
".github/workflows/docker-build.yml" in addition to "Dockerfile",
"requirements.txt", and "**.py" so edits to the workflow file itself will run
the workflow for PR validation.
- Line 71: Update the tag generation line that currently reads
"type=sha,prefix=,suffix=,format=short" to include a meaningful prefix so SHA
tags become "sha-<sha>"; specifically change the prefix value to "sha-" (i.e.,
"type=sha,prefix=sha-,suffix=,format=short") so that the generated tag clearly
indicates a commit SHA.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 1f17273 and 600e0c4.

📒 Files selected for processing (1)
  • .github/workflows/docker-build.yml

sakullla and others added 2 commits February 26, 2026 21:11
Add GitHub Actions workflow to build and push mcp-sse-server Docker
image to GHCR. Triggered on changes to mcp-sse-server/** directory.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🧹 Nitpick comments (1)
.github/workflows/docker-build-mcp-sse-server.yml (1)

49-92: Pin all GitHub Actions to commit SHAs instead of floating version tags.

Using floating tags (@v4, @v3, etc.) across all workflows allows upstream tag drift and increases supply-chain risk. Pin each action to a specific commit SHA for immutability and reproducibility. This applies to all five workflow files (backup.yml, ci.yml, docker-build-mcp-sse-server.yml, docker-build.yml, and release-please.yml).

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.github/workflows/docker-build-mcp-sse-server.yml around lines 49 - 92, The
workflow uses floating action tags (actions/checkout@v4,
docker/setup-buildx-action@v3, docker/login-action@v3,
docker/metadata-action@v5, docker/build-push-action@v6,
actions/attest-build-provenance@v2) which must be pinned to specific commit
SHAs; replace each uses: owner/action@tag entry with the corresponding
owner/action@<commit-sha> for the exact release you want to lock, verify the
SHAs from each action's GitHub repo, and apply the same SHA-pinning pattern
across the other workflows mentioned (backup.yml, ci.yml, docker-build.yml,
release-please.yml) to ensure immutability and reproducibility.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In @.github/workflows/docker-build-mcp-sse-server.yml:
- Around line 41-45: The workflow grants overly broad permissions under the
permissions block (packages: write, attestations: write, id-token: write) for
all events; change it so the PR/build job uses least privilege (e.g., keep
contents: read and remove packages/attestations/id-token writes) and create a
separate non-PR publish/attest job that runs on push/tags with elevated
permissions (add packages: write, attestations: write, id-token: write) and
which contains the publish and attest steps referenced in the workflow; update
job triggers so publish/attest only run on non-pull_request events and ensure
the original build job retains only the minimal permissions it needs.
- Around line 16-21: The current workflow mixes push.tags and push.paths which
is ineffective because GitHub Actions ignores paths for tag events; update by
splitting tag-based triggers into a separate workflow (or remove push.tags
here): keep this workflow's push.block with branches and push.paths (remove
push.tags), and create a new workflow that uses push.tags: ["v*"] alone (or with
its own logic) so tag pushes run independently; reference the push.tags and
push.paths entries to locate and modify the trigger blocks and ensure the tag
workflow is scoped appropriately (or add conditional checks if you prefer a
single workflow).

---

Nitpick comments:
In @.github/workflows/docker-build-mcp-sse-server.yml:
- Around line 49-92: The workflow uses floating action tags
(actions/checkout@v4, docker/setup-buildx-action@v3, docker/login-action@v3,
docker/metadata-action@v5, docker/build-push-action@v6,
actions/attest-build-provenance@v2) which must be pinned to specific commit
SHAs; replace each uses: owner/action@tag entry with the corresponding
owner/action@<commit-sha> for the exact release you want to lock, verify the
SHAs from each action's GitHub repo, and apply the same SHA-pinning pattern
across the other workflows mentioned (backup.yml, ci.yml, docker-build.yml,
release-please.yml) to ensure immutability and reproducibility.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 9f0ccac and 6ae928a.

📒 Files selected for processing (1)
  • .github/workflows/docker-build-mcp-sse-server.yml

Comment thread .github/workflows/docker-build-mcp-sse-server.yml
Comment thread .github/workflows/docker-build-mcp-sse-server.yml
- Split push.tags into separate workflow (tags ignore paths filters)
- Separate build (PR) and publish (non-PR) jobs with least privilege
- Build job: contents:read only, no push
- Publish job: elevated permissions for GHCR push and attestation

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In @.github/workflows/docker-build-mcp-sse-server-tags.yml:
- Around line 9-14: The workflow can produce stale mutable tags when multiple
tag-triggered runs overlap; add a top-level concurrency block to serialize tag
publish runs by inserting concurrency: with a stable group name (e.g., group:
"docker-build-mcp-sse-server-tags") and cancel-in-progress: false so runs are
queued rather than racing; update the workflow named "Docker Build (MCP SSE
Server - Tags)" to include this concurrency stanza so the tag publish steps
cannot overlap and overwrite newer aliases.

In @.github/workflows/docker-build-mcp-sse-server.yml:
- Around line 13-26: Add GitHub Actions concurrency to the workflow named
"Docker Build (MCP SSE Server)" to serialize runs that could push mutable tags
(e.g., latest/branch) and cancel in-progress duplicates; specifically, add a
top-level concurrency block (e.g., concurrency: { group:
"docker-build-mcp-sse-server-${{ github.ref }}", cancel-in-progress: true }) so
runs for the same branch/ref are serialized and any older in-flight run is
cancelled to prevent out-of-order publishing.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 6ae928a and 3f959df.

📒 Files selected for processing (2)
  • .github/workflows/docker-build-mcp-sse-server-tags.yml
  • .github/workflows/docker-build-mcp-sse-server.yml

Comment thread .github/workflows/docker-build-mcp-sse-server-tags.yml Outdated
Comment thread .github/workflows/docker-build-mcp-sse-server.yml
sakullla and others added 3 commits February 26, 2026 23:17
- Tags workflow: serialize runs with cancel-in-progress: false to queue
- Branch/PR workflow: cancel in-progress runs for same ref to save resources

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>

@jack-arturo jack-arturo left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review: CI speed & trigger strategy

Thanks for putting this together @sakullla! The workflows are well-structured — good separation of concerns between the main app and mcp-sse-server, proper concurrency controls, and the build/publish split on the SSE workflow is solid.

A few changes to make this production-ready without burning excessive CI minutes:


1. Multi-arch builds are too slow for PRs and push-to-main

Building linux/amd64,linux/arm64 on GitHub's amd64 runners uses QEMU emulation for arm64. For a Python app with compiled dependencies, that's 20-40+ minutes per run. This should only happen when we're actually publishing an image (releases).

Proposed strategy:

Trigger Platforms Push? Rationale
v* tags (releases) linux/amd64,linux/arm64 Yes Published images need multi-arch
Push to main linux/amd64 only No Smoke test that image builds (~2 min)
PRs linux/amd64 only No Only validate Dockerfile changes
workflow_dispatch linux/amd64,linux/arm64 Yes Manual escape hatch

2. PR path filter **.py is too broad

**.py matches every Python file in the repo, meaning the Docker build workflow fires on virtually every PR. Since we already have CI tests (make test, make lint), Docker validation on PR is only needed when the container definition itself changes.

Suggested PR paths:

paths:
    - Dockerfile
    - requirements.txt
    - ".github/workflows/docker-build.yml"

3. Push to main should also have a path filter

Currently, push to main has no path filter — every merge triggers a Docker build. Since we publish images on tags (via release-please), the push-to-main build is just a smoke test and should only run when container-relevant files change.


Suggested docker-build.yml:

name: Docker Build

on:
    push:
        branches: [main]
        tags: ["v*"]
        paths:
            - Dockerfile
            - requirements.txt
            - ".github/workflows/docker-build.yml"
    pull_request:
        branches: [main]
        paths:
            - Dockerfile
            - requirements.txt
            - ".github/workflows/docker-build.yml"
    workflow_dispatch:
        inputs:
            tag:
                description: "Custom tag for the image (optional)"
                required: false
                default: ""

env:
    REGISTRY: ghcr.io
    IMAGE_NAME: ${{ github.repository }}

jobs:
    build:
        runs-on: ubuntu-latest
        permissions:
            contents: read
            packages: write
            attestations: write
            id-token: write

        steps:
            - name: Checkout repository
              uses: actions/checkout@v4

            - name: Set up Docker Buildx
              uses: docker/setup-buildx-action@v3

            - name: Log in to Container Registry
              if: github.event_name != 'pull_request'
              uses: docker/login-action@v3
              with:
                  registry: ${{ env.REGISTRY }}
                  username: ${{ github.actor }}
                  password: ${{ secrets.GITHUB_TOKEN }}

            - name: Extract metadata
              id: meta
              uses: docker/metadata-action@v5
              with:
                  images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
                  tags: |
                      type=ref,event=branch
                      type=ref,event=pr
                      type=semver,pattern={{version}}
                      type=semver,pattern={{major}}.{{minor}}
                      type=semver,pattern={{major}}
                      type=sha,prefix=sha-,suffix=,format=short
                      type=raw,value=latest,enable={{is_default_branch}}
                      type=raw,value=${{ inputs.tag }},enable=${{ inputs.tag != '' }}

            - name: Build and push Docker image
              id: push
              uses: docker/build-push-action@v6
              with:
                  context: .
                  push: ${{ github.event_name != 'pull_request' }}
                  tags: ${{ steps.meta.outputs.tags }}
                  labels: ${{ steps.meta.outputs.labels }}
                  cache-from: type=gha
                  cache-to: type=gha,mode=max
                  # Multi-arch only for releases and manual dispatch; amd64-only otherwise
                  platforms: ${{ (startsWith(github.ref, 'refs/tags/v') || github.event_name == 'workflow_dispatch') && 'linux/amd64,linux/arm64' || 'linux/amd64' }}

            - name: Generate artifact attestation
              if: github.event_name != 'pull_request'
              uses: actions/attest-build-provenance@v2
              with:
                  subject-name: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
                  subject-digest: ${{ steps.push.outputs.digest }}
                  push-to-registry: true

            - name: Print image digest
              if: github.event_name != 'pull_request'
              run: |
                  echo "Image pushed successfully!"
                  echo "Digest: ${{ steps.push.outputs.digest }}"
                  echo "Tags:"
                  echo "${{ steps.meta.outputs.tags }}"

Key changes:

  • Dynamic platforms: Multi-arch only on v* tags and workflow_dispatch; amd64-only for branch pushes and PRs
  • Path filter on push-to-main: Only triggers on Dockerfile/requirements.txt changes
  • PR path filter tightened: Removed **.py — Python changes don't need Docker validation

The same pattern should be applied to docker-build-mcp-sse-server.yml (dynamic platforms, and the build job should use amd64-only since it never pushes).

Happy to iterate on this!

@sakullla

sakullla commented Mar 6, 2026

Copy link
Copy Markdown
Contributor Author

Review: CI speed & trigger strategy

Thanks for putting this together @sakullla! The workflows are well-structured — good separation of concerns between the main app and mcp-sse-server, proper concurrency controls, and the build/publish split on the SSE workflow is solid.

A few changes to make this production-ready without burning excessive CI minutes:

1. Multi-arch builds are too slow for PRs and push-to-main

Building linux/amd64,linux/arm64 on GitHub's amd64 runners uses QEMU emulation for arm64. For a Python app with compiled dependencies, that's 20-40+ minutes per run. This should only happen when we're actually publishing an image (releases).

Proposed strategy:

Trigger Platforms Push? Rationale
v* tags (releases) linux/amd64,linux/arm64 Yes Published images need multi-arch
Push to main linux/amd64 only No Smoke test that image builds (~2 min)
PRs linux/amd64 only No Only validate Dockerfile changes
workflow_dispatch linux/amd64,linux/arm64 Yes Manual escape hatch

2. PR path filter **.py is too broad

**.py matches every Python file in the repo, meaning the Docker build workflow fires on virtually every PR. Since we already have CI tests (make test, make lint), Docker validation on PR is only needed when the container definition itself changes.

Suggested PR paths:

paths:
    - Dockerfile
    - requirements.txt
    - ".github/workflows/docker-build.yml"

3. Push to main should also have a path filter

Currently, push to main has no path filter — every merge triggers a Docker build. Since we publish images on tags (via release-please), the push-to-main build is just a smoke test and should only run when container-relevant files change.

Suggested docker-build.yml:

name: Docker Build

on:
    push:
        branches: [main]
        tags: ["v*"]
        paths:
            - Dockerfile
            - requirements.txt
            - ".github/workflows/docker-build.yml"
    pull_request:
        branches: [main]
        paths:
            - Dockerfile
            - requirements.txt
            - ".github/workflows/docker-build.yml"
    workflow_dispatch:
        inputs:
            tag:
                description: "Custom tag for the image (optional)"
                required: false
                default: ""

env:
    REGISTRY: ghcr.io
    IMAGE_NAME: ${{ github.repository }}

jobs:
    build:
        runs-on: ubuntu-latest
        permissions:
            contents: read
            packages: write
            attestations: write
            id-token: write

        steps:
            - name: Checkout repository
              uses: actions/checkout@v4

            - name: Set up Docker Buildx
              uses: docker/setup-buildx-action@v3

            - name: Log in to Container Registry
              if: github.event_name != 'pull_request'
              uses: docker/login-action@v3
              with:
                  registry: ${{ env.REGISTRY }}
                  username: ${{ github.actor }}
                  password: ${{ secrets.GITHUB_TOKEN }}

            - name: Extract metadata
              id: meta
              uses: docker/metadata-action@v5
              with:
                  images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
                  tags: |
                      type=ref,event=branch
                      type=ref,event=pr
                      type=semver,pattern={{version}}
                      type=semver,pattern={{major}}.{{minor}}
                      type=semver,pattern={{major}}
                      type=sha,prefix=sha-,suffix=,format=short
                      type=raw,value=latest,enable={{is_default_branch}}
                      type=raw,value=${{ inputs.tag }},enable=${{ inputs.tag != '' }}

            - name: Build and push Docker image
              id: push
              uses: docker/build-push-action@v6
              with:
                  context: .
                  push: ${{ github.event_name != 'pull_request' }}
                  tags: ${{ steps.meta.outputs.tags }}
                  labels: ${{ steps.meta.outputs.labels }}
                  cache-from: type=gha
                  cache-to: type=gha,mode=max
                  # Multi-arch only for releases and manual dispatch; amd64-only otherwise
                  platforms: ${{ (startsWith(github.ref, 'refs/tags/v') || github.event_name == 'workflow_dispatch') && 'linux/amd64,linux/arm64' || 'linux/amd64' }}

            - name: Generate artifact attestation
              if: github.event_name != 'pull_request'
              uses: actions/attest-build-provenance@v2
              with:
                  subject-name: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
                  subject-digest: ${{ steps.push.outputs.digest }}
                  push-to-registry: true

            - name: Print image digest
              if: github.event_name != 'pull_request'
              run: |
                  echo "Image pushed successfully!"
                  echo "Digest: ${{ steps.push.outputs.digest }}"
                  echo "Tags:"
                  echo "${{ steps.meta.outputs.tags }}"

Key changes:

  • Dynamic platforms: Multi-arch only on v* tags and workflow_dispatch; amd64-only for branch pushes and PRs
  • Path filter on push-to-main: Only triggers on Dockerfile/requirements.txt changes
  • PR path filter tightened: Removed **.py — Python changes don't need Docker validation

The same pattern should be applied to docker-build-mcp-sse-server.yml (dynamic platforms, and the build job should use amd64-only since it never pushes).

Happy to iterate on this!

Thanks for the detailed review — great points.

Implemented in:

What changed:

  1. Multi-arch strategy
  • v* tags + workflow_dispatch: linux/amd64,linux/arm64 and push enabled
  • push to main + PRs: linux/amd64 only, build validation only (no push)
  1. Trigger/path tightening
  • docker-build.yml now only triggers on:
    • Dockerfile
    • requirements.txt
    • .github/workflows/docker-build.yml
  • Removed broad **.py PR trigger
  • Added the same path restriction for push to main
  1. MCP SSE workflow alignment
  • docker-build-mcp-sse-server.yml is now aligned with the same strategy/pattern as docker-build.yml
  • Path filters narrowed to container-defining files + workflow file
  • Removed the separate tag-only workflow (docker-build-mcp-sse-server-tags.yml) after merging tag behavior into the main MCP SSE workflow

Please take another look when you have a moment — happy to adjust further.

@jack-arturo

Copy link
Copy Markdown
Member

Thanks @sakullla ! I made one tiny follow-up so package-lock.json changes also trigger the SSE Docker smoke-build. Everything else looks good, shipping shortly in the next release 🙌

@jack-arturo jack-arturo merged commit 39bf6e7 into verygoodplugins:main Mar 7, 2026
9 checks passed
jack-arturo added a commit that referenced this pull request Mar 7, 2026
🤖 I have created a release *beep* *boop*
---


##
[0.14.0](v0.13.0...v0.14.0)
(2026-03-07)


### Features

* **config:** add QDRANT_HOST + QDRANT_PORT as alternative to QDRANT_URL
([#112](#112))
([0871904](0871904))
* **docker:** Add Docker build workflow
([#98](#98))
([39bf6e7](39bf6e7))


### Bug Fixes

* **benchmarks:** handle possessive speaker names in LoCoMo
([#116](#116))
([abcbcca](abcbcca))
* **consolidation:** reduce decay rate, add importance floor, filter
archived memories
([#78](#78))
([#105](#105))
([3fce4ce](3fce4ce))
* handle smart apostrophes in recall entity extraction
([#115](#115))
([05b4daa](05b4daa))
* harden MCP bridge resilience, adopt stateless transport, and update
cross-client docs
([#114](#114))
([ec88da6](ec88da6))
* **qdrant:** prevent silent vector dimension mismatch, set Voyage as
recommended default
([#108](#108))
([5f88105](5f88105))

---
This PR was generated with [Release
Please](https://github.com/googleapis/release-please). See
[documentation](https://github.com/googleapis/release-please#release-please).
@sakullla

sakullla commented Mar 8, 2026

Copy link
Copy Markdown
Contributor Author

Thanks @sakullla ! I made one tiny follow-up so package-lock.json changes also trigger the SSE Docker smoke-build. Everything else looks good, shipping shortly in the next release 🙌

Hi,
I'm trying to deploy automem using the Helm chart, but I'm encountering an authentication error when pulling the container image from GitHub Container Registry:
failed to pull and unpack image "ghcr.io/verygoodplugins/automem:0.14.0":
failed to resolve reference "ghcr.io/verygoodplugins/automem:0.14.0":
failed to authorize: failed to fetch anonymous token:
unexpected status from GET request to https://ghcr.io/token?scope=repository%3Averygoodplugins%2Fautomem%3Apull&service=ghcr.io: 401 Unauthorized
Environment:

Kubernetes cluster attempting to pull the image

Image: ghcr.io/verygoodplugins/automem:0.14.0

Error: 401 Unauthorized when attempting anonymous pull
Questions:
1.
Is this container image intended to be private? If so, could you provide documentation on how to configure imagePullSecrets for authentication?
2.
If the image should be public, could you please update the package visibility settings on GitHub to allow anonymous pulls?
Workaround I'm considering: Creating a GitHub Personal Access Token with read:packages permission and configuring it as an imagePullSecret in Kubernetes, but I wanted to confirm if this is the intended approach or if the image should be publicly accessible.
Thanks for your help!

@jack-arturo

Copy link
Copy Markdown
Member

Oops sorry @sakullla, the package was set to private by default -- just flipped it to public.

ghcr.io/verygoodplugins/automem:0.14.0 should pull without auth now. Let me know if you hit anything else.

@sakullla

Copy link
Copy Markdown
Contributor Author

Oops sorry @sakullla, the package was set to private by default -- just flipped it to public.

ghcr.io/verygoodplugins/automem:0.14.0 should pull without auth now. Let me know if you hit anything else.

This also doesn’t work on my side.
I’m getting the following error when trying to pull the image:

Back-off pulling image "ghcr.io/verygoodplugins/automem/mcp-sse-server:0.14.0": ErrImagePull: failed to pull and unpack image "ghcr.io/verygoodplugins/automem/mcp-sse-server:0.14.0": failed to resolve reference "ghcr.io/verygoodplugins/automem/mcp-sse-server:0.14.0": failed to authorize: failed to fetch anonymous token: unexpected status from GET request to https://ghcr.io/token?scope=repository%3Averygoodplugins%2Fautomem%2Fmcp-sse-server%3Apull&service=ghcr.io: 401 Unauthorized
It looks like the GHCR image may not be publicly accessible, or there may be a permissions issue with the package. Could you please check?

@jack-arturo

Copy link
Copy Markdown
Member

Ok @sakullla sorry for the delay I got tripped up in blocker-hell trying to align docker, railway, github, and the new docs site. I think they're all in sync now.

docker pull ghcr.io/verygoodplugins/automem:0.15.2
docker pull ghcr.io/verygoodplugins/automem/mcp-sse-server:0.15.2

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants