-
Notifications
You must be signed in to change notification settings - Fork 163
chore: take over release automation and remove Stainless dependencies #100
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Merged
Changes from all commits
Commits
Show all changes
6 commits
Select commit
Hold shift + click to select a range
bb9023d
chore: take over release automation and remove Stainless dependencies
MingruiZhang c24f61f
chore: make releases dispatch-only with maintainer-chosen version bump
MingruiZhang 1a3245c
chore: release directly from dispatch — no release PR
MingruiZhang 7f63c8a
fix: satisfy repo lints in release-notes script
MingruiZhang b42ff51
fix: address Copilot review — release concurrency + cleanups
MingruiZhang c9aeb85
fix: gate the release on building and testing the stamped tree
MingruiZhang File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Some comments aren't visible on the classic Files Changed page.
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,77 @@ | ||
| #!/usr/bin/env python3 | ||
| """Generate a markdown changelog section for the commits since the previous tag. | ||
|
|
||
| Usage: generate_release_notes.py <owner/repo> <prev_tag> <next_version> | ||
|
|
||
| Reads `git log <prev_tag>..HEAD` and groups Conventional Commit subjects into | ||
| sections (same section layout the repo's CHANGELOG.md has always used). The | ||
| Release workflow prepends the output to CHANGELOG.md and uses it as the GitHub | ||
| Release notes. | ||
| """ | ||
|
|
||
| from __future__ import annotations | ||
|
|
||
| import re | ||
| import sys | ||
| import subprocess | ||
| from datetime import date | ||
|
|
||
| SECTIONS = [ | ||
| ("feat", "Features"), | ||
| ("fix", "Bug Fixes"), | ||
| ("perf", "Performance Improvements"), | ||
| ("revert", "Reverts"), | ||
| ("chore", "Chores"), | ||
| ("docs", "Documentation"), | ||
| ("style", "Styles"), | ||
| ("refactor", "Refactors"), | ||
| ("build", "Build System"), | ||
| ("other", "Other Changes"), | ||
| ] | ||
| SECTION_KEYS = {key for key, _ in SECTIONS} | ||
| HIDDEN = {"test", "ci", "release"} | ||
| CONVENTIONAL = re.compile(r"^(?P<type>[a-z]+)(?:\((?P<scope>[^)]*)\))?!?:\s*(?P<desc>.+)$") | ||
|
|
||
|
|
||
| def main() -> None: | ||
| repo, prev_tag, next_version = sys.argv[1:4] | ||
| log = subprocess.run( | ||
| ["git", "log", "--no-merges", "--pretty=format:%h\t%H\t%s", f"{prev_tag}..HEAD"], | ||
| capture_output=True, | ||
| text=True, | ||
| check=True, | ||
| ).stdout | ||
|
|
||
| buckets: dict[str, list[str]] = {} | ||
| for line in log.splitlines(): | ||
| if not line.strip(): | ||
| continue | ||
| short, full, subject = line.split("\t", 2) | ||
| match = CONVENTIONAL.match(subject) | ||
| if match: | ||
| kind = match.group("type") | ||
| if kind in HIDDEN: | ||
| continue | ||
| if kind not in SECTION_KEYS: | ||
| kind = "other" | ||
| scope, desc = match.group("scope"), match.group("desc") | ||
| text = f"**{scope}:** {desc}" if scope else desc | ||
| else: | ||
| kind, text = "other", subject | ||
| entry = f"* {text} ([{short}](https://github.com/{repo}/commit/{full}))" | ||
| buckets.setdefault(kind, []).append(entry) | ||
|
|
||
| out = [ | ||
| f"## {next_version} ({date.today().isoformat()})", | ||
| "", | ||
| f"Full Changelog: [{prev_tag}...v{next_version}](https://github.com/{repo}/compare/{prev_tag}...v{next_version})", | ||
| ] | ||
| for kind, title in SECTIONS: | ||
| entries = buckets.get(kind, []) | ||
| if entries: | ||
| out += ["", f"### {title}", ""] + entries | ||
| sys.stdout.write("\n".join(out) + "\n") | ||
|
|
||
|
|
||
| if __name__ == "__main__": | ||
| main() |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,122 @@ | ||
| # Manual, dispatch-only release automation (replaces the Stainless-run | ||
| # release-please after the platform sunset on 2026-09-01). | ||
| # | ||
| # A maintainer runs this workflow (Actions -> Release -> Run workflow) and | ||
| # picks the bump: patch / minor / major. The workflow then, in one shot: | ||
| # 1. computes the next version from the latest git tag, | ||
| # 2. stamps it into pyproject.toml and src/landingai_ade/_version.py, | ||
| # 3. prepends a changelog section (grouped by Conventional Commit prefixes) | ||
| # to CHANGELOG.md, | ||
| # 4. builds and tests the stamped tree — the release aborts here, before | ||
| # any commit or tag exists, if anything is red, | ||
| # 5. lands that as a "release: x.y.z" commit directly on main, | ||
| # 6. tags it and creates the GitHub Release, which triggers | ||
| # .github/workflows/publish-pypi.yml. | ||
| # | ||
| # No release PR, no second confirmation: dispatching the workflow IS the | ||
| # release decision. Ordinary PR merges never trigger any of this. | ||
| # | ||
| # RELEASE_TOKEN requirements: | ||
| # - a fine-grained PAT (or GitHub App installation token) with | ||
| # Contents: write on this repository; | ||
| # - its owner must be able to bypass the main-branch ruleset (the ruleset | ||
| # requires PRs; this repo's ruleset grants "always" bypass to | ||
| # organization admins). Otherwise the direct push in step 4 is rejected. | ||
| # - The default GITHUB_TOKEN cannot be used: releases it creates do not | ||
| # trigger other workflows, so publishing would silently never run. | ||
| name: Release | ||
|
|
||
| on: | ||
| workflow_dispatch: | ||
| inputs: | ||
| bump: | ||
| description: 'Version bump for this release' | ||
| type: choice | ||
| required: true | ||
| options: | ||
| - patch | ||
| - minor | ||
| - major | ||
|
|
||
| # Only one release can run at a time; a second dispatch queues rather than | ||
| # racing the version computation and the push to main. | ||
| concurrency: | ||
| group: release | ||
| cancel-in-progress: false | ||
|
|
||
| jobs: | ||
| release: | ||
| name: release | ||
| runs-on: ubuntu-latest | ||
| if: github.repository == 'landing-ai/ade-python' && github.ref == 'refs/heads/main' | ||
| steps: | ||
| - uses: actions/checkout@v6 | ||
| with: | ||
| fetch-depth: 0 # full history: needed for the previous tag + changelog range | ||
| token: ${{ secrets.RELEASE_TOKEN }} | ||
|
MingruiZhang marked this conversation as resolved.
|
||
|
|
||
| - name: Compute next version | ||
| id: version | ||
| env: | ||
| BUMP: ${{ inputs.bump }} | ||
| run: | | ||
| prev_tag="$(git describe --tags --abbrev=0)" | ||
| current="${prev_tag#v}" | ||
| IFS='.' read -r major minor patch <<< "$current" | ||
| case "$BUMP" in | ||
| major) next="$((major + 1)).0.0" ;; | ||
| minor) next="${major}.$((minor + 1)).0" ;; | ||
| patch) next="${major}.${minor}.$((patch + 1))" ;; | ||
| esac | ||
| echo "bumping $current -> $next ($BUMP)" | ||
| { | ||
| echo "prev_tag=$prev_tag" | ||
| echo "version=$next" | ||
| } >> "$GITHUB_OUTPUT" | ||
|
|
||
| - name: Stamp version | ||
| env: | ||
| NEXT: ${{ steps.version.outputs.version }} | ||
| run: | | ||
| sed -i -E "s/^version = \".*\"/version = \"$NEXT\"/" pyproject.toml | ||
| sed -i -E "s/__version__ = \".*\"/__version__ = \"$NEXT\"/" src/landingai_ade/_version.py | ||
| git diff --stat | ||
|
|
||
| - name: Update changelog | ||
| env: | ||
| PREV_TAG: ${{ steps.version.outputs.prev_tag }} | ||
| NEXT: ${{ steps.version.outputs.version }} | ||
| run: | | ||
| python3 .github/scripts/generate_release_notes.py \ | ||
| "${{ github.repository }}" "$PREV_TAG" "$NEXT" > /tmp/release-notes.md | ||
| { head -n 2 CHANGELOG.md; cat /tmp/release-notes.md; echo; tail -n +3 CHANGELOG.md; } > /tmp/changelog.md | ||
| mv /tmp/changelog.md CHANGELOG.md | ||
|
|
||
| - name: Install Rye | ||
| run: | | ||
| curl -sSf https://rye.astral.sh/get | bash | ||
| echo "$HOME/.rye/shims" >> $GITHUB_PATH | ||
| env: | ||
| RYE_VERSION: '0.44.0' | ||
| RYE_INSTALL_OPTION: '--yes' | ||
|
|
||
| - name: Build and test the stamped tree | ||
| run: | | ||
| ./scripts/bootstrap | ||
| rye build | ||
| ./scripts/test | ||
|
|
||
| - name: Commit, tag, and create the GitHub Release | ||
| env: | ||
| GH_TOKEN: ${{ secrets.RELEASE_TOKEN }} | ||
| NEXT: ${{ steps.version.outputs.version }} | ||
|
MingruiZhang marked this conversation as resolved.
|
||
| run: | | ||
| git config user.name "github-actions[bot]" | ||
| git config user.email "41898282+github-actions[bot]@users.noreply.github.com" | ||
| git add pyproject.toml src/landingai_ade/_version.py CHANGELOG.md | ||
| git commit -m "release: $NEXT" | ||
| git push origin HEAD:main | ||
| gh release create "v$NEXT" \ | ||
| --target "$(git rev-parse HEAD)" \ | ||
| --title "v$NEXT" \ | ||
| --notes-file /tmp/release-notes.md | ||
This file was deleted.
Oops, something went wrong.
This file was deleted.
Oops, something went wrong.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -2,25 +2,22 @@ | |
|
|
||
| ## Reporting Security Issues | ||
|
|
||
| This SDK is generated by [Stainless Software Inc](http://stainless.com). Stainless takes security seriously, and encourages you to report any security vulnerability promptly so that appropriate action can be taken. | ||
| This SDK is maintained by [LandingAI](https://landing.ai/). | ||
|
|
||
| To report a security issue, please contact the Stainless team at [email protected]. | ||
| To report a security issue, please use GitHub's private vulnerability reporting on this repository | ||
| ("Security" → "Report a vulnerability"), or contact us at [email protected]. | ||
|
|
||
| ## Responsible Disclosure | ||
|
|
||
| We appreciate the efforts of security researchers and individuals who help us maintain the security of | ||
| SDKs we generate. If you believe you have found a security vulnerability, please adhere to responsible | ||
| our SDKs. If you believe you have found a security vulnerability, please adhere to responsible | ||
| disclosure practices by allowing us a reasonable amount of time to investigate and address the issue | ||
| before making any information public. | ||
|
|
||
| ## Reporting Non-SDK Related Security Issues | ||
|
|
||
| If you encounter security issues that are not directly related to SDKs but pertain to the services | ||
| or products provided by LandingAI ADE, please follow the respective company's security reporting guidelines. | ||
|
|
||
| ### LandingAI ADE Terms and Policies | ||
|
|
||
| Please contact [email protected] for any questions or concerns regarding the security of our services. | ||
| If you encounter security issues that are not directly related to this SDK but pertain to the services | ||
| or products provided by LandingAI, please contact [email protected]. | ||
|
|
||
| --- | ||
|
|
||
|
|
||
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.