66 lines
1.9 KiB
Python
66 lines
1.9 KiB
Python
#!/usr/bin/env python3
|
|
"""Detect whether the latest git commit is a release commit.
|
|
|
|
Release commits have the format ``release: vX.Y.Z [skip ci]``.
|
|
This script writes ``is-release=true`` or ``is-release=false`` to
|
|
``$GITHUB_OUTPUT`` for use in CI workflow conditionals.
|
|
|
|
Usage::
|
|
|
|
python3 scripts/ci/detect_release_commit.py
|
|
"""
|
|
|
|
from __future__ import annotations
|
|
|
|
import os
|
|
import re
|
|
import subprocess # nosec B404
|
|
|
|
import click
|
|
|
|
RELEASE_RE = re.compile(r"^release: v\d+\.\d+\.\d+")
|
|
|
|
|
|
def get_commit_message() -> str:
|
|
"""Get the subject of the latest git commit."""
|
|
result = subprocess.run( # nosec B603 B607
|
|
["git", "log", "-1", "--pretty=%s"],
|
|
capture_output=True,
|
|
text=True,
|
|
check=False,
|
|
)
|
|
if result.returncode != 0:
|
|
raise click.ClickException(f"git log failed: {result.stderr.strip()}")
|
|
return result.stdout.strip()
|
|
|
|
|
|
def is_release_commit(message: str) -> bool:
|
|
"""Check if a commit message matches the release commit format."""
|
|
return bool(RELEASE_RE.match(message))
|
|
|
|
|
|
def write_github_output(key: str, value: str) -> None:
|
|
"""Append a key=value line to the $GITHUB_OUTPUT file."""
|
|
gh_output = os.environ.get("GITHUB_OUTPUT")
|
|
if not gh_output:
|
|
raise click.ClickException("GITHUB_OUTPUT environment variable is not set")
|
|
with open(gh_output, "a") as f: # noqa: PTH123
|
|
f.write(f"{key}={value}\n")
|
|
|
|
|
|
@click.command()
|
|
def main() -> None:
|
|
"""Detect if the latest commit is a release commit and set GITHUB_OUTPUT."""
|
|
msg = get_commit_message()
|
|
click.echo(f"Commit message: {msg}")
|
|
is_release = is_release_commit(msg)
|
|
write_github_output("is-release", "true" if is_release else "false")
|
|
if is_release:
|
|
click.echo("Release commit — skipping all post-merge jobs.")
|
|
else:
|
|
click.echo("Regular merge commit — running all post-merge jobs.")
|
|
|
|
|
|
if __name__ == "__main__": # pragma: no cover
|
|
main() # pragma: no cover
|