feat: automated weekly release workflow with security hardening and promotion fix - W-23900552 - #7995
Merged
Merged
Conversation
- Add new workflow to build releases directly from promoted prerelease tags - Eliminates need for release branches - Auto-detects latest nightly tag or accepts manual input - Auto-calculates version (minor bump) or accepts override - Creates GitHub pre-release with testing checklist - Deprecate old createReleaseBranch workflow (disabled Monday cron) - Update documentation for new workflow This implements the ultra-minimal release workflow: 1. Build from Wednesday's promoted prerelease 2. Test VSIXs from GitHub pre-release 3. Publish exact same VSIXs to marketplace (zero rebuild risk) Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Simplifies buildReleaseFromPrerelease.yml and publishVSCode.yml by extracting bash logic into testable Node.js scripts and eliminating unnecessary jobs. Changes: - Extract version calculation into scripts/calculate-release-version.js - Extract package updates into scripts/update-release-versions.js - Remove build-extension-list job from publishVSCode.yml - Extract extensions directly from release assets in CBW trigger - Remove RELEASE_WORKFLOW_CHANGES.md (implementation notes) - Update documentation to reflect simplified workflows Benefits: - 76 fewer workflow lines (-25% buildReleaseFromPrerelease, -10% publishVSCode) - Version logic is now unit testable - No checkout/npm setup needed for extension discovery - Scripts are reusable across workflows Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
The buildReleaseFromPrerelease workflow checks out an old prerelease tag that doesn't contain the new scripts. Copy scripts to temp before checkout, then restore them after. This allows the workflow to use the latest script versions even when building from old prerelease tags. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
The buildReleaseFromPrerelease workflow updates package versions on an old prerelease tag. Running npm install tries to resolve the new versions (which don't exist yet), causing dependency resolution errors. Skip lockfile update since we're building from existing code with bumped versions. The lockfile will be updated when the version is committed back to main after marketplace publish. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
The update-release-versions script was finding ALL package.json files including those in node_modules subdirectories, incorrectly updating dependency versions (e.g., @opentelemetry/[email protected]). Add -not -path "*/node_modules/*" to find command to only update top-level packages in packages/ directory. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
The generate-sha256.js script expects VSIXs in ./extensions/, but vscode:package leaves them in individual package directories. Added step to collect all VSIXs into ./extensions/ before SHA256 generation, matching the pattern used in tagAndRelease.yml. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
The workflow needs to run concatenate-sha256.js to create SHA256.md from the raw SHA256 file, and reference the file at the root (not in packages/salesforcedx-vscode/), matching the tagAndRelease.yml flow. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Handle retry scenarios where the release was partially created but failed during asset upload. Delete and recreate to ensure a clean state. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Changed approach to create the release first, then upload assets individually. This is more robust and handles partial failures better. Also added aggressive cleanup of any existing release/tag to handle retry scenarios. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Security Fixes: - Command injection prevention with strict regex validation - VSIX validation ensuring builds produce files before release - Script integrity SHA256 checksum verification - Integer overflow protection max 9999 per version component Workflow Fixes: - Fix npm install ordering moved to AFTER version updates - Fix release deletion race condition with 20s timeout - Fix promote-prerelease.yml concurrency deadlock - Added Monday 8 AM UTC cron for automated weekly releases Documentation Updates: - Updated release workflow for Wed prerelease to Mon stable - Updated publishing.md with complete release timeline - Updated SKILL.md to use new buildReleaseFromPrerelease Error Handling: - Enhanced error messages in update-release-versions.js - Always update package-lock.json for dependency integrity - Better validation throughout scripts Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Adds capabilities to match Platform CLI Release Guide for emergency response: New Workflows: - create-patch-release-branch.yml: Creates release-base/vX.Y.x branches from tags - build-patch-release.yml: Tags and builds patch releases with auto version increment Enhanced buildReleaseFromPrerelease.yml: - Added startFromRef input to accept any git ref (tag/branch/SHA) - Detection priority: startFromRef → prereleaseTag → auto-detect nightly - Enables emergency builds from hotfix branches, specific commits, or old tags Documentation: - contributing/publishing.md: Emergency patch workflow + flexible ref examples - .github/workflows/NIGHTLY-BUILDS.md: Quick reference for new capabilities - .claude/skills/release/SKILL.md: CLI-ready emergency release commands Use Cases: 1. Patch marketplace release: v67.12.0 → v67.12.1 2. Build from hotfix branch before tagging 3. Build from specific commit SHA for emergency fix 4. Iterative development on release-base branches Cherry-pick guidance auto-generated in release notes to ensure fixes reach develop. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
1. Checksum verification path mismatch (buildReleaseFromPrerelease.yml) - Generate checksums from scripts/ dir to match verification path - Prevents always-fail integrity check 2. Version overflow after increment (calculate-release-version.js) - Add post-increment validation for newMinor > 9999 - Prevents v67.9999.0 → v67.10000.0 overflow 3. Missing VSIX validation (publishVSCode.yml) - Validate at least one VSIX exists in release before extraction - Prevents empty extensions being dispatched to CBW 4. Release deletion without ownership check (buildReleaseFromPrerelease.yml) - Check release body for workflow marker before deletion - Prevents destroying manual emergency releases 5. Uncaught JSON.parse exception (update-release-versions.js) - Wrap JSON.parse in try-catch - Skip malformed files, continue with valid ones - Report errors without aborting entire script Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
1. Validate latest tag is stable release before patch extraction - Reject prerelease tags (v67.12.0-beta.1) with clear error - Add extraction validation to catch sed failures 2. Use PREV_TAG from calculate-version output instead of deriving from VERSION - Prevents fragile dependency on sed selecting 2nd tag - More reliable for git log range 3. Add warning to startFromRef description about bypassing validation - Documents that it bypasses nightly tag validation - Reminds users to verify ref is reviewed/merged 4. Batch VSIX uploads instead of sequential loop - Replace for-loop with single gh release upload command - Applies to both buildReleaseFromPrerelease.yml and build-patch-release.yml - Reduces API overhead by ~30s for 10+ extensions 5. Use update-release-versions.js script instead of inline jq - Replace 14-line inline bash loop with single script call - Ensures consistent versioning logic across workflows 6. Add comment about release deletion marker fragility - Documents that text matching is fragile - Suggests future improvement: use GitHub labels/metadata 7. Add TODO for package versioning criteria duplication - Flag for future extraction to shared module 8. Add TODO for VSIX collection duplication - Flag for future composite action extraction Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Change promote-prerelease workflow to run daily (6 AM UTC) and promote last night's nightly build immediately after E2E tests pass, rather than waiting 7 days. This enables faster iteration - if issues arise, we can patch pre-release and push fixes quickly. Changes: - Schedule: Wed 7 AM UTC to Daily 6 AM UTC (2h after nightly at 4 AM) - min-tag-age-days: 7 to 0 (promotes newest eligible nightly) - Updated docs to reflect new promotion cadence Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Address all implementation gaps identified in PR-7995-WORKFLOW-SCENARIOS.md: - Monday source selection uses marketplace-prerelease-* tracking tags - Tag creation explicitly targets commit with --target flag - Isolated branch materialization for emergency builds - Prerelease-to-stable detection via IS_PRERELEASE output - Patch branches auto-copy version helper scripts from develop - Patch tag discovery filters stable tags before sorting - Version validators accept prerelease formats (67.12.0-beta.1) - Comprehensive rollback documentation added - Backport instructions filter out version-bump commits - Upstream gate-check configuration documented - All documentation updated to reflect changes Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Change promote-prerelease schedule: - Wed 7 AM UTC (not daily 6 AM) - min-tag-age-days: 0 (promotes latest nightly, not 7-day-old) - 5-day prerelease baking period (Wed to Mon) Rationale: Wednesday morning nightly gets promoted immediately, then 5-day testing period before Monday stable build. Manual override available if longer wait needed. Updated all documentation to reflect new schedule. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Update final doc references from daily 6 AM to Wed 7 AM UTC: - .claude/skills/release/SKILL.md - .github/workflows/TODO-UPSTREAM-GATE-CHECK.md Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
TEMPORARY WORKAROUND - DO NOT MERGE TO MAIN Creates dummy CI Complete check to satisfy promote-prerelease quality gate. ci-testing lacks this check, blocking promotion. Drop this commit before pushing to salesforcedx-vscode. See .github/workflows/TODO-UPSTREAM-GATE-CHECK.md for proper fix. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Documents commit 1419966 (CI Complete dummy) that must be dropped before pushing to salesforcedx-vscode main repo. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Change trigger from develop-only to all pushes/PRs so the check exists for all commits, including nightly builds. Still temporary - drop before merging to main. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
* fix: sort sObject field decls by name - W-23573457 * ci-repair: W-23573457
) * ci: approve PRs on /ai-auto approve via svc-idee-bot - W-24030619 PR author on @forcedotcom/ide-experience comments exactly `/ai-auto approve`. Node gates check author, team, open/non-draft, green CI, then APPROVE as svc-idee-bot on the current head (IDEE_GH_TOKEN). pre-commit compile already fails on origin/develop (SDR standardValueSet). * ci: approve PRs on /ai-auto approve via svc-idee-bot - W-24030619 PR author on @forcedotcom/ide-experience comments exactly `/ai-auto approve`. Node gates check author, team, open/non-draft, green CI, then APPROVE as svc-idee-bot on the current head (IDEE_GH_TOKEN). * ci: restrict auto-approve workflow token - W-24030619
* feat(soql): migrate From selection to Lit * fix(soql): address From selection review feedback - W-23928681 * refactor(soql): adopt Lit decorators - W-23928681
…-24017196 (#8078) * fix(services): redact sf command arguments in telemetry - W-24017196 * fix(services): omit commands from terminal telemetry - W-24017196 * test(metadata): identify terminal spans by parent - W-24017196 * chore: update jsforce dependencies * chore: update jsforce dependencies
…40 (#8088) * fix(services): persist later web memfs writes to IndexedDB - W-24062740 Hung IDB write after request.onsuccess blocked the serial watcher. Later files never reached IDB. * test(services): cover IDB settle timeout abort and persist isolation - W-24062740 Timeout abort unblocks the next write. A persist error does not skip the following updateIDB. * test(services): drop IDBTransaction this from settleIdbTransaction fakes - W-24062740
Updated the changelog to reflect new features, fixes, and under-the-hood changes for version 67.17.2.
Co-Authored-By: GitHub Actions <[email protected]>
…e-pr] (#8096) Add property "versionedIndependently": true to pjson Reset version to 9.0.7 Set pjson property "private": true to exclude from npm publish
Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Addresses PR review comment to use DRY principle by using the existing .github/actions/gitConfig action instead of duplicating git config commands. Fixes: #7995 (comment) Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
…testing Previously: - Wed 7 AM: promote-nightly-to-prerelease (creates new marketplace prerelease) - Wed 8 AM: build-release (would pick the JUST-CREATED prerelease from 1 hour ago) Problem: build-release would use a prerelease that was only on marketplace for 1 hour, not the intended 7+ days of customer testing. Now: - Wed 7 AM: build-release (builds stable from LAST week's marketplace prerelease) - Wed 8 AM: promote-nightly-to-prerelease (promotes THIS week's nightly) This ensures stable releases are built from marketplace prereleases that have been tested by customers for 7+ days, as intended. Fixes: #7995 (comment) Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
The old workflow (createReleaseBranch.yml) is deprecated and no longer in use. No need to document what doesn't exist anymore. - Removed 'Old Workflow' section (lines 5-126) - Changed title from 'Before & After' to just 'Release Workflow Architecture' - Changed 'NEW WORKFLOW' to 'RELEASE WORKFLOW' in diagram Fixes: #7995 (comment) Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Resolved conflicts by accepting develop's changes for: - All package.json files (version updates) - package-lock.json - soql-builder-ui component files Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
The fix for monorepo GitHub release creation has been merged to main: salesforcecli/github-workflows#181 Updating from test branch @ms/fix-monorepo-github-release to @main. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
mshanemc
reviewed
Sep 3, 2026
| - name: Build VSIXs | ||
| run: npm run vscode:package | ||
|
|
||
| - name: Collect VSIXs |
Contributor
There was a problem hiding this comment.
you made a composite action for this, right?
Contributor
Author
There was a problem hiding this comment.
used it with a small caveat
Contributor
Author
There was a problem hiding this comment.
Decided it makes sense to just keep it in a shared workflow repo salesforcecli/github-workflows#182 once that is merged we can update this and use it across the repo.
Contributor
There was a problem hiding this comment.
it's merged. You're approved to merge this once that change goes in
mshanemc
reviewed
Sep 3, 2026
| ## Build Release from Prerelease | ||
|
|
||
| Scheduled [Github Action](https://github.com/forcedotcom/salesforcedx-vscode/actions/workflows/createReleaseBranch.yml) creates release branch from `develop` Mondays 1PM GMT. Format: `release/vXX.YY.ZZ`. | ||
| Manual workflow [`buildReleaseFromPrerelease.yml`](https://github.com/forcedotcom/salesforcedx-vscode/actions/workflows/buildReleaseFromPrerelease.yml) builds release VSIXs from promoted prerelease tags for internal testing. Auto-detects latest nightly tag and bumps minor version, or accepts manual overrides. |
Contributor
There was a problem hiding this comment.
This file was renamed to build-release.yml. Same stale name at L100 and L210.
promote-prerelease.yml at L87 is now promote-nightly-to-prerelease.yml.
Replaces inline VSIX collection logic with the shared collect-vsix action to match repo convention and the patch-branch workflow. Added a comment noting it may fail when building from historical refs that predate the action (2026-08-26), since local actions resolve from the checked-out tree. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
Updated renamed workflow references: - buildReleaseFromPrerelease.yml → build-release.yml (lines 24, 100, 210) - promote-prerelease.yml → promote-nightly-to-prerelease.yml (line 87 + CI-TESTING-PLAN) Fixes: #7995 (comment) Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
mshanemc
approved these changes
Sep 3, 2026
The collect-vsix action was merged into salesforcecli/github-workflows (PR #182). Switch both build-release.yml and build-and-release-patch-branch.yml to the remote @main reference and delete the local copy. Using the remote reference also fixes the historical-ref edge case in build-release.yml: remote actions are fetched from the pinned repo/ref regardless of what $SOURCE_REF is checked out, so builds from older tags no longer fail on VSIX collection. Co-Authored-By: Claude Sonnet 4.5 <[email protected]>
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
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
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.
Summary
Replaces manual release branch workflow with automated prerelease-to-stable promotion, adds comprehensive security fixes, resolves critical concurrency deadlock, and adds emergency response capabilities with two-step pre-release workflow.
@W-23900552@
What Changed
New Automated Release Workflow
build-release.yml(renamed frombuildReleaseFromPrerelease.yml) with Monday 8 AM UTC cron schedulestartFromRefinputpublishAsPrerelease: trueflag for hotfixes without version bumpingcreateReleaseBranch.ymlMonday cronEmergency Pre-release Workflow (NEW - Two-Step Process)
Step 1: Build VSIXs
build-release.ymlwithpublishAsPrerelease: true- builds from any git ref without version bumpingv67.13.7-nightly.develop.20260821)Step 2: Publish to Marketplace
promote-prerelease.ymlwithreleaseTaginput - publishes specific release to marketplace as pre-releasereleaseTagparameter added to upstream workflow (PR pending)Emergency Patch Release Workflows (Stable Releases)
create-patch-release-branch.yml: Creates release-base/vX.Y.x branches from existing tags for iterative patchingbuild-patch-release.yml: Tags and builds patch releases with auto version incrementSecurity & Robustness Fixes (7 total)
prereleaseTaginput prevents malicious payloadsFixed Pre-release Promotion Workflow
promote-prerelease.ymlDocumentation Updates
.claude/skills/release/SKILL.md) for new automation + emergency workflowscontributing/publishing.md) with Wed → Mon flow + emergency pre-release instructions.github/workflows/NIGHTLY-BUILDS.mdwith emergency release examplesNew Weekly Automation Flow
promote-prerelease.ymlpublishes latest nightly to marketplace as pre-releasebuild-release.ymlbuilds stable release from Wed pre-releaseEmergency Response Capabilities (NEW)
Use Case 1: Emergency Pre-release (Hotfix → Marketplace in ~5 min)
Use Case 2: Patch Current Marketplace Stable Release
Use Case 3: Build Stable from Specific Commit
# Emergency stable release from specific commit SHA gh workflow run build-release.yml \ -f startFromRef=abc123def \ -f releaseVersion=67.13.1Use Case 4: Rollback to Previous Version
# Re-publish older version to marketplace gh workflow run publishVSCode.yml -f version=67.11.0Benefits
Testing
versionnotreleaseVersion)releaseTaginput (feat: add release-tag input to support emergency pre-release publishing W-23900552 salesforcecli/github-workflows#173)Rollout Plan
createReleaseBranch.ymlFiles Changed
New Files:
.github/workflows/build-release.yml(renamed from buildReleaseFromPrerelease.yml, enhanced with emergency pre-release mode).github/workflows/create-patch-release-branch.yml(120 lines).github/workflows/build-patch-release.yml(267 lines)scripts/calculate-release-version.js(64 lines)scripts/update-release-versions.js(79 lines)Modified Files:
.github/workflows/promote-prerelease.yml(concurrency fix, min-tag-age-days default: 7→0, added releaseTag input).github/workflows/createReleaseBranch.yml(deprecated, cron disabled).github/workflows/publishVSCode.yml(verify-release job refactor, parameter name fixes).claude/skills/release/SKILL.md(updated for new workflow + emergency pre-releases)contributing/publishing.md(documented new flow + emergency pre-releases).github/workflows/NIGHTLY-BUILDS.md(updated schedule info + emergency examples)Key Changes from Initial Implementation
buildReleaseFromPrerelease.yml→build-release.ymlfor claritypublishAsPrereleaseflag to enable pre-release builds without version bumpingrelease-taginput to upstream vscode-promote-prerelease.yml workflow (PR pending)