@ifc-lite/drawing-2d@3.1.1 #1341
Workflow file for this run
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| # This Source Code Form is subject to the terms of the Mozilla Public | |
| # License, v. 2.0. If a copy of the MPL was not distributed with this | |
| # file, You can obtain one at https://mozilla.org/MPL/2.0/. | |
| name: Docker Image | |
| on: | |
| release: | |
| types: | |
| - published | |
| push: | |
| branches: | |
| - main | |
| paths: | |
| - '.github/workflows/docker.yml' | |
| - '.cargo/**' | |
| - 'Cargo.lock' | |
| - 'Cargo.toml' | |
| - 'apps/server/**' | |
| - 'rust/**' | |
| # Build the image BEFORE merge when the Dockerfile itself changes. The push | |
| # lane above only reports once a change has already landed on main, which is | |
| # how #2008 reached review fully green — a python 3.12 -> 3.14 base bump | |
| # whose requirements.lock could not resolve on the new interpreter (numpy / | |
| # shapely ship cp-tagged wheels), invisible because no PR ever built a | |
| # Dockerfile. | |
| # | |
| # Deliberately much narrower than the push paths. Over the last 6 months the | |
| # push paths matched 447 commits and the Dockerfile alone matched ~6, so | |
| # scoping to the Dockerfile is the difference between a Depot build on most | |
| # PRs and roughly one a month. Source changes are already covered by | |
| # test.yml's "Validate Server Binary" jobs plus the post-merge build here; | |
| # the only unique signal this lane adds is "does the image still build". | |
| # | |
| # This workflow's own path is NOT listed: it would fire a full ~9 min image | |
| # build on every dependabot actions-SHA bump (10 of the 31 commits that | |
| # touched either file) for no build-relevant change. Use workflow_dispatch | |
| # to exercise an edit to this file. | |
| pull_request: | |
| paths: | |
| - 'apps/server/Dockerfile' | |
| workflow_dispatch: | |
| concurrency: | |
| group: ${{ github.workflow }}-${{ github.ref }} | |
| # A newer push to main supersedes an in-flight image build — cancel the older | |
| # run rather than queueing behind it, so a slow/hung build can't jam the | |
| # queue (as happened when #874's large Rust diff cache-busted the build and a | |
| # later commit's run sat pending behind it). | |
| cancel-in-progress: true | |
| permissions: | |
| contents: read | |
| env: | |
| REGISTRY: ghcr.io | |
| IMAGE_NAME: ${{ github.repository_owner }}/ifc-lite-server | |
| jobs: | |
| docker: | |
| name: Build & Push Docker Image | |
| runs-on: depot-ubuntu-24.04-4 | |
| # Cap a stuck "Build and push" so it can't run to GitHub's 6h default. | |
| # A *cold* build — cargo-chef cooking the whole workspace after a | |
| # deps-cache miss — is the long pole, and a cold build that gets cancelled | |
| # never warms the registry cache, so the cap must let one complete. 120 | |
| # covers a cold build; warm builds finish in minutes. | |
| timeout-minutes: 120 | |
| permissions: | |
| contents: read | |
| packages: write | |
| steps: | |
| - name: Checkout Repo | |
| uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 | |
| with: | |
| lfs: false | |
| persist-credentials: false | |
| # QEMU is only needed to emulate the non-native arm64 build, which we | |
| # now only do on `release: published` (see the `platforms` expression | |
| # below). Skipping it on main pushes shaves setup time off the frequent | |
| # amd64-only builds. | |
| - name: Set up QEMU | |
| if: github.event_name == 'release' | |
| uses: docker/setup-qemu-action@96fe6ef7f33517b61c61be40b68a1882f3264fb8 # v4.2.0 | |
| - name: Set up Docker Buildx | |
| uses: docker/setup-buildx-action@37fe631027851001ddb9b187196cc803df7f5f0e # v4.3.0 | |
| - name: Log in to GitHub Container Registry | |
| uses: docker/login-action@dbcb813823bdd20940b903addbd779551569679f # v4.6.0 | |
| with: | |
| registry: ${{ env.REGISTRY }} | |
| username: ${{ github.actor }} | |
| password: ${{ secrets.GITHUB_TOKEN }} | |
| - name: Extract metadata (tags, labels) | |
| id: meta | |
| uses: docker/metadata-action@dc802804100637a589fabce1cb79ff13a1411302 # v6.2.0 | |
| with: | |
| images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }} | |
| tags: | | |
| # tag release as version (e.g. 0.5.0) | |
| type=match,pattern=v(.*),group=1,event=tag | |
| # tag release also as latest | |
| type=raw,value=latest,enable={{is_default_branch}} | |
| type=raw,value=latest,event=tag | |
| # sha for push-to-main builds | |
| type=sha,prefix=,event=branch | |
| # pr-123 for the build-only PR lane. Never pushed (see `push:` | |
| # below); it just keeps the tag list non-empty so buildx has | |
| # something to name the image. | |
| type=ref,event=pr | |
| # The registry cache exporter requires a fully lowercase repository name | |
| # (OCI spec), but ${{ github.repository_owner }} preserves case | |
| # (`LTplus-AG`). The image *tags* are fine because docker/metadata-action | |
| # lowercases them; the raw cache ref below is not, so lowercase it here. | |
| - name: Compute lowercase cache ref | |
| run: echo "CACHE_IMAGE=${REGISTRY}/$(echo "$IMAGE_NAME" | tr '[:upper:]' '[:lower:]')" >> "$GITHUB_ENV" | |
| - name: Build and push | |
| uses: docker/build-push-action@53b7df96c91f9c12dcc8a07bcb9ccacbed38856a # v7.3.0 | |
| with: | |
| context: . | |
| file: apps/server/Dockerfile | |
| push: ${{ github.event_name != 'pull_request' }} | |
| tags: ${{ steps.meta.outputs.tags }} | |
| labels: | | |
| ${{ steps.meta.outputs.labels }} | |
| org.opencontainers.image.source=${{ github.server_url }}/${{ github.repository }} | |
| # Cache lives in GHCR (a `:buildcache` tag on the same package), NOT | |
| # in the GitHub Actions cache. On a Depot runner `type=gha` is | |
| # intercepted by Depot's cache backend and billed per-GB — with | |
| # mode=max writing the multi-GB cargo-chef layer set on ~1/3 of main | |
| # pushes, that was the single largest contributor to Depot's uncapped | |
| # cache bill. `type=registry` writes straight to GHCR instead, which | |
| # is free + unlimited for public packages, so the cache cost drops to | |
| # $0 while warm builds stay fast. Trade: pushing the cache to GHCR | |
| # adds ~1-3 min of network per build vs Depot's local cache. | |
| cache-from: type=registry,ref=${{ env.CACHE_IMAGE }}:buildcache | |
| # mode=max keeps the cargo-chef "cooked deps" stage in the cache — | |
| # that layer is what makes warm builds finish in minutes instead of | |
| # recompiling the whole workspace, so dropping to mode=min would | |
| # *raise* compute minutes. image-manifest+oci-mediatypes make the | |
| # cache blob a GHCR-compatible OCI manifest (required for the registry | |
| # backend to push to ghcr.io). | |
| # | |
| # Empty on pull_request: a PR from a fork — and every Dependabot PR — | |
| # runs with a read-only GITHUB_TOKEN, so exporting the cache would | |
| # fail and take the build down with it, on exactly the PRs this lane | |
| # exists to catch. PRs read the cache and never write it; main keeps | |
| # it warm. | |
| # | |
| # The condition is written "not pull_request && <value> || ''" and | |
| # not the other way round on purpose: Actions has no ternary, and in | |
| # `a && b || c` an empty-string b is FALSY, so putting '' in the b | |
| # slot silently falls through to c and the cache export runs anyway. | |
| cache-to: ${{ github.event_name != 'pull_request' && format('type=registry,ref={0}:buildcache,mode=max,image-manifest=true,oci-mediatypes=true', env.CACHE_IMAGE) || '' }} | |
| # Build arm64 only for actual releases (distribution images). On the | |
| # frequent push-to-main builds (~1/3 of commits touch rust/** and | |
| # trigger this workflow) we build amd64 only — the arm64 leg runs | |
| # under slow QEMU emulation and roughly doubled build time (and, when | |
| # the cache was on Depot, the cache bill too). The `latest`/sha main | |
| # images stay amd64; multi-arch manifests ship on release. | |
| platforms: ${{ github.event_name == 'release' && 'linux/amd64,linux/arm64' || 'linux/amd64' }} |