Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Image publishing to DockerHub is misconfigured #3917

Closed
3 of 5 tasks
polarathene opened this issue Jan 5, 2025 · 7 comments
Closed
3 of 5 tasks

Image publishing to DockerHub is misconfigured #3917

polarathene opened this issue Jan 5, 2025 · 7 comments
Labels
bug Something is not working.

Comments

@polarathene
Copy link
Contributor

polarathene commented Jan 5, 2025

Preflight checklist

Ory Network Project

No response

Describe the bug

Presently (probably since the introduction of GoReleaser for this task?) the DockerHub image registry has:

  • Redundant single platform tags still published (GoReleaser was introduced for multi-platform image publishing back in early 2022) despite publishing a multi-platform image.
  • Images of a couple hundred bytes in size with SHA256 digest sigs published as tag names (redundant noise that shouldn't be there?).

Originally reported here: #3914 (comment)

image

image

It would be ideal if that was cleaned up, or at least a fix to prevent publishing this tags in future releases.

Reproducing the bug

Visit DockerHub for oryd/hydra

Relevant log output

No response

Relevant configuration

No response

Version

2.2.0

On which operating system are you observing this issue?

None

In which environment are you deploying?

None

Additional Context

As a potential solution that is known to work without the undesirable tags being pushed, see the original report for advice on publishing the image via Github Actions.

Additional improvements:

  • The Hydra + Docker install docs reference oryd/hydra, but could also provide a link to the page as a minor convenience to the reader. Likewise on this repo README ("Get Started" and "Develop" sections for Docker, or more commonly via another badge at the top of the README)
  • The DockerHub README directs the user to Hydra docs.
    • It provides no additional context on the image usage (nor about rootless info which is relevant for volume bind mounts) or on the variant tags available. It should note images are published with each semver variant are Alpine based, while an additional -distroless suffix in the tag provides an image variant using Google's Distroless (Minimal Debian base image without a package manager).
    • Linking to the Quickstart guide could also be helpful since it's oriented around using the image.
@polarathene polarathene added the bug Something is not working. label Jan 5, 2025
@aeneasr
Copy link
Member

aeneasr commented Jan 7, 2025

Thank you for the report, setting up gorelease can be immensely painful and frustrating so I'm happy it works at all at the moment 😓

You can find the base config here: https://github.com/ory/xgoreleaser/blob/master/build.tmpl.yml

@polarathene
Copy link
Contributor Author

In 2025 do you still think it's worth publishing ARM v7 and v6 binaries for releases? In a project I maintain (15k stars mail-server dockerized service), we dropped ARM v7 support back in Dec 2022. There was a few users still interested IIRC, but no major complaints declaring the platform legacy and for those users to build the project themselves or spend say $50 to replace that hardware.

Might be worth considering for Ory to take the same stance going forward? Usually I see projects on Github publish for a wide variety of platforms on GH Releases just because the build platform / CI can support it, rather than actual demand for the more esoteric platforms published.


You should be able to drop the entire dockers config from there shaving almost 200 lines away.

The image labels assigned could be part of your Dockerfile, or centralized via Github Actions in a single step.

It's up to you if you want to keep building Hydra via GoReleaser and copy the binary during the image build, otherwise the Docker images build + publish could be managed entirely separately if that's simpler to grok and maintain.

I am not familiar with CoSign and your usage with it for Docker, but I assume that's related to the random digest .sig image tags being accidentally published to the image registry?


This would need some tweaking, and I've not accounted for the -distroless variant yet, but that could be handled via a separate input, or introducing some extra steps/jobs in the 2nd workflow that gets called.

It's split into two to keep the trigger workflow for your repo small and simple, with the dynamic inputs clearly visible under the with parameters (these become inputs when referenced in the 2nd workflow). It'd need a bit of adjustment but would allow for the 2nd workflow to be centralized at it's own repo if your other Ory projects were to share it like you do with GoReleaser 👍

name: 'Build and Publish Docker Images'

on:
  workflow_dispatch:
  push:
    branches:
      - master
    # Optional: Only trigger this workflow if the push event
    # involves files matching these path patterns:
    paths:
      - src/**
      - .dockerignore
      - Dockerfile
    # Release tags as an alternative trigger to branch push,
    # For example, when creating a GH Release which adds a tag:
    tags:
      - 'v*.*.*'

permissions:
  contents: read
  packages: write

jobs:
  docker:
    name: 'Deploy Docker Images'
    uses: ory/hydra/.github/workflows/generic_publish.yml@master
    with:
      project-name: hydra
      revision: ${{ github.sha }}
      source: https://github.com/${{ github.repository }}
      version: ${{ github.ref_type == 'tag' && github.ref_name || 'edge' }}
    secrets: inherit
name: 'Build and Publish the Docker Image'

on:
  workflow_call:
    inputs:
      image-variant:
        required: false
        type: string
      project-name:
        required: true
        type: string
      revision:
        required: true
        type: string
      source:
        required: true
        type: string
      version:
        required: true
        type: string

permissions:
  contents: read
  packages: write

jobs:
  publish-images:
    name: 'Build and Publish'
    runs-on: ubuntu-latest
    steps:
      - name: "Get current timestamp (ISO 8601)"
        id: build-info
        run: echo "date=$(date --utc --iso-8601=seconds)" >> "${GITHUB_OUTPUT}"

      - name: 'Checkout'
        uses: actions/checkout@v4

      # This step will support building non-native platform archs via emulation (slow)
      # Skip this when you can compile for that platform natively, or cross-compile (Zig, Go)
      - name: 'Set up QEMU'
        uses: docker/setup-qemu-action@v3
        with:
          platforms: arm64

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

      # The metadata action appends labels and sets the image names + tags to publish.
      # Tags for the image to be published, based on the following rules:
      # https://github.com/docker/metadata-action?tab=readme-ov-file#typeedge
      # https://github.com/docker/metadata-action?tab=readme-ov-file#typesemver
      # Updates to master branch will publish an image with the `:edge` tag (useful between official releases)
      # Pushing a git tag will publish an image with all 3 semver tags
      #
      # NOTE: Publishing the semver tags like this is useful for software that monitors an image
      # for updates only by a digest change to the image tag at the registry, like WatchTower does:
      # https://github.com/containrrr/watchtower/issues/1802
      #
      # NOTE: By default the `:latest` image tag will be updated for the `semver` type below,
      # you may want to have more control over that if your release policy could publish a patch
      # release to an older major/minor release (as this would unintentionally update the latest tag too):
      # https://github.com/docker/metadata-action?tab=readme-ov-file#latest-tag
      - name: 'Prepare tags'
        id: docker-metadata
        uses: docker/metadata-action@v5
        with:
          images: |
            docker.io/oryd/${{ inputs.project-name }}
            ghcr.io/ory/${{ inputs.project-name }}
          tags: |
            type=edge,branch=master
            type=semver,pattern=v{{major}}
            type=semver,pattern=v{{major}}.{{minor}}
            type=semver,pattern=v{{major}}.{{minor}}.{{patch}}
          labels: |
            org.opencontainers.image.created=${{ steps.build-info.outputs.date }}
            org.opencontainers.image.title=${{ inputs.project-name }}
            org.opencontainers.image.revision=${{ inputs.revision }}
            org.opencontainers.image.source=${{ inputs.source }}
            org.opencontainers.image.version=${{ inputs.version }}
            org.opencontainers.image.vendor=Ory
            org.opencontainers.image.url=https://www.ory.sh
            org.opencontainers.image.documentation=https://www.ory.sh/docs


      # Publish to image registries (DockerHub and GHCR):
      - name: 'Login to DockerHub'
        uses: docker/login-action@v3
        with:
          registry: docker.io
          username: ${{ secrets.DOCKER_USERNAME }}
          password: ${{ secrets.DOCKER_PASSWORD }}
      - name: 'Login to GitHub Container Registry'
        uses: docker/login-action@v3
        with:
          registry: ghcr.io
          username: ${{ github.actor }}
          password: ${{ secrets.GITHUB_TOKEN }}


      # Build the image from a Dockerfile for the requested platforms,
      # then publish a multi-platform image at the registries with the tags and labels declared above
      - name: 'Build and publish images'
        uses: docker/build-push-action@v6
        with:
          context: .
          # Customize any Dockerfile ARG values here:
          build-args: |
            BASE_IMAGE=${{ inputs.image-variant }}
          platforms: linux/amd64,linux/arm64
          push: true
          labels: ${{ steps.docker-metadata.outputs.labels }}
          tags: ${{ steps.docker-metadata.outputs.tags }}
          # Disable provenance attestation: https://docs.docker.com/build/attestations/slsa-provenance/
          provenance: false

NOTE:

  • You'll need to set DOCKER_USERNAME and DOCKER_PASSWORD in your repo secrets.
  • The build-info step to get the build date for the image.created label could probably be replaced by the metadata-action support for formatting a date in a similar way.
  • To support the -distroless suffix, you could probably append ,suffix= to each tag variant, with a conditional on if image-variant input was defined, I've not looked into that atm (nor the last step build-push-action with build-arg specifying BASE_IMAGE with an empty default). These refer to my Dockerfile proposal which could self-contain the Go builder stage with the Alpine + Distroless variants both supported.

@aeneasr
Copy link
Member

aeneasr commented Jan 10, 2025

I've configured gorelease to no longer publish the individual architecture variants but instead only docker multiplatform images. The sha things you're mentioning are part of SBOM and the official way to sign artifacts in Docker. I don't think there's anything I can do here!

I'm closing this as resolved with ory/xgoreleaser@2f7806d

@aeneasr aeneasr closed this as completed Jan 10, 2025
@polarathene
Copy link
Contributor Author

The sha things you're mentioning are part of SBOM and the official way to sign artifacts in Docker. I don't think there's anything I can do here!

I don't think they're meant to be published to the registry as tags though? I've not seen that anywhere else.

@aeneasr
Copy link
Member

aeneasr commented Jan 10, 2025

https://hub.docker.com/layers/goreleaser/goreleaser/sha256-c5666f6691ae48881b0fc8417a8d35a08346283c217089df2f292ea4f80ff040.sig/images/sha256-b60747920eb9987e9130c34b2771fcbbc8aaed29bb67ffeb6f9e2859f4be680d

If you disagree please open an issue with goreleaser, but it's an official feature.

@polarathene
Copy link
Contributor Author

Yeah alright, seems like registries need to implement support for that to hide such artifacts/tags published when showing the actual image tags: docker/roadmap#269 (comment) (not much activity on that issue, rather stale)

I don't have the time atm to get clued up on this properly, but it seems like since that 2022 cosign specific approach, an official OCI spec has since been standardized, and there is also OCI artifacts (which is what should have been used for this on DockerHub but at the time DockerHub did not have OCI artifact support, which it gained late 2022)

Apparently SBOM attachments are now deprecated and one should favor SBOM attestations, but compatibility/adoption of that may be in a similar situation to the issues cosign had taken years ago with earlier approaches 🤷‍♂️

So sure GoReleaser implemented support for such a feature, but I assume that was some time ago and just because it exists and can be used today does not necessarily mean it's not outdated/deprecated for it's intended use 😅

Up to you if you choose to continue using it, I assume you're more familiar with it's relevance and value to users that are interested in it, and that it is providing those users with the intended value despite the industry having presumably moved on to a different approach? 🤔

@aeneasr
Copy link
Member

aeneasr commented Jan 11, 2025

Appreciate the thoughtful response, thank you very much!

Fir now we‘ll just go with what goreleaser supports because it’s the pipeline we settled on. The project is very active and I‘m confident they‘ll update their features once it makes sense :)

ps: I fixed up all of the docker images and improved the quickstart and HSM stuff

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something is not working.
Projects
None yet
Development

No branches or pull requests

2 participants