Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 11 additions & 0 deletions .github/workflows/release-check.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
name: "🔖 Release PR check"

on:
pull_request:
branches: [main]
types: [opened, synchronize, reopened, edited]

jobs:
release-check:
name: "🤙 Call SDK release-check workflow"
uses: clamsproject/.github/.github/workflows/sdk-release-check.yml@main
7 changes: 7 additions & 0 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,13 @@ from clams.ver import __version__
For a dev install without a matching tag, `setuptools-scm` generates a
version like `1.4.1.dev20+gaf551a4e4.d20260325`.

## Releases

Release PRs (from `develop` to `main`) are gated by the `release-check` CI workflow. Before opening one:

1. Title the PR exactly `releasing X.Y.Z` (strict semver); `release-check` reads the version from the title.
2. Run `python build-tools/prep_release.py X.Y.Z` and commit its changes. See inside the prep script to see what's actually prepared.

## Migration from Makefile

The old `Makefile` and `setup.py` have been removed. If you are
Expand Down
104 changes: 104 additions & 0 deletions build-tools/prep_release.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
"""
Prepare release artifacts for the clams-python package.

Run while preparing a release PR, passing the version being released::

python build-tools/prep_release.py X.Y.Z

Currently this adds a row to ``documentation/target-versions.csv`` for
the release version. The ``mmif-python`` column is read from this
package's pinned dependency in ``pyproject.toml``, and the target MMIF
spec version from the installed ``mmif.__specver__``. This script is the
single place that writes the target-versions table; the docs build only
renders it, and CI verifies (on the release PR) that a row for the PR's
version exists.

Requires an editable install (``pip install -e .``) so that
``mmif.__specver__`` is importable.
"""
import argparse
import re
import sys
from pathlib import Path

PROJECT_ROOT = Path(__file__).parent.parent
CSV_PATH = PROJECT_ROOT / 'documentation' / 'target-versions.csv'
PYPROJECT_PATH = PROJECT_ROOT / 'pyproject.toml'

VERSION_RE = re.compile(r'^\d+\.\d+\.\d+$')
TOP_ROW_RE = re.compile(r'`(\d+\.\d+\.\d+) <')
MMIF_PIN_RE = re.compile(r'mmif-python\s*==\s*(\d+\.\d+\.\d+)')


def _row(version, mmif_ver, specver):
return (
f'`{version} <https://pypi.org/project/clams-python/{version}/>`__,'
f'`{mmif_ver} <https://pypi.org/project/mmif-python/{mmif_ver}/>`__,'
f'`{specver} <https://mmif.clams.ai/{specver}/>`__'
)


def _version_tuple(v):
return tuple(int(x) for x in v.split('.'))


def _top_version(data_lines):
if not data_lines:
return None
m = TOP_ROW_RE.match(data_lines[0])
return m.group(1) if m else None


def _pinned_mmif_version():
m = MMIF_PIN_RE.search(PYPROJECT_PATH.read_text())
if not m:
sys.exit("Error: could not find a pinned 'mmif-python==X.Y.Z' "
"dependency in pyproject.toml.")
return m.group(1)


def main():
parser = argparse.ArgumentParser(
description="Prepare release artifacts for clams-python."
)
parser.add_argument(
"version", metavar="X.Y.Z",
help="the release version being prepared",
)
args = parser.parse_args()
version = args.version

if not VERSION_RE.match(version):
sys.exit(f"Error: '{version}' is not a valid X.Y.Z version.")

mmif_ver = _pinned_mmif_version()
try:
import mmif
specver = mmif.__specver__
except (ImportError, AttributeError):
sys.exit("Error: cannot read mmif.__specver__. "
"Run `pip install -e .` first.")

lines = CSV_PATH.read_text().splitlines()
header, data = lines[0], lines[1:]
top = _top_version(data)

if top is not None and _version_tuple(version) < _version_tuple(top):
sys.exit(f"Error: {version} is older than the current top row "
f"{top}; refusing to insert an out-of-order version.")

new_row = _row(version, mmif_ver, specver)
if top == version:
data[0] = new_row # update in place
action = "updated"
else:
data.insert(0, new_row) # prepend as the new latest
action = "added"

CSV_PATH.write_text('\n'.join([header] + data) + '\n')
print(f"target-versions.csv: {action} row {version} "
f"-> mmif-python {mmif_ver}, MMIF spec {specver}")


if __name__ == "__main__":
main()
20 changes: 0 additions & 20 deletions documentation/conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,6 @@
import inspect
import json
import os
import re
import shutil
import subprocess
import sys
from pathlib import Path
Expand Down Expand Up @@ -196,24 +194,6 @@ def generate_jsonschema(app):
json.dump(schema_dict, f, indent=2)


def update_target_spec(app):
target_vers_csv = Path(__file__).parent / 'target-versions.csv'
version = _get_version('clams-python')
# Skip dev/dummy versions to avoid dirtying the git-tracked CSV
if 'dev' in version or not re.match(r'^\d+\.\d+\.\d+$', version):
return
mmifver = mmif.__version__
specver = mmif.__specver__
with open(target_vers_csv) as in_f, open(f'{target_vers_csv}.new', 'w') as out_f:
lines = in_f.readlines()
if not lines[1].startswith(f"`{version}"):
lines.insert(1, f"`{version} <https://pypi.org/project/clams-python/{version}/>`__,`{mmifver} <https://pypi.org/project/mmif-python/{mmifver}/>`__,`{specver} <https://mmif.clams.ai/{specver}/>`__\n")
for line in lines:
out_f.write(line)
shutil.move(out_f.name, in_f.name)


def setup(app):
app.connect('builder-inited', generate_whatsnew_rst)
app.connect('builder-inited', generate_jsonschema)
app.connect('builder-inited', update_target_spec)
7 changes: 6 additions & 1 deletion documentation/target-versions.csv
Original file line number Diff line number Diff line change
@@ -1,4 +1,9 @@
"``clams-python`` version","``mmif-python`` version","Target MMIF Specification"
`1.7.1 <https://pypi.org/project/clams-python/1.7.1/>`__,`1.5.1 <https://pypi.org/project/mmif-python/1.5.1/>`__,`1.2.0 <https://mmif.clams.ai/1.2.0/>`__
`1.7.0 <https://pypi.org/project/clams-python/1.7.0/>`__,`1.5.0 <https://pypi.org/project/mmif-python/1.5.0/>`__,`1.2.0 <https://mmif.clams.ai/1.2.0/>`__
`1.6.0 <https://pypi.org/project/clams-python/1.6.0/>`__,`1.4.0 <https://pypi.org/project/mmif-python/1.4.0/>`__,`1.1.1 <https://mmif.clams.ai/1.1.1/>`__
`1.5.0 <https://pypi.org/project/clams-python/1.5.0/>`__,`1.3.1 <https://pypi.org/project/mmif-python/1.3.1/>`__,`1.1.0 <https://mmif.clams.ai/1.1.0/>`__
`1.4.0 <https://pypi.org/project/clams-python/1.4.0/>`__,`1.2.1 <https://pypi.org/project/mmif-python/1.2.1/>`__,`1.1.0 <https://mmif.clams.ai/1.1.0/>`__
`1.3.3 <https://pypi.org/project/clams-python/1.3.3/>`__,`1.1.2 <https://pypi.org/project/mmif-python/1.1.2/>`__,`1.1.0 <https://mmif.clams.ai/1.1.0/>`__
`1.3.2 <https://pypi.org/project/clams-python/1.3.2/>`__,`1.1.1 <https://pypi.org/project/mmif-python/1.1.1/>`__,`1.1.0 <https://mmif.clams.ai/1.1.0/>`__
`1.3.1 <https://pypi.org/project/clams-python/1.3.1/>`__,`1.0.19 <https://pypi.org/project/mmif-python/1.0.19/>`__,`1.0.5 <https://mmif.clams.ai/1.0.5/>`__
Expand Down Expand Up @@ -50,4 +55,4 @@
`0.1.7 <https://pypi.org/project/clams-python/0.1.7/>`__,`0.2.2 <https://pypi.org/project/mmif-python/0.2.2/>`__,`0.2.1 <https://mmif.clams.ai/0.2.1/>`__
`0.1.6 <https://pypi.org/project/clams-python/0.1.6/>`__,`0.2.1 <https://pypi.org/project/mmif-python/0.2.1/>`__,`0.2.1 <https://mmif.clams.ai/0.2.1/>`__
`0.1.5 <https://pypi.org/project/clams-python/0.1.5/>`__,`0.2.1 <https://pypi.org/project/mmif-python/0.2.1/>`__,`0.2.1 <https://mmif.clams.ai/0.2.1/>`__
`0.1.4 <https://pypi.org/project/clams-python/0.1.4/>`__,`0.2.1 <https://pypi.org/project/mmif-python/0.2.1/>`__,`0.2.1 <https://mmif.clams.ai/0.2.1/>`__
`0.1.4 <https://pypi.org/project/clams-python/0.1.4/>`__,`0.2.1 <https://pypi.org/project/mmif-python/0.2.1/>`__,`0.2.1 <https://mmif.clams.ai/0.2.1/>`__
2 changes: 1 addition & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ classifiers = [
"Programming Language :: Python :: 3 :: Only",
]
dependencies = [
"mmif-python==1.5.0",
"mmif-python==1.5.1",
"Flask>=2",
"Flask-RESTful>=0.3.9",
"gunicorn>=20",
Expand Down
Loading