diff --git a/.github/workflows/cmake_release.yml b/.github/workflows/cmake_release.yml index 063e1b63..78f11fdd 100644 --- a/.github/workflows/cmake_release.yml +++ b/.github/workflows/cmake_release.yml @@ -264,4 +264,9 @@ jobs: installers/*/*.dmg - name: Create Release - run: gh release create ${{ github.ref_name }} --prerelease installers/*/*.msi installers/*/*.zip installers/*/*.dmg \ No newline at end of file + # a product that doesn't build on every platform has no installers of some kinds (Dialogue: no Linux zips) + run: | + shopt -s nullglob + tag="${{ github.ref_name }}" + python3 scripts/release_notes.py "${tag%-v*}" "${tag##*-v}" > notes.md + gh release create "$tag" --prerelease --notes-file notes.md installers/*/*.msi installers/*/*.zip installers/*/*.dmg \ No newline at end of file diff --git a/cmake/AltvanePlugin.cmake b/cmake/AltvanePlugin.cmake index 4056b3b0..dce2271e 100644 --- a/cmake/AltvanePlugin.cmake +++ b/cmake/AltvanePlugin.cmake @@ -46,6 +46,15 @@ function(altvane_add_plugin target) if (NOT ARG_AAX_CATEGORY) set(ARG_AAX_CATEGORY AAX_ePlugInCategory_None) endif () + # checked here, on every platform, rather than only where LV2 is built (patch_lv2.py fails the build there) + file(STRINGS "${CMAKE_SOURCE_DIR}/packaging/patch_lv2.py" lv2_lines REGEX "^ '[a-z]+': 'lv2:") + list(TRANSFORM lv2_lines REPLACE "^ '([a-z]+)'.*" "\\1" OUTPUT_VARIABLE lv2_known) + foreach (tag IN LISTS ARG_LV2_TAGS) + string(TOLOWER "${tag}" tag_lower) + if (NOT tag_lower IN_LIST lv2_known) + message(FATAL_ERROR "altvane_add_plugin(${target}): '${tag}' is not an LV2 tag packaging/patch_lv2.py knows") + endif () + endforeach () set(product_dir "${CMAKE_CURRENT_SOURCE_DIR}") diff --git a/scripts/release_notes.py b/scripts/release_notes.py new file mode 100755 index 00000000..d6dcc3c3 --- /dev/null +++ b/scripts/release_notes.py @@ -0,0 +1,43 @@ +#!/usr/bin/env python3 +"""Print the release notes for one product's release: its CHANGELOG section and how to install an unsigned build. + + scripts/release_notes.py + +The section is the one headed `## ` in products//CHANGELOG.md. Its headings move up a level and its +hard-wrapped lines are joined, since GitHub keeps line breaks in release notes.""" +import pathlib +import re +import sys + +root = pathlib.Path(__file__).resolve().parent.parent +product, version = sys.argv[1], sys.argv[2] +changelog = (root / "products" / product / "CHANGELOG.md").read_text() +match = re.search(rf"^## {re.escape(version)}\n(.*?)(?=^## |\Z)", changelog, re.S | re.M) +if not match: + sys.exit(f"products/{product}/CHANGELOG.md has no '## {version}' section") +notes = match.group(1).strip() +notes = re.sub(r"^### ", "## ", notes, flags=re.M) +notes = re.sub(r"\n {2,}(?=\S)", " ", notes) # a list item's continuation lines +notes = re.sub(r"(?<=[^\n])\n(?=[^\n\-#*\s|])", " ", notes) # a paragraph's + +platforms_file = root / "products" / product / "PLATFORMS" +platforms = None +if platforms_file.exists(): + platforms = {line.strip() for line in platforms_file.read_text().splitlines() + if line.strip() and not line.startswith("#")} + + +def builds_on(system: str) -> bool: + return platforms is None or any(p.startswith(system) for p in platforms) + + +install = ["## Installing", "", "These builds are not signed yet.", ""] +if builds_on("Darwin"): + install.append("- **macOS:** if macOS says the installer can't be opened, open System Settings → Privacy & Security " + "and choose **Open Anyway**.") +if builds_on("Windows"): + install.append("- **Windows:** if SmartScreen stops the installer, choose **More info → Run anyway**.") +if builds_on("Linux"): + install.append("- **Linux:** unzip and copy the plug-ins into `~/.vst3` or `~/.lv2`.") +install += ["", "Pick the AVX2 build on x86-64 machines from about 2013 onwards; the plain x86-64 build runs everywhere."] +print(notes + "\n\n" + "\n".join(install))