From 126d56c482805d862389a063669502d92401959e Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 31 Oct 2026 05:46:45 +0000 Subject: [PATCH 1/2] Release workflow: a new version can be started by hand Run workflow with a version that has no tag yet builds main, and publishing the release creates the tag on the commit that was built. An existing tag is still built exactly as tagged. The release text can also come from .github/release-notes/.md. Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01GvUq7HnA5ggbuHBogzS2rV --- .github/workflows/release.yml | 44 +++++++++++++++++++++++++++-------- 1 file changed, 34 insertions(+), 10 deletions(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 8b27495..8b3a4ad 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -24,7 +24,7 @@ on: workflow_dispatch: inputs: tag: - description: 'Existing tag to release (for example v1.25.0)' + description: 'Version to release, e.g. v1.25.0: an existing tag is built as it is, a new one is built from main and tagged' required: true dry_run: description: 'Dry run: build and check only, sign and publish nothing' @@ -55,7 +55,6 @@ jobs: steps: - uses: actions/checkout@v4 with: - ref: ${{ inputs.tag || github.ref }} # The annotated tag message becomes the release notes, and that # annotation only exists in a clone that carries the tag objects. fetch-depth: 0 @@ -70,6 +69,26 @@ jobs: go-version: 'stable' cache: true + # Started by hand: an existing tag is built exactly as tagged. A new + # version is built from main, and publishing the release creates its + # tag on the commit that was built. + - name: Commit to build + if: github.event_name == 'workflow_dispatch' + env: + RELEASE_TAG: ${{ inputs.tag }} + run: | + git rev-parse -q --verify "refs/tags/$env:RELEASE_TAG" *> $null + if ($LASTEXITCODE -eq 0) { + git checkout -q --detach "refs/tags/$env:RELEASE_TAG" + Write-Host "Building the existing tag $env:RELEASE_TAG." + } elseif ($env:GITHUB_REF_NAME -ne 'main' -and $env:DRY_RUN -ne 'true') { + Write-Host "::error::A new version is released from main only, not from $env:GITHUB_REF_NAME." + exit 1 + } else { + Write-Host "Tag $env:RELEASE_TAG does not exist yet: building $env:GITHUB_REF_NAME, the release creates the tag." + } + $global:LASTEXITCODE = 0 + # A tag that disagrees with appVersion would ship an exe announcing the # wrong version in its own startup header. Cheaper to catch here than to # replace a published asset afterwards. A pull request has no tag: it @@ -188,13 +207,18 @@ jobs: $title = "NVENCForge $tag" Write-Host "Publishing $tag with NVENCForge.exe ($((Get-Item NVENCForge.exe).Length) bytes)." - # The release text is the annotated tag message - one source, written - # once, at the moment the version is cut. A tag without one is a - # mistake worth stopping for, not something to paper over with an - # empty release. - $notes = (git tag -l --format='%(contents)' $tag) -join "`n" + # The release text is .github/release-notes/.md, or else the + # annotated tag message - one source, written once, at the moment + # the version is cut. A release without either is a mistake worth + # stopping for, not something to paper over with an empty release. + $file = ".github/release-notes/$tag.md" + if (Test-Path $file) { + $notes = [IO.File]::ReadAllText("$PWD/$file") + } else { + $notes = (git tag -l --format='%(contents)' $tag) -join "`n" + } if ([string]::IsNullOrWhiteSpace($notes)) { - Write-Host "::error::Tag $tag has no annotation - the release notes come from it. Create it with 'git tag -a'." + Write-Host "::error::No release text for $tag: add $file or create the tag with 'git tag -a'." exit 1 } # The release page is the download page, so it links the code @@ -205,7 +229,7 @@ jobs: } else { $footer = "NVENCForge.exe is not code signed, so Windows SmartScreen may warn. [Code signing policy]($policy)" } - "$notes`n`n---`n`n$footer" | Out-File -FilePath release-notes.md -Encoding utf8 + "$($notes.TrimEnd())`n`n---`n`n$footer" | Out-File -FilePath release-notes.md -Encoding utf8 # gh release view exits non-zero when the release does not exist yet. # Re-running a release (a corrected workflow, a retried build) has to @@ -220,5 +244,5 @@ jobs: gh release edit $tag --title $title --notes-file release-notes.md --draft=false gh release upload $tag NVENCForge.exe --clobber } else { - gh release create $tag NVENCForge.exe --title $title --notes-file release-notes.md + gh release create $tag NVENCForge.exe --target (git rev-parse HEAD) --title $title --notes-file release-notes.md } From b4450ccf4398ef1f1da83210a1ae47b14f73b68c Mon Sep 17 00:00:00 2001 From: Claude Date: Sat, 31 Oct 2026 05:46:45 +0000 Subject: [PATCH 2/2] Release 2.2.2: built on GitHub, ready for code signing Version 2.2.2 in main.go and TECHNICAL.md, and the release text. No change to what the program does. Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01GvUq7HnA5ggbuHBogzS2rV --- .github/release-notes/v2.2.2.md | 10 ++++++++++ TECHNICAL.md | 2 +- main.go | 2 +- 3 files changed, 12 insertions(+), 2 deletions(-) create mode 100644 .github/release-notes/v2.2.2.md diff --git a/.github/release-notes/v2.2.2.md b/.github/release-notes/v2.2.2.md new file mode 100644 index 0000000..9439a86 --- /dev/null +++ b/.github/release-notes/v2.2.2.md @@ -0,0 +1,10 @@ +## NVENCForge 2.2.2: built on GitHub, ready for code signing + +Converting works exactly as in 2.2.1. This release is about where the exe comes from. + +- **Built by GitHub Actions** from the source in this repository, never on a private PC. Releases can now also be started by hand on GitHub, and a dry run checks the whole build without publishing anything. +- **File properties:** `NVENCForge.exe` now shows its name and version under right-click > Properties > Details. +- **Code signing prepared:** free code signing through the SignPath Foundation is applied for. Until it is active the exe stays unsigned. What would be signed, who approves it and what NVENCForge sends over the network (only the FFmpeg download): [code signing policy](https://github.com/burnersen/NVENCForge/blob/main/CODE_SIGNING.md). +- **License:** GPL-3.0-only, and nothing else. + +Update: replace `NVENCForge.exe` with the new one. Your settings stay. With NVENCForgeGUI: use the converter's update button. diff --git a/TECHNICAL.md b/TECHNICAL.md index 258b04c..ef7d1f0 100644 --- a/TECHNICAL.md +++ b/TECHNICAL.md @@ -396,7 +396,7 @@ That's it. `build.bat` resolves the dependencies and compiles `NVENCForge.exe` ( Released exes are built by the [release workflow](.github/workflows/release.yml) on GitHub, which also writes name and version into the file properties (from [`winres/winres.json`](winres/winres.json)) and, once code signing is switched on, has the exe signed: see [`.signpath/README.md`](.signpath/README.md). To get the same file properties locally, run this before `build.bat`: ``` -go run github.com/tc-hib/go-winres@v0.3.3 make --in winres/winres.json --out rsrc --arch amd64 --product-version 2.2.1 --file-version 2.2.1 +go run github.com/tc-hib/go-winres@v0.3.3 make --in winres/winres.json --out rsrc --arch amd64 --product-version 2.2.2 --file-version 2.2.2 ``` --- diff --git a/main.go b/main.go index f147d11..8f4a6ff 100644 --- a/main.go +++ b/main.go @@ -51,7 +51,7 @@ import ( // appVersion is shown in the startup header so the running build is obvious. // Keep it in sync with the git tag / GitHub release on every release. -const appVersion = "2.2.1" +const appVersion = "2.2.2" // ---------------------------------------------------------------------------- // Package-level sentinels and tool paths (set once in initTools, read-only after)