-
-
Notifications
You must be signed in to change notification settings - Fork 952
feat(releases): add a prerelease workflow #2737
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
Conversation
Adds a manual trigger to the `release.yml` workflow for publishing prerelease versions. Needs to be in the same workflow file due to a NPM limitation on how OIDC claims are checked. Currently there is a validation step on the ref for the prerelease: it must be merged to the main branch. We can revisit this in the future in case we find it too limiting.
|
WalkthroughThis change adds a manual workflow dispatch trigger and prerelease publishing path to the GitHub Actions release workflow. The modification introduces workflow_dispatch inputs for ref and tag, creates a new prerelease job that validates the ref is on the main branch, and adds prerelease-specific publishing steps. The existing automated release flow is preserved with added conditions to exclude workflow_dispatch events. Step titles are also cleaned up for consistency by removing decorative symbols. Estimated code review effort🎯 3 (Moderate) | ⏱️ ~20 minutes
Pre-merge checks and finishing touches❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
✨ Finishing touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
🧹 Nitpick comments (2)
.github/workflows/release.yml (2)
24-26: Concurrency group serializes release and prerelease jobs.The shared concurrency group means that if a prerelease is manually triggered while a release job is in progress (both on main), the prerelease will cancel the release job due to
cancel-in-progress: true.While the mutual conditions (line 37 and line 162) ensure only one job type runs per trigger, the concurrency cancellation could interrupt a long-running release. Consider whether you'd prefer separate concurrency groups to allow them to run independently, or whether serialization is intentional.
If you prefer to allow release and prerelease to run in parallel, you could use separate concurrency groups:
-concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true +concurrency: + group: ${{ github.workflow }}-${{ github.event_name }}-${{ github.ref }} + cancel-in-progress: trueThis keeps prerelease runs separate from automated release runs.
163-206: Changeset commands are correct; type-check omission appears intentional but consider documenting the rationale.The snapshot versioning and publishing commands use proper Changeset CLI syntax:
changeset version --snapshot ${{ github.event.inputs.tag }}correctly generates snapshot versionschangeset publish --no-git-tag --snapshot --tag ${{ github.event.inputs.tag }}properly combines snapshot publishing with custom dist-tagThe type-check step is deliberately omitted from the prerelease job (present in release job at line 68-69 but absent after the build step in prerelease). This appears to be an intentional optimization for faster prerelease cycles. Consider adding an inline comment explaining this design choice to prevent future confusion.
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
.github/workflows/release.yml(4 hunks)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (23)
- GitHub Check: units / internal / 🧪 Unit Tests: Internal (1, 8)
- GitHub Check: units / webapp / 🧪 Unit Tests: Webapp (5, 8)
- GitHub Check: units / internal / 🧪 Unit Tests: Internal (6, 8)
- GitHub Check: units / internal / 🧪 Unit Tests: Internal (5, 8)
- GitHub Check: units / internal / 🧪 Unit Tests: Internal (4, 8)
- GitHub Check: units / internal / 🧪 Unit Tests: Internal (7, 8)
- GitHub Check: units / internal / 🧪 Unit Tests: Internal (8, 8)
- GitHub Check: units / webapp / 🧪 Unit Tests: Webapp (7, 8)
- GitHub Check: units / internal / 🧪 Unit Tests: Internal (3, 8)
- GitHub Check: units / internal / 🧪 Unit Tests: Internal (2, 8)
- GitHub Check: units / webapp / 🧪 Unit Tests: Webapp (8, 8)
- GitHub Check: units / webapp / 🧪 Unit Tests: Webapp (1, 8)
- GitHub Check: units / webapp / 🧪 Unit Tests: Webapp (3, 8)
- GitHub Check: units / webapp / 🧪 Unit Tests: Webapp (6, 8)
- GitHub Check: units / webapp / 🧪 Unit Tests: Webapp (4, 8)
- GitHub Check: units / webapp / 🧪 Unit Tests: Webapp (2, 8)
- GitHub Check: e2e / 🧪 CLI v3 tests (windows-latest - npm)
- GitHub Check: units / packages / 🧪 Unit Tests: Packages (1, 1)
- GitHub Check: e2e / 🧪 CLI v3 tests (ubuntu-latest - npm)
- GitHub Check: e2e / 🧪 CLI v3 tests (windows-latest - pnpm)
- GitHub Check: e2e / 🧪 CLI v3 tests (ubuntu-latest - pnpm)
- GitHub Check: typecheck / typecheck
- GitHub Check: Analyze (javascript-typescript)
🔇 Additional comments (4)
.github/workflows/release.yml (4)
12-22: ✓ Well-structured workflow_dispatch trigger.The inputs are clearly defined with appropriate descriptions and defaults. No concerns.
37-37: ✓ Release job condition correctly gates automated flow.The condition prevents the automated release flow from interfering with manual prerelease triggers.
159-161: Prerelease job permissions are appropriately minimal.The prerelease job has only
contents: readandid-token: write, which is suitable for read-only builds and OIDC-based NPM publishing. This follows the principle of least privilege compared to the release job.Confirm that your NPM OIDC setup works with only
id-token: write(no explicit NPM token needed).
43-102: Step title cleanup is safe.Removing emoji decorators from step titles improves readability and maintainability. Step titles are display-only in GitHub Actions; downstream workflows and scripts reference steps by their
idfield, not titles, so this change poses no risk to automation.
| - name: Validate ref is on main | ||
| run: | | ||
| if ! git merge-base --is-ancestor ${{ github.event.inputs.ref }} origin/main; then | ||
| echo "Error: ref must be an ancestor of main (i.e., already merged)" | ||
| exit 1 | ||
| fi |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧩 Analysis chain
🌐 Web query:
actions/checkout@v4 fetch-depth origin/main remote tracking branch
💡 Result:
Short answer: use actions/checkout@v4 with fetch-depth: 0 (or a depth that includes the commit you need) and then explicitly fetch and set the remote-tracking branch for origin/main. Example:
-
uses: actions/checkout@v4
with:
fetch-depth: 0
ref: refs/heads/${{ github.ref_name }} # optional: explicit ref -
run: |
ensure origin/main exists as a remote-tracking ref
git fetch origin main:refs/remotes/origin/main --no-tags
(optional) create local branch and set upstream to origin/main
git checkout -B main origin/main
git branch --set-upstream-to=origin/main main
Notes:
- actions/checkout defaults to a single-commit shallow fetch; set fetch-depth: 0 to fetch full history and tags. [1]
- There are known problems (Git 2.50 / runner changes) where origin/HEAD may not be created automatically; the explicit git fetch above is a reliable workaround. [2]
Sources:
[1] actions/checkout README (v4) — checkout docs.
[2] GitHub issues/blog reports on origin/HEAD missing after Git 2.50 / runner updates.
🏁 Script executed:
#!/bin/bash
# Better test: Verify git merge-base behavior in realistic scenarios
cd /tmp/git-test-validation
rm -rf /tmp/git-test-validation
# Setup: Create a repo with realistic structure
mkdir -p /tmp/git-test-validation
cd /tmp/git-test-validation
# Initialize local repo
git init local-repo
cd local-repo
git config user.email "[email protected]"
git config user.name "Test"
# Create initial commit
echo "v1" > file.txt
git add file.txt
git commit -m "initial commit"
# Create main branch explicitly
git branch -M main
# Setup a "remote" (in same filesystem to simulate)
cd ..
git clone --bare local-repo origin-repo.git
# Now work in local repo with origin configured
cd local-repo
git remote add origin ../origin-repo.git
git push -u origin main
# Test 1: HEAD on main (typical case after checkout of main branch)
echo "=== Test 1: HEAD on main ==="
REF=$(git rev-parse HEAD)
if git merge-base --is-ancestor "$REF" origin/main 2>&1; then
echo "✓ PASS: SHA on main validated"
else
echo "✗ FAIL: SHA on main rejected"
fi
# Test 2: Branch name as ref
echo "=== Test 2: Branch name as ref ==="
git checkout -b feature-branch
echo "v2" > file.txt
git add file.txt
git commit -m "feature work"
if git merge-base --is-ancestor feature-branch origin/main 2>&1; then
echo "✓ PASS: Non-pushed local branch validated (unexpected - it's a descendant)"
else
echo "✗ FAIL: Non-pushed local branch rejected"
fi
# Test 3: Non-existent ref (error case)
echo "=== Test 3: Non-existent ref ==="
if git merge-base --is-ancestor "nonexistent-abc123" origin/main 2>&1; then
echo "✗ FAIL: Non-existent ref should be rejected"
else
echo "✓ PASS: Non-existent ref properly rejected"
fi
# Test 4: Tag name as ref
echo "=== Test 4: Tag as ref ==="
git tag v1.0.0 main
if git merge-base --is-ancestor v1.0.0 origin/main 2>&1; then
echo "✓ PASS: Tag on main validated"
else
echo "✗ FAIL: Tag on main rejected"
fi
# Test 5: Branch not ancestor of main
echo "=== Test 5: Branch not ancestor of main ==="
git checkout main
git checkout -b diverged
git revert --no-edit HEAD
git push origin diverged 2>/dev/null || true
if git merge-base --is-ancestor diverged origin/main 2>&1; then
echo "✗ FAIL: Non-ancestor branch should be rejected"
else
echo "✓ PASS: Non-ancestor branch properly rejected"
fiRepository: triggerdotdev/trigger.dev
Length of output: 1917
🏁 Script executed:
cat -n .github/workflows/release.yml | sed -n '164,206p'Repository: triggerdotdev/trigger.dev
Length of output: 1665
Add explicit git fetch before validating ref ancestry.
The validation at line 172 will fail because actions/checkout@v4 with fetch-depth: 0 does not automatically create the origin/main remote-tracking branch. This is a known issue with GitHub Actions runners (Git 2.50+). The command git merge-base --is-ancestor ${{ github.event.inputs.ref }} origin/main will fail with "fatal: Not a valid object name origin/main".
Add an explicit fetch step between checkout and validation:
- name: Validate ref is on main
run: |
git fetch origin main --no-tags
if ! git merge-base --is-ancestor ${{ github.event.inputs.ref }} origin/main; then
echo "Error: ref must be an ancestor of main (i.e., already merged)"
exit 1
fi🤖 Prompt for AI Agents
.github/workflows/release.yml around lines 170 to 175: the ancestry check uses
origin/main but the runner may not have the origin/main remote-tracking branch
available, causing "Not a valid object name origin/main"; fix by performing an
explicit git fetch of origin main (no tags) before running the merge-base check
so origin/main exists, then proceed with the existing git merge-base
--is-ancestor check and error/exit logic.
Adds a manual trigger to the
release.ymlworkflow for publishing prerelease versions. Needs to be in the same workflow file due to a NPM limitation on how OIDC claims are checked.Currently there is a validation step on the ref for the prerelease: it must be merged to the main branch. We can revisit this in the future in case we find it too limiting.