name: Release # A pushed v* tag makes this workflow build every desktop target, run the # end-to-end suites and attach the binaries to the matching GitHub release. # workflow_dispatch lets an existing tag be rebuilt without moving it. on: push: tags: - "v*" workflow_dispatch: inputs: tag: description: "Tag to build and publish; leave empty to use the latest tag" required: false default: "" type: string permissions: contents: write concurrency: group: release-${{ github.ref }} cancel-in-progress: false jobs: test: name: End-to-end tests # Gitea also discovers .github/workflows; this keeps the run on GitHub only. if: github.server_url == 'https://github.com' runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - uses: actions/setup-go@v5 with: go-version-file: go.mod cache: true - name: golink suite run: ./smoketest/run.sh - name: goscp suite run: ./smoketest/run-goscp.sh release: name: Build and publish needs: test if: github.server_url == 'https://github.com' runs-on: ubuntu-latest steps: # Full history and tags: a manual run resolves the tag with git describe. - uses: actions/checkout@v4 with: fetch-depth: 0 - uses: actions/setup-go@v5 with: go-version-file: go.mod cache: true - name: Resolve tag id: tag env: INPUT_TAG: ${{ inputs.tag }} REF_NAME: ${{ github.ref_name }} EVENT_NAME: ${{ github.event_name }} run: | set -euo pipefail tag="${INPUT_TAG:-}" if [ -z "$tag" ]; then if [ "$EVENT_NAME" = "push" ]; then tag="$REF_NAME" else tag="$(git describe --tags --abbrev=0)" fi fi [ -n "$tag" ] || { echo "no tag found, pass one explicitly" >&2; exit 1; } echo "value=$tag" >> "$GITHUB_OUTPUT" echo "building $tag" - name: Build every target env: TAG: ${{ steps.tag.outputs.value }} run: | set -euo pipefail VERSION="${TAG#v}" ./build.sh - name: Verify the binaries env: TAG: ${{ steps.tag.outputs.value }} run: | set -euo pipefail want="${TAG#v}" for program in golink goscp; do got="$(./dist/$program -version | awk '{print $2}')" echo "$program: $got" [ "$got" = "$want" ] || { echo "version mismatch: want $want, got $got" >&2; exit 1; } done # SHA256SUMS lists bare file names, so verify from inside dist/. ( cd dist && sha256sum -c SHA256SUMS ) - name: Publish to the release env: GH_TOKEN: ${{ github.token }} TAG: ${{ steps.tag.outputs.value }} run: | set -euo pipefail if gh release view "$TAG" >/dev/null 2>&1; then echo "release $TAG already exists, replacing assets" else gh release create "$TAG" \ --title "sshtools $TAG" \ --generate-notes \ --verify-tag fi gh release upload "$TAG" dist/golink_* dist/goscp_* dist/SHA256SUMS --clobber gh release view "$TAG"