Kai Ole Hartwig
yasrt · Dokumentation

CI-Pipelines

Jedes Release liefert yasrt-linux-{amd64,arm64} und yasrt-darwin-{arm64,amd64} mit SHA256SUMS und einer detached cosign-Signatur darüber. Die Binaries werden einmal in meiner Pipeline gebaut und signiert; auf GitHub liegen dieselben Dateien, dort wird nichts neu gebaut.

  • Binary:go install github.com/ohartwig/yasrt/cmd/yasrt@latest oder die signierten Releases
  • Image:registry.ole-hartwig.eu/devops/images/yasrt:1 trägt das Binary mit git, gpg und ssh-keygen
  • Prüfen:cosign verify-blob --key <public-key> --signature SHA256SUMS.sig --insecure-ignore-tlog=true SHA256SUMS, dann sha256sum -c SHA256SUMS

GitLab CI

stages: [version, build, release]

default:
  image:
    name: registry.ole-hartwig.eu/devops/images/yasrt:1
    entrypoint: [""]

version:
  stage: version
  variables: { GIT_DEPTH: 0 }          # yasrt braucht die ganze Historie
  script: yasrt next --output .release.env
  artifacts:
    reports: { dotenv: .release.env }
  rules: [{ if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH }]

build:
  stage: build
  image: dein/build-image
  script:
    - '[ "$RELEASE_STATUS" = "release" ] || exit 0'   # im Script gaten, nicht in rules:
    - make build VERSION=$RELEASE_VERSION
  rules: [{ if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH }]

release:
  stage: release
  variables: { GIT_DEPTH: 0 }
  script: yasrt release
  rules: [{ if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH }]

 

GitLab wertet rules: aus, wenn die Pipeline entsteht, bevor .release.env existiert. Downstream-Jobs gaten deshalb im Script auf RELEASE_STATUS. Das Projekt muss Job-Token-Pushes erlauben (Settings → CI/CD → Job token permissions → Allow Git push requests to the repository), und wer auf den Default-Branch mergen darf, muss den Release-Tag anlegen dürfen; yasrt check prüft beides. Ein Push mit dem Job-Token startet keine Pipeline, und genau das verhindert, dass der Release-Commit sich selbst noch einmal released.

Ein Repository, dessen Veröffentlichung auf dem Tag laufen muss (etwa weil das OIDC-Vertrauen einer Signierrolle auf ref_type:tag begrenzt ist), behält diese Pipeline, indem das Release sie startet: after_release.triggers expandiert ${tag}, ${version} und CI-Variablen in project, ref und variables; { project: "${CI_PROJECT_PATH}", ref: "${tag}" } startet die Tag-Pipeline, die der Job-Token-Push nicht gestartet hat.

Ein Trigger geht mit dem Job-Token raus, es sei denn, der Eintrag nennt mit token_var eine Variable mit einem Pipeline-Trigger-Token des Zielprojekts. Der Unterschied ist, als wer die gestartete Pipeline läuft: mit dem Job-Token als der Nutzer hinter dem Release-Job, der im Zielprojekt Pipelines starten dürfen muss; mit einem Trigger-Token als dessen Besitzer, egal wer gemerged hat.

Eine CI/CD-Komponente mit dieser Form (version, release, eine geteilte Defaults-Schicht, product und tag-format als Inputs) liegt auf meiner Instanz unter devops/ci-cd-components/release-tools.

GitHub Actions und Forgejo Actions

permissions: { contents: write }
jobs:
  release:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
        with: { fetch-depth: 0 }
      - run: yasrt next --output .release.env
      - run: make build                    # gatet innen auf RELEASE_STATUS
      - run: yasrt release
        env: { GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} }   # FORGEJO_TOKEN auf Forgejo

 

Ein Push mit GITHUB_TOKEN startet keinen Workflow, der Changelog-Commit released sich also nicht selbst. Wo die Plattform an ihren Variablen nicht zu erkennen ist, sag --forge gitlab|github|forgejo oder setz YASRT_FORGE. Vollständige Dateien liegen unter docs/examples im Repository.

Weiter

Zurück zu yasrt

Die Übersicht: Problem, Fit-Check, drei Kommandos, alle Kapitel.

yasrt →
Zurück zu yasrt

Konfiguration und Hooks

Eine Zeile pro Repository, Organisationsdefaults darunter, Hooks an fünf Punkten des Releases.

Lesen →
Konfiguration und Hooks