Skip to content

[codex] Include sync in core workflow defaults#1030

Merged
TabishB merged 3 commits into
mainfrom
codex/default-sync-workflow
May 1, 2026
Merged

[codex] Include sync in core workflow defaults#1030
TabishB merged 3 commits into
mainfrom
codex/default-sync-workflow

Conversation

@TabishB

@TabishB TabishB commented May 1, 2026

Copy link
Copy Markdown
Contributor

Summary

Adds sync to the default core workflow profile so new installs generate /opsx:sync skills and commands by default.

This also updates profile/init/update/config tests, user docs, and adds a changeset for the behavior change.

Existing Users

This PR does not silently mutate custom profiles.

  • Users on explicit core get sync the next time they run openspec update, because core resolves through CORE_WORKFLOWS.
  • Users on custom keep their configured workflow list.
  • If openspec update sees a custom workflow set matching the old core defaults (propose, explore, apply, archive), it prints a non-blocking note explaining that core now includes sync and tells users to run openspec config profile core followed by openspec update to opt in.

Validation

  • pnpm build
  • pnpm exec vitest run test/core/update.test.ts
  • pnpm lint
  • pnpm test
  • git diff --check

Summary by CodeRabbit

  • New Features

    • The sync workflow is now part of the default core profile; new installs include the /opsx:sync command.
    • The update command now suggests opting into the core preset and re-running update to add sync for users with prior custom profiles.
  • Documentation

    • All docs updated to show sync in the core workflow; sync removed from the expanded-only lists and quick-start workflow references adjusted.
  • Tests

    • Test suite expectations updated to treat sync as a core workflow step.

@coderabbitai

coderabbitai Bot commented May 1, 2026

Copy link
Copy Markdown
Contributor
📝 Walkthrough

Walkthrough

The PR makes /opsx:sync part of the default core profile by adding sync to the exported CORE_WORKFLOWS, updates update/migration logic to detect prior core-preserving custom profiles and suggest opting into the new core, and adjusts docs and tests accordingly.

Changes

Cohort / File(s) Summary
Core Profile Definition
src/core/profiles.ts
Added sync to the exported CORE_WORKFLOWS array (now includes propose, explore, apply, sync, archive).
Update Command Logic
src/core/update.ts
Detects when a custom profile exactly matches the old core workflows and logs guidance suggesting switching to the updated core profile to adopt sync (no automatic mutation).
Documentation
README.md, docs/cli.md, docs/commands.md, docs/getting-started.md, docs/migration-guide.md, docs/opsx.md, docs/supported-tools.md, docs/workflows.md
Replaced occurrences of the old core workflow list with one that includes sync; moved /opsx:sync from expanded-only tables into the default core profile documentation and removed duplication.
Changelog / Release
.changeset/sync-default-core.md
Adds a changeset noting a minor version bump and that /opsx:sync is included in the default core profile.
Tests — Core & Init
test/core/profiles.test.ts, test/core/init.test.ts, test/core/update.test.ts
Updated expectations to include sync in core-generated artifacts; added/adjusted tests verifying update guidance when custom profiles match the old core set.
Tests — Config & Profiles
test/commands/config.test.ts, test/commands/config-profile.test.ts, test/core/profile-sync-drift.test.ts
Adjusted interactive and derivation tests to treat sync as core; renamed/updated test helpers and fixtures to reflect new workflow identifiers.

Sequence Diagram(s)

(Skipped — changes are code/docs/tests around workflow membership and migration guidance; no new multi-component control flow requiring a sequence diagram.)

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Possibly related PRs

Poem

🐇 I hopped through code with a cheerful clack,
Now sync is in core — no turning back.
Five steps dancing, tidy and bright,
Docs and tests aligned just right.
A carrot for CI, and a twinkle of light.

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately reflects the main change: adding the sync workflow to the core profile defaults, which is the primary objective across code, documentation, and tests.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch codex/default-sync-workflow

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.

❤️ Share
Review rate limit: 7/8 reviews remaining, refill in 7 minutes and 30 seconds.

Comment @coderabbitai help to get the list of available commands and usage tips.

@TabishB TabishB marked this pull request as ready for review May 1, 2026 12:29

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

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 (1)
test/core/update.test.ts (1)

1430-1463: ⚡ Quick win

Add an explicit “no config mutation” assertion in this new scenario.

This test already verifies messaging/artifacts well; adding a direct check that saveGlobalConfig is not called would lock in the non-mutating contract from the PR objective.

✅ Small test hardening
   it('should suggest core preset when custom profile preserves the old core workflow set', async () => {
+    const { saveGlobalConfig } = await import('../../src/core/global-config.js');
     setMockConfig({
       featureFlags: {},
       profile: 'custom',
       delivery: 'both',
       workflows: ['propose', 'explore', 'apply', 'archive'],
@@
       path.join(testDir, '.claude', 'commands', 'opsx', 'sync.md')
     )).toBe(false);

+    expect(saveGlobalConfig).not.toHaveBeenCalled();
+
     consoleSpy.mockRestore();
   });
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@test/core/update.test.ts` around lines 1430 - 1463, Add an explicit assertion
that ConfigUtils.saveGlobalConfig is not called in this test: before calling
updateCommand.execute(testDir) spy on ConfigUtils.saveGlobalConfig (e.g., const
saveSpy = vi.spyOn(ConfigUtils,
'saveGlobalConfig').mockResolvedValue(undefined)), run
updateCommand.execute(...), then assert expect(saveSpy).not.toHaveBeenCalled();
finally restore the spy (saveSpy.mockRestore()) alongside
consoleSpy.mockRestore(); place these lines in the same test that uses
InitCommand and updateCommand so the non-mutating contract is enforced.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@docs/migration-guide.md`:
- Line 11: Update the command listings so the “default core” and “expanded
workflow” sections are consistent: ensure the default core includes
/opsx:propose, /opsx:apply, /opsx:sync, /opsx:archive and also include
/opsx:explore (which was omitted), and make the expanded/optional list reflect
only additional commands beyond those core ones; search for occurrences of
/openspec:proposal, /openspec:apply, /openspec:archive and /opsx:propose,
/opsx:apply, /opsx:sync, /opsx:archive, /opsx:explore (including the other
occurrence mentioned in the comment) and replace or reconcile them so every
command table and sentence consistently shows sync in core and explore included
where appropriate.

---

Nitpick comments:
In `@test/core/update.test.ts`:
- Around line 1430-1463: Add an explicit assertion that
ConfigUtils.saveGlobalConfig is not called in this test: before calling
updateCommand.execute(testDir) spy on ConfigUtils.saveGlobalConfig (e.g., const
saveSpy = vi.spyOn(ConfigUtils,
'saveGlobalConfig').mockResolvedValue(undefined)), run
updateCommand.execute(...), then assert expect(saveSpy).not.toHaveBeenCalled();
finally restore the spy (saveSpy.mockRestore()) alongside
consoleSpy.mockRestore(); place these lines in the same test that uses
InitCommand and updateCommand so the non-mutating contract is enforced.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 326a0c34-bc6c-4b18-b40c-883ab2450ab2

📥 Commits

Reviewing files that changed from the base of the PR and between 347f027 and aad1f7c.

📒 Files selected for processing (16)
  • .changeset/sync-default-core.md
  • README.md
  • docs/cli.md
  • docs/commands.md
  • docs/getting-started.md
  • docs/migration-guide.md
  • docs/opsx.md
  • docs/supported-tools.md
  • src/core/profiles.ts
  • src/core/update.ts
  • test/commands/config-profile.test.ts
  • test/commands/config.test.ts
  • test/core/init.test.ts
  • test/core/profile-sync-drift.test.ts
  • test/core/profiles.test.ts
  • test/core/update.test.ts

Comment thread docs/migration-guide.md
| Aspect | Legacy | OPSX |
|--------|--------|------|
| **Commands** | `/openspec:proposal`, `/openspec:apply`, `/openspec:archive` | Default: `/opsx:propose`, `/opsx:apply`, `/opsx:archive` (expanded workflow commands optional) |
| **Commands** | `/openspec:proposal`, `/openspec:apply`, `/openspec:archive` | Default: `/opsx:propose`, `/opsx:apply`, `/opsx:sync`, `/opsx:archive` (expanded workflow commands optional) |

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Core command listings are now inconsistent within this doc.

After moving sync into default core, some command lists still reflect the old split (and Line 11 omits explore). Please align all “default core” and “expanded” sections in this file to avoid user confusion.

📝 Suggested doc alignment
-| **Commands** | `/openspec:proposal`, `/openspec:apply`, `/openspec:archive` | Default: `/opsx:propose`, `/opsx:apply`, `/opsx:sync`, `/opsx:archive` (expanded workflow commands optional) |
+| **Commands** | `/openspec:proposal`, `/openspec:apply`, `/openspec:archive` | Default: `/opsx:propose`, `/opsx:explore`, `/opsx:apply`, `/opsx:sync`, `/opsx:archive` (expanded workflow commands optional) |
 **Default (`core` profile):**
 | Command | Purpose |
 |---------|---------|
 | `/opsx:propose` | Create a change and generate planning artifacts in one step |
 | `/opsx:explore` | Think through ideas with no structure |
 | `/opsx:apply` | Implement tasks from tasks.md |
+| `/opsx:sync` | Preview/spec-merge without archiving |
 | `/opsx:archive` | Finalize and archive the change |

 **Expanded workflow (custom selection):**
 ...
-| `/opsx:sync` | Preview/spec-merge without archiving |

Also applies to: 87-87

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@docs/migration-guide.md` at line 11, Update the command listings so the
“default core” and “expanded workflow” sections are consistent: ensure the
default core includes /opsx:propose, /opsx:apply, /opsx:sync, /opsx:archive and
also include /opsx:explore (which was omitted), and make the expanded/optional
list reflect only additional commands beyond those core ones; search for
occurrences of /openspec:proposal, /openspec:apply, /openspec:archive and
/opsx:propose, /opsx:apply, /opsx:sync, /opsx:archive, /opsx:explore (including
the other occurrence mentioned in the comment) and replace or reconcile them so
every command table and sentence consistently shows sync in core and explore
included where appropriate.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
docs/workflows.md (1)

444-444: ⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Update the profile designation for /opsx:sync in the reference table.

The "When to Use" column currently says "Expanded mode, optional" for /opsx:sync, but this is now inconsistent with the changes in this PR. Since sync is now part of the default core profile (as documented in lines 36-40), the reference table should reflect this.

📝 Suggested update
-| `/opsx:sync` | Merge delta specs | Expanded mode, optional |
+| `/opsx:sync` | Merge delta specs | Core profile, optional |

Or simply:

-| `/opsx:sync` | Merge delta specs | Expanded mode, optional |
+| `/opsx:sync` | Merge delta specs | Optional (archive prompts if needed) |
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@docs/workflows.md` at line 444, Update the reference table entry for
`/opsx:sync` to reflect that sync is now part of the default core profile:
replace the "When to Use" text "Expanded mode, optional" with wording that
indicates it belongs to the core profile (e.g., "core profile (default)") so the
table matches the PR's documentation changes; look for the table row containing
the symbol `/opsx:sync` in the workflows reference and update that cell
accordingly.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Outside diff comments:
In `@docs/workflows.md`:
- Line 444: Update the reference table entry for `/opsx:sync` to reflect that
sync is now part of the default core profile: replace the "When to Use" text
"Expanded mode, optional" with wording that indicates it belongs to the core
profile (e.g., "core profile (default)") so the table matches the PR's
documentation changes; look for the table row containing the symbol `/opsx:sync`
in the workflows reference and update that cell accordingly.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 3afe425f-9312-4002-8cb0-c562c8c81034

📥 Commits

Reviewing files that changed from the base of the PR and between aad1f7c and b822af5.

📒 Files selected for processing (1)
  • docs/workflows.md

@alfred-openspec alfred-openspec left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approved. Checks are green and the core-profile sync default update looks scoped to profiles, update messaging, docs, tests, and changeset.

@TabishB TabishB added this pull request to the merge queue May 1, 2026
Merged via the queue into main with commit 485c97e May 1, 2026
12 checks passed
@TabishB TabishB deleted the codex/default-sync-workflow branch May 1, 2026 14:22
kaze-droid pushed a commit to kaze-droid/OpenSpec that referenced this pull request May 10, 2026
* Include sync in core workflow defaults

* Add old core custom profile sync hint

* Update workflows sync default docs
kaze-droid pushed a commit to kaze-droid/OpenSpec that referenced this pull request May 11, 2026
* Include sync in core workflow defaults

* Add old core custom profile sync hint

* Update workflows sync default docs
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants