npx skills add ...
npx skills add jezweb/claude-skills --skill fork-discipline
Audit and enforce the core/client boundary in multi-client projects. Detects where shared platform code is tangled with client-specific code, finds hardcoded client checks, config files that replace instead of merge, scattered client code, migration conflicts, and missing extension points. Produces a boundary map, violation report, and refactoring plan. Optionally generates FORK.md documentation and restructuring scripts. Triggers: 'fork discipline', 'check the boundary', 'is this core or client', 'platform audit', 'client separation', 'fork test', 'refactor for multi-client', 'clean up the fork'.
npx skills add jezweb/claude-skills --skill fork-discipline
Audit the core/client boundary in multi-client codebases. Every multi-client project should have a clean separation between shared platform code (core) and per-deployment code (client). This skill finds where that boundary is blurred and shows you how to fix it.
The fork test: Before modifying any file, ask "is this core or client?" If you can't tell, the boundary isn't clean enough.
if (client === 'acme') checks creeping into shared code| Mode | Trigger | What it produces |
|---|---|---|
| audit | "fork discipline", "check the boundary" | Boundary map + violation report |
| document | "write FORK.md", "document the boundary" | FORK.md file for the project |
| refactor | "clean up the fork", "enforce the boundary" | Refactoring plan + migration scripts |
Default: audit
Determine if this is a multi-client project and what pattern it uses:
| Signal | Pattern |
|---|---|
clients/ or tenants/ directory | Explicit multi-client |
| Multiple config files with client names | Config-driven multi-client |
packages/ with shared + per-client packages | Monorepo multi-client |
Environment variables like CLIENT_NAME or TENANT_ID | Runtime multi-client |
| Only one deployment, no client dirs | Single-client (may be heading multi-client) |
If single-client: check if the project CLAUDE.md or codebase suggests it will become multi-client. If so, audit for readiness. If genuinely single-client forever, this skill isn't needed.
Build a boundary map by scanning the codebase:
Scan for these specific anti-patterns:
Severity: High. Every hardcoded client check in core code means the next client requires modifying shared code.
Check if client configs replace entire files or merge over defaults:
Look for: client config files that are suspiciously large (close to the size of the defaults file), or client configs that define fields the defaults already handle.
Severity: Medium. Stale client configs miss new defaults and features.
Check if client-specific code lives outside the client directory:
Severity: High. Client code in src/ means core is not truly shared.
Check if core has mechanisms for client customisation without modification:
| Extension point | How to check | What it enables |
|---|---|---|
| Config merge | Does config/ have a merge function? | Client overrides without replacing |
| Dynamic imports | Does core look for clients/{name}/custom/? | Client-specific routes/pages |
| Feature flags | Are features toggled by config, not code? | Enable/disable per client |
| Theme tokens | Are colours/styles in variables, not hardcoded? | Visual customisation |
| Content injection | Can clients provide seed data, templates? | Per-client content |
| Hook/event system | Can clients extend behaviour without patching? | Custom business logic |
Severity: Medium. Missing extension points force client code into core.
Severity: Low until it causes a conflict, then Critical.
Search for patterns where behaviour branches on client identity instead of configuration.
Write to .jez/artifacts/fork-discipline-audit.md:
Generate a FORK.md for the project root that documents the boundary:
After an audit, generate the concrete steps to enforce the boundary:
For each violation where client code lives in src/:
For each if (client === ...) in core:
If the project replaces configs instead of merging:
If clients need custom routes but currently modify core:
Write a script to .jez/scripts/fork-refactor.sh that:
| Client count | What to do |
|---|---|
| 1 | Don't refactor. Just document the boundary (FORK.md) so you know where it is. |
| 2 | Run the audit. Fix high-severity violations. Start the config merge pattern. |
| 3+ | Full refactor mode. The boundary must be clean — you now have proof of what varies. |
Rule 5 from the discipline: Don't abstract until client #3. With 1 client you're guessing. With 2 you're pattern-matching. With 3+ you know what actually varies.
if (client) even with one client. "This is mostly the same except..." = feature flag, not fork.