Repository navigation
feat(release): publish signed archives for Linux, macOS and Windows with install scripts #4
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
Merged
Merged
Changes from all commits
Commits
Show all changes
9 commits
Select commit
Hold shift + click to select a range
58c9f3d
feat(release): publish signed archives for Linux, macOS and Windows w…
devin-ai-integration[bot] 47f444a
fix(release): write the archives from Go and keep LF on Windows check…
devin-ai-integration[bot] b91326b
test(install): read the fake server's port as a line, not a character
devin-ai-integration[bot] 55f5bd6
fix(release): write SHA256SUMS.txt in text mode on every host
devin-ai-integration[bot] 40efe24
test(install): exit 0 from install-test.ps1 after a clean run
devin-ai-integration[bot] 8b2cab9
Merge remote-tracking branch 'origin/develop' into feat/release-line
devin-ai-integration[bot] 40a31e8
ci: gate the release on Windows with hg and svn, as CI does
devin-ai-integration[bot] be7646b
fix(release): read the identity regexp before entering dist; sign pre…
devin-ai-integration[bot] fb2c6d8
test(install): expect install.sh's own wording when cosign is absent
devin-ai-integration[bot] File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
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 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
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,61 +1,185 @@ | ||
| name: Release | ||
|
|
||
| # A maintainer tags vX.Y.Z on main (CONTRIBUTING.md § Releases). The tag publishes nothing | ||
| # until the repository gate is green on every platform the release is built for; then the | ||
| # archives are built, their checksum manifest signed with cosign (keyless, the identity being | ||
| # this workflow on the tag), and the GitHub release created with the CHANGELOG.md section | ||
| # of the version as its notes. The installers are then run against the published release. | ||
|
|
||
| on: | ||
| push: | ||
| tags: ["v*"] | ||
|
|
||
| permissions: | ||
| contents: write | ||
| contents: read | ||
|
|
||
| env: | ||
| SYSPI_REQUIRE_VCS: "1" | ||
|
|
||
| jobs: | ||
| build: | ||
| name: Build ${{ matrix.goos }}/${{ matrix.goarch }} | ||
| runs-on: ubuntu-latest | ||
| gate: | ||
| name: Go gate (${{ matrix.os }}) | ||
| strategy: | ||
| fail-fast: false | ||
| matrix: | ||
| goos: [linux, darwin, windows] | ||
| goarch: [amd64, arm64] | ||
| os: [ubuntu-latest, macos-latest, windows-latest] | ||
| runs-on: ${{ matrix.os }} | ||
| timeout-minutes: 20 | ||
| defaults: | ||
| run: | ||
| shell: bash | ||
| steps: | ||
| - uses: actions/checkout@v4 | ||
| - uses: actions/setup-go@v5 | ||
| - uses: actions/checkout@08c6903cd8c0fde910a37f88322edcfb5dd907a8 # v5.0.0 | ||
| - uses: actions/setup-go@44694675825211faa026b3c33043df3e48a5fa00 # v6.0.0 | ||
| with: | ||
| go-version-file: go.mod | ||
| - name: Install mercurial and subversion (Linux) | ||
| if: runner.os == 'Linux' | ||
| run: sudo apt-get update -q && sudo apt-get install -y -q mercurial subversion | ||
| - name: Install mercurial and subversion (macOS) | ||
| if: runner.os == 'macOS' | ||
| run: brew install mercurial subversion | ||
| - name: Install mercurial and subversion (Windows) | ||
| if: runner.os == 'Windows' | ||
| shell: pwsh | ||
| run: | | ||
| choco install -y --no-progress hg sliksvn | ||
| Add-Content $env:GITHUB_PATH 'C:\Program Files\Mercurial' | ||
| Add-Content $env:GITHUB_PATH 'C:\Program Files\SlikSvn\bin' | ||
| - name: Versions | ||
| run: go version && git --version && hg --version | head -1 && svn --version --quiet | ||
| - name: Build | ||
| env: | ||
| GOOS: ${{ matrix.goos }} | ||
| GOARCH: ${{ matrix.goarch }} | ||
| CGO_ENABLED: "0" | ||
| run: | | ||
| ext="" | ||
| [ "$GOOS" = windows ] && ext=".exe" | ||
| name="syspi_${GITHUB_REF_NAME}_${GOOS}_${GOARCH}" | ||
| mkdir -p dist | ||
| go build -trimpath -ldflags "-s -w -X main.Version=${GITHUB_REF_NAME}" -o "dist/${name}${ext}" ./cmd/syspi | ||
| - uses: actions/upload-artifact@v4 | ||
| with: | ||
| name: syspi-${{ matrix.goos }}-${{ matrix.goarch }} | ||
| path: dist/* | ||
| if-no-files-found: error | ||
| release: | ||
| name: Checksums and GitHub release | ||
| needs: build | ||
| run: go build ./... | ||
| - name: Vet | ||
| run: go vet ./... | ||
| - name: gofmt | ||
| run: test -z "$(gofmt -l .)" || { gofmt -l .; exit 1; } | ||
| - name: Tidy | ||
| run: go mod tidy && git diff --exit-code go.mod go.sum | ||
| - name: Unit and end-to-end tests | ||
| run: go test -count=1 ./... | ||
|
|
||
| publish: | ||
| name: Build, sign and publish | ||
| needs: gate | ||
| runs-on: ubuntu-latest | ||
| timeout-minutes: 30 | ||
| permissions: | ||
| contents: write # create the release and upload its assets | ||
| id-token: write # cosign keyless signing | ||
| steps: | ||
| - uses: actions/checkout@v4 | ||
| - uses: actions/download-artifact@v4 | ||
| - uses: actions/checkout@08c6903cd8c0fde910a37f88322edcfb5dd907a8 # v5.0.0 | ||
| - uses: actions/setup-go@44694675825211faa026b3c33043df3e48a5fa00 # v6.0.0 | ||
| with: | ||
| go-version-file: go.mod | ||
|
|
||
| - name: Check the tag names a version with a changelog section | ||
| env: | ||
| TAG: ${{ github.ref_name }} | ||
| run: | | ||
| [[ "$TAG" =~ ^v[0-9]+\.[0-9]+\.[0-9]+(-[0-9A-Za-z.-]+)?$ ]] || { echo "::error::tag $TAG is not vX.Y.Z"; exit 1; } | ||
| python3 scripts/changelog.py release-notes "${TAG#v}" > "$RUNNER_TEMP/notes.md" | ||
| echo "notes for $TAG:"; cat "$RUNNER_TEMP/notes.md" | ||
|
|
||
| - name: Build the release archives | ||
| env: | ||
| TAG: ${{ github.ref_name }} | ||
| run: scripts/build-release-artifacts.sh "$TAG" dist | ||
|
|
||
| - name: Check the checksum manifest | ||
| run: | | ||
| cd dist | ||
| repeated=$(awk '{ print $2 }' SHA256SUMS.txt | sort | uniq -d) | ||
| [[ -z "$repeated" ]] || { echo "::error::SHA256SUMS.txt lists more than once: $repeated"; exit 1; } | ||
| [[ $(wc -l < SHA256SUMS.txt) -eq 6 ]] || { echo "::error::SHA256SUMS.txt lists $(wc -l < SHA256SUMS.txt) assets, not 6"; exit 1; } | ||
| sha256sum --check --strict SHA256SUMS.txt | ||
|
|
||
| - name: Install cosign | ||
| uses: sigstore/cosign-installer@6f9f17788090df1f26f669e9d70d6ae9567deba6 # v4.1.2 | ||
| with: | ||
| path: dist | ||
| merge-multiple: true | ||
| - name: Check the tag equals the version it carries | ||
| run: | | ||
| case "$GITHUB_REF_NAME" in | ||
| v[0-9]*.[0-9]*.[0-9]*) ;; | ||
| *) echo "tag $GITHUB_REF_NAME is not v<semver>"; exit 1 ;; | ||
| esac | ||
| - name: SHA-256 checksums | ||
| working-directory: dist | ||
| run: sha256sum syspi_* > SHA256SUMS && cat SHA256SUMS | ||
| - name: Create the release | ||
| cosign-release: v3.0.3 | ||
|
|
||
| - name: Sign the checksum manifest with cosign keyless | ||
| run: | | ||
| cd dist | ||
| cosign sign-blob SHA256SUMS.txt \ | ||
| --bundle SHA256SUMS.txt.bundle \ | ||
| --use-signing-config=false \ | ||
| --yes | ||
|
|
||
| - name: Verify the signature against the identity install.sh checks | ||
| env: | ||
| WORKFLOW_REF: ${{ github.workflow_ref }} | ||
| run: | | ||
| regexp=$(sed -n "s/^RELEASE_IDENTITY_REGEXP='\(.*\)'$/\1/p" install.sh) | ||
| [[ -n "$regexp" ]] || { echo "::error::RELEASE_IDENTITY_REGEXP not found in install.sh"; exit 1; } | ||
| cd dist | ||
| cosign verify-blob SHA256SUMS.txt \ | ||
| --bundle SHA256SUMS.txt.bundle \ | ||
| --certificate-oidc-issuer https://token.actions.githubusercontent.com \ | ||
| --certificate-identity "https://github.com/${WORKFLOW_REF}" | ||
| cosign verify-blob SHA256SUMS.txt \ | ||
| --bundle SHA256SUMS.txt.bundle \ | ||
| --certificate-oidc-issuer https://token.actions.githubusercontent.com \ | ||
| --certificate-identity-regexp "$regexp" | ||
|
|
||
| - name: Create the GitHub release | ||
| env: | ||
| GH_TOKEN: ${{ github.token }} | ||
| run: gh release create "$GITHUB_REF_NAME" dist/* --title "$GITHUB_REF_NAME" --generate-notes --verify-tag | ||
| TAG: ${{ github.ref_name }} | ||
| run: | | ||
| cat >> "$RUNNER_TEMP/notes.md" <<'NOTES' | ||
|
|
||
| --- | ||
|
|
||
| Install with the scripts in the repository (`install.sh`, `install.ps1`; see the | ||
| README) or download an archive and check it against `SHA256SUMS.txt`, which is signed | ||
| keyless by this workflow (`SHA256SUMS.txt.bundle`): | ||
|
|
||
| ```sh | ||
| cosign verify-blob SHA256SUMS.txt --bundle SHA256SUMS.txt.bundle \ | ||
| --certificate-oidc-issuer https://token.actions.githubusercontent.com \ | ||
| --certificate-identity https://github.com/Open-MBEE/SysPI/.github/workflows/release.yml@refs/tags/TAG | ||
| sha256sum --check --ignore-missing SHA256SUMS.txt | ||
| ``` | ||
| NOTES | ||
| sed -i "s|@refs/tags/TAG|@refs/tags/$TAG|" "$RUNNER_TEMP/notes.md" | ||
| gh release create "$TAG" \ | ||
| --title "$TAG" \ | ||
| --notes-file "$RUNNER_TEMP/notes.md" \ | ||
| --verify-tag \ | ||
| dist/syspi-* dist/SHA256SUMS.txt dist/SHA256SUMS.txt.bundle | ||
| gh release view "$TAG" --json url,assets --jq '.url, (.assets[].name)' | ||
|
|
||
| validate-install: | ||
| name: Install from the release (${{ matrix.os }}) | ||
| needs: publish | ||
| strategy: | ||
| fail-fast: false | ||
| matrix: | ||
| os: [ubuntu-latest, macos-latest, windows-latest] | ||
| runs-on: ${{ matrix.os }} | ||
| timeout-minutes: 10 | ||
| steps: | ||
| - uses: actions/checkout@08c6903cd8c0fde910a37f88322edcfb5dd907a8 # v5.0.0 | ||
| - name: Install cosign | ||
| if: runner.os != 'Windows' | ||
| uses: sigstore/cosign-installer@6f9f17788090df1f26f669e9d70d6ae9567deba6 # v4.1.2 | ||
| with: | ||
| cosign-release: v3.0.3 | ||
| - name: install.sh | ||
| if: runner.os != 'Windows' | ||
| env: | ||
| TAG: ${{ github.ref_name }} | ||
| run: | | ||
| sh install.sh --version "$TAG" --prefix "$RUNNER_TEMP/syspi" --verify-signature | ||
| "$RUNNER_TEMP/syspi/bin/syspi" version | grep -Fx "syspi $TAG" | ||
| - name: install.ps1 | ||
| if: runner.os == 'Windows' | ||
| shell: pwsh | ||
| env: | ||
| TAG: ${{ github.ref_name }} | ||
| run: | | ||
| .\install.ps1 -Version $env:TAG -InstallDir "$env:RUNNER_TEMP\syspi" -NoPath | ||
| $reported = & "$env:RUNNER_TEMP\syspi\syspi.exe" version | ||
| if ($reported -ne "syspi $env:TAG") { throw "reports '$reported'" } | ||
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 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 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
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1 +1 @@ | ||
| - Package identities are ECMA-427 Package-URLs: a repository package is `pkg:generic/<name>?vcs_url=<vcs>+<transport>://<host>/<path>[@<version>][#<subpath>]` with the Annex B.3.5 `vcs_url` qualifier percent-encoded (`<name>` is the repository's last path segment, `<version>` a tag naming a semantic version). `pkg:git/<host>/<path>[@<version>][#<subpath>]` and the bare `<vcs>+<transport>://…` notation are accepted as input and normalised to it; `syspi add` writes the canonical form into `.project.json`. `<vcs>+file:///path` addresses a repository on this machine. A plain `http(s)` IRI is only dereferenced as a project interchange file (KerML 1.1 §10.3 Table 12). | ||
| - Package identities are ECMA-427 Package-URLs: a repository package is `pkg:generic/<name>?vcs_url=<vcs>+<transport>://<host>/<path>[@<version>][#<subpath>]` with the Annex B.3.5 `vcs_url` qualifier percent-encoded (`<name>` is the repository's last path segment, `<version>` a tag naming a semantic version). `pkg:git/<host>/<path>[@<version>][#<subpath>]` and the bare `<vcs>+<transport>://…` notation are accepted as input and normalised to it; `syspi add` writes the canonical form into `.project.json`. `<vcs>+file:///path` addresses a repository on this machine. A plain `http(s)` IRI is only dereferenced as a project interchange file (KerML 1.1 §10.3 Table 12). Other spellings (`pkg:svn/…`, `pkg:hg/…`, clone URLs such as `https://host/path.git@v`, `git@host:path`, `file:///path@v`) are refused with a message naming the accepted ones. |
This file was deleted.
Oops, something went wrong.
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
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| - Releases publish `syspi-<os>-<arch>.tar.gz` (`.zip` on Windows) for Linux, macOS and Windows on amd64 and arm64, each holding `syspi` and `LICENSE`, with `SHA256SUMS.txt` signed keyless by the release workflow (`SHA256SUMS.txt.bundle`); the tag publishes nothing until the repository gate is green on all three systems. `install.sh` (Linux, macOS) and `install.ps1` (Windows) install a release after checking the download against the manifest and the installed binary against the tag. |
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
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1 +1 @@ | ||
| - The `syspi` command: `init`, `add`, `install`, `sync`, `lock`, `bundle` and `index emit` for KerML / SysML v2 project-interchange packages identified as `pkg:<vcs>/<host>/<path>[@<version>][#<subpath>]` (git, svn, hg), local directories, local and remote `.kpar` files, OMG standard-library IRIs and `pkg:sysand/<publisher>/<name>` through a static index. Packages are verified before use, installed under `lib/<publisher>-<name>_<version>` beside `.project.json` and recorded in a deterministic `.project.lock.json` with a VCS-neutral tree hash. | ||
| - The `syspi` command: `init`, `add`, `install`, `sync`, `lock`, `bundle` and `version` for KerML / SysML v2 project-interchange packages — any git, svn or hg repository with `.project.json` at a tag, a local directory, a local or remote `.kpar` file, or an OMG standard-library IRI. Packages are verified before use, installed under `lib/<publisher>-<name>_<version>` beside `.project.json` and recorded in a deterministic `.project.lock.json` with a VCS-neutral tree hash. |
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.