Changelog
All notable changes to Soleur.
v3.91.1 — 2026-05-14
- feat(content): auto-generate article 2026-05-14
v3.91.0 — 2026-05-14
Web Platform
feat(auth):NEXT_PUBLIC_DEV_EXTRA_ORIGINSmulti-port CSRF allowlist (dev-mode only). Production behavior unchanged.feat(chat):export type StreamEventfromchat-state-machine.ts(folds #2224 line item).feat(e2e):cc-soleur-go-ws-injector.tsPlaywrightrouteWebSockethelper with typedsend/sendControlchannels and ownedpageErrors.feat(e2e):cc-soleur-go-bubbles.e2e.ts— 6 Playwright tests for the 4 cc-soleur-go bubbles. Covers BOTH chip-removal triggers (stream_endANDworkflow_started).refactor(e2e): extract sharedsupabase-mockshelper; dedupstart-fresh-onboardingandstart-fresh-conversations-railagainst it (-184 / +60 lines net).chore(config): widenplaywright.config.tstestMatchto array to admitcc-soleur-go-*.e2e.tsto theauthenticatedproject.
Plugin (skills)
routeplan/SKILL.mdSharp Edges: 1 bullet on plan-prescribed runtime shape verification (library method names against installed types, DOM conditional renders,testMatchglob coverage).routereview/SKILL.mdSharp Edges: 1 paragraph on directory-scoped reading ofcross-cutting-refactorcriterion.
v3.90.1 — 2026-05-14
- Replace
eyJhbGciOiJIUzI1NiJ9.eyJzdW...(entropy 5.2) with low-entropyeyJ<17 a's>.<17 a's>.<17 a's>form inplugins/soleur/skills/incident/test/fixtures/positive-corpus.md. Still triggers the sentinel's JWT regex (eyJ[A-Za-z0-9_-]{10,}\.[A-Za-z0-9_-]{10,}\.[A-Za-z0-9_-]{10,}) but bypasses gitleaks default-packjwtregex (ey[A-Za-z0-9_-]{17,}\.ey[A-Za-z0-9_-]{17,}...— segment 2 starts withanoteynow).
v3.90.0 — 2026-05-14
Plugin
- New skill:
plugins/soleur/skills/incident/— 9 phases (Phase 0 fact capture → Phase 8 compound-capture handoff). Operator-invoked via/soleur:incidentor/soleur:go "production is down". - Redaction sentinel (
scripts/redact-sentinel.sh, 14 regex classes): JWT, email, UUID, Stripe (sk_/pk_/rk_/whsec_/acct_/cus_/pi_/seti_/sub_/in_), IPv4, env-var, GitHub PAT (ghp_/github_pat_), Anthropic, OpenAI, Supabase (sbp_/sb_secret_/sb_publishable_), PEM private-key headers. Meta-redacted offset output. Exit codes 0/1/2. - Pre-write gate — sentinel runs BEFORE Phase 7 inline-emit AND before disk commit. Transcripts are write boundaries.
- GDPR Art. 33/34 parity blocking (Phase 2) — both acks required when
risk_to_subjects: high; only Art. 33 ack when lower-risk. - Literal
COMMIT-PIRtoken at Phase 7 — case-sensitive equality after\r+ whitespace canonicalization (agent-user parity). Free-form yes is rejected. --dry-runmode — wraps the skill with captured output for greppable ACs (AC8-AC13)./soleur:gointent extension — newincidentrouting row inserted at line 50 (betweenreviewanddefault).- Inspiration: clean-room derivation from alirezarezvani/claude-skills/engineering-team/incident-commander; MIT NOTICE attribution.
Tests
plugins/soleur/skills/incident/test/redact-sentinel.test.sh— 19 tests (negative-baseline + 14 regex-class triggers + invalid-arg + output-format).- 1053 plugin compliance tests pass (after
SKILL_DESCRIPTION_WORD_BUDGETbump 1800 → 1850 for the new skill).
Documentation
- Spec + brainstorm
[Updated 2026-05-13]markers for D1-reversal reciprocal updates. - Cross-reference header in canonical PIR (
runbooks/dashboard-error-postmortem.md) pointing future PIR scaffolding at/soleur:incident.
v3.89.4 — 2026-05-14
- feat(legal): DPD §(m) operational telemetry & breach detection user-facing entry
web-v0.85.0 — 2026-05-14
Web Platform
feat(auth):NEXT_PUBLIC_DEV_EXTRA_ORIGINSmulti-port CSRF allowlist (dev-mode only). Production behavior unchanged.feat(chat):export type StreamEventfromchat-state-machine.ts(folds #2224 line item).feat(e2e):cc-soleur-go-ws-injector.tsPlaywrightrouteWebSockethelper with typedsend/sendControlchannels and ownedpageErrors.feat(e2e):cc-soleur-go-bubbles.e2e.ts— 6 Playwright tests for the 4 cc-soleur-go bubbles. Covers BOTH chip-removal triggers (stream_endANDworkflow_started).refactor(e2e): extract sharedsupabase-mockshelper; dedupstart-fresh-onboardingandstart-fresh-conversations-railagainst it (-184 / +60 lines net).chore(config): widenplaywright.config.tstestMatchto array to admitcc-soleur-go-*.e2e.tsto theauthenticatedproject.
Plugin (skills)
routeplan/SKILL.mdSharp Edges: 1 bullet on plan-prescribed runtime shape verification (library method names against installed types, DOM conditional renders,testMatchglob coverage).routereview/SKILL.mdSharp Edges: 1 paragraph on directory-scoped reading ofcross-cutting-refactorcriterion.
v3.89.3 — 2026-05-13
- feat(agents): hr-no-dashboard-eyeball-pull-data-yourself
v3.89.2 — 2026-05-13
Plugin (D1 vocabulary canonicalization)
- Frontmatter key:
brand_threshold:(1 file),brand_survival:(5 files), semanticthreshold:(4 files) →brand_survival_threshold: - Value-form:
single-user-incident(50 files) →single-user incident(canonical space form) - 6 learning files preserve hyphenated tag-array entries (KB slug convention)
- 2 protected files preserve
threshold:for orthogonal semantics:- preflight Check 6 scope-out sentinel (
threshold: none, reason:) - skill-security-scan test fixture (numeric
threshold: 0.5)
- preflight Check 6 scope-out sentinel (
- 3 self-referential files (this PR's plan, tasks.md, session-state.md) preserve their literal token examples (renaming would corrupt the rename's own documentation)
kb-tags.txt+INDEX.mdauto-regenerated
v3.89.1 — 2026-05-13
Web Platform
- feat(observability): bind
Sentry.setUserwith HMAC-pseudonymoususer.idat the per-user-rate-limit HOC, wrapped inSentry.withIsolationScopefor cross-request scope isolation under the custom-server boot path. - feat(observability): migrate 11 silent-fallback sites in
app/**/route.tstoreportSilentFallback+ inlinesetUser; preserves original pino diagnostic message strings and existing Sentry tag continuity (feature/oppairs unchanged). - feat(observability):
sentry-scrub.ts:scrubRecursivenow renamesuserId/user_idkeys (case-insensitive, recursive) touserIdHashat thebeforeSend/beforeBreadcrumbboundary. Defensive precedence preserves caller-supplieduserIdHashand drops raw key. - docs(legal): Article 30 PA8 §(c)(i)+(c)(ii) updated to document the
shipped substrate and reference the canonical inventory in
sentry-scrub.ts.
v3.89.0 — 2026-05-13
- feat(cc-router): deny-by-default MCP tool surface + DPA prerequisites (#2909)
v3.88.5 — 2026-05-13
Web Platform
- Added: pino
formatters.log()boundary hook pseudonymises every top-leveluserId/user_idemission touserIdHash(HMAC-SHA256, Doppler pepper). - Added: shared
renameUserIdToHashwalker (apps/web-platform/server/userid-pseudonymize.ts) — single source of truth for the rename. - Hardened:
mirrorCrossTenantViolationstripsuserId/user_idfrom operator-suppliedctxbefore Sentry payload spread (defense-in-depth; pino side already covered by the new hook). - Updated: Article 30 register PA8 §(c)(ii) — top-level boundary qualification, F2 fail-safe disclosure, DSAR domain-distinct hash field-name documentation.
- Added: ADR-029 (rename-at-boundary userId pseudonymisation) with invariants I1–I10 including two-primitive separation table.
- Added:
userid-bypass-lintCI gate enforces baseline coverage; new directlogger.error({userId})sites must route through helpers or emituserIdHashdirectly.
web-v0.84.0 — 2026-05-13
Web Platform
- Add
hash-user-idnpm script +apps/web-platform/scripts/hash-user-id.tsoperator CLI for recovering pseudonymous pino log lines from a raw user UUID. Pepper enters via Doppler env injection; never persisted, never typed at the operator terminal. - Add
apps/web-platform/test/scripts/hash-user-id.test.ts(5 spawnSync tests: happy-path, no-argv, no-pepper, deterministic, 64-hex sanity guard). Tests bypass the npm wrapper to validate the runtime contract directly.
Knowledge Base
- PA8 §(f) Hetzner pino retention concretised in
knowledge-base/legal/article-30-register.mdwith structural cap, observed-volume sentinel, and closed 4-trigger re-verification list. - New runbook
knowledge-base/engineering/ops/runbooks/recover-userid-from-pino-stdout.mdcovering both operator flows. Documents the two-primitive separation (hashUserIdvshashUserIdForSentry) load-bearingly per ADR-029 §I10. knowledge-base/legal/compliance-posture.mdArticle 30 row appended with concretisation note.
web-v0.83.1 — 2026-05-13
Web Platform
- feat(observability): bind
Sentry.setUserwith HMAC-pseudonymoususer.idat the per-user-rate-limit HOC, wrapped inSentry.withIsolationScopefor cross-request scope isolation under the custom-server boot path. - feat(observability): migrate 11 silent-fallback sites in
app/**/route.tstoreportSilentFallback+ inlinesetUser; preserves original pino diagnostic message strings and existing Sentry tag continuity (feature/oppairs unchanged). - feat(observability):
sentry-scrub.ts:scrubRecursivenow renamesuserId/user_idkeys (case-insensitive, recursive) touserIdHashat thebeforeSend/beforeBreadcrumbboundary. Defensive precedence preserves caller-supplieduserIdHashand drops raw key. - docs(legal): Article 30 PA8 §(c)(i)+(c)(ii) updated to document the
shipped substrate and reference the canonical inventory in
sentry-scrub.ts.
web-v0.83.0 — 2026-05-13
- feat(cc-router): deny-by-default MCP tool surface + DPA prerequisites (#2909)
web-v0.82.2 — 2026-05-13
Web Platform
- Added: pino
formatters.log()boundary hook pseudonymises every top-leveluserId/user_idemission touserIdHash(HMAC-SHA256, Doppler pepper). - Added: shared
renameUserIdToHashwalker (apps/web-platform/server/userid-pseudonymize.ts) — single source of truth for the rename. - Hardened:
mirrorCrossTenantViolationstripsuserId/user_idfrom operator-suppliedctxbefore Sentry payload spread (defense-in-depth; pino side already covered by the new hook). - Updated: Article 30 register PA8 §(c)(ii) — top-level boundary qualification, F2 fail-safe disclosure, DSAR domain-distinct hash field-name documentation.
- Added: ADR-029 (rename-at-boundary userId pseudonymisation) with invariants I1–I10 including two-primitive separation table.
- Added:
userid-bypass-lintCI gate enforces baseline coverage; new directlogger.error({userId})sites must route through helpers or emituserIdHashdirectly.
v3.88.4 — 2026-05-12
Web Platform infra
- Wall-clock cap (
ci-deploy-wrapper.sh) enforces 900s SIGTERM + 20s SIGKILL onci-deploy.sh. - TERM/INT trap in
ci-deploy.shwrites terminalreason=timeoutto the deploy state file when trap CAN dispatch. - Six trigger files now tracked by
terraform_data.deploy_pipeline_fix(was five).
Soleur plugin
deepen-planskill: new bullet prescribing a 10-line parent.sh/child.sh repro for any AC bound to PGID/session/signal-defer semantics (PGID-inheritance gotcha caught at /work).postmerge/deploy-status-debugging.md: newtimeout | 124taxonomy row with concretejournalctlinvocation.shipskill: Deploy Pipeline Fix Drift Gate updated for 6 trigger files; test fixture updated.
v3.88.3 — 2026-05-12
- feat(ci): split test job into 3 shards + synthetic aggregator (~41% wall-clock reduction)
v3.88.2 — 2026-05-12
Plugin
plugins/soleur/skills/one-shot/SKILL.md: new Step 0a.5 between the Linear preflight (0a) and worktree creation (0b).
v3.88.1 — 2026-05-12
- fix(work,plan): no mid-plan pause gates + operator-step automation gate
v3.88.0 — 2026-05-12
Web Platform
- NEW GDPR Art. 15 + Art. 20 self-serve export at
/dashboard/settings/privacy - NEW
dsar_export_jobs+dsar_export_audit_piitables with WORM trigger (migrations 041 + 042) - NEW Storage bucket
dsar-exportswith folder-prefix RLS - NEW Account-delete cascade extended for Art. 17 compliance with the new DSAR surface
Plugin
- NEW
.github/workflows/legal-doc-cross-document-gate.yml— blocks DSAR PRs that don't update all 4 legal docs in lockstep - NEW Operator runbooks:
dsar-export-oversize.md,dsar-export-failed-job.md,scripts/dsar-export-oversize.sh - UPDATED Privacy Policy §4.7 + §8.1, GDPR Policy §3.7 + §5.3, Data Protection Disclosure §2.3 + §5.3 + §10.3, compliance-posture.md
🤖 Generated with Claude Code
v3.87.11 — 2026-05-12
Plugin
- Pre-commit gate: new
rule-budget-lintcommand inlefthook.ymlrejects commits when AGENTS.md+AGENTS.core.md exceed 22 k or any rule body exceeds 600 B. - Anchor parity: every
[skill-enforced: ...]tag must now resolve to a real anchor in its targetSKILL.mdunder a tolerant matcher; the linter resolves all 21 existing pairs against the current tree. - Shared SECTIONS module:
scripts/_agents_md_sections.pyis the single source of truth.
v3.87.10 — 2026-05-12
Plugin (hooks + skills)
- New:
.claude/hooks/lib/session-state.sh—acquire_lock/release_lock/acquire_lock_shared/with_lock(per-name FD multiplexing viaexec {fd}>>file, flock-based),acquire_lease/release_lease/is_lease_active/sweep_orphan_leases/_register_lease_release_trap(durable key=value leases with PID + hostname +started_atFlohr-rule release-guard, ISO-8601-Z anchored to defenddate -dagainst natural-language DoS, path-traversal validator on worktree names),headless_or_stderr(TTY-aware routing — log file underclaude --bg, stderr foreground),SOLEUR_DISABLE_SESSION_STATE=1kill switch. Hard-fails with operator-facing error ifflockmissing. 349 LOC + 349 LOC tests (T1–T8 covering mutual exclusion, timeout, lease roundtrip, dead-PID detection, orphan sweep, flock-missing hard-fail, multi-signal trap, headless/foreground branch). - Edit:
plugins/soleur/skills/git-worktree/scripts/worktree-manager.sh— sourcessession-state.shwith loud-warn fallback;create_for_featurecallssweep_orphan_leases + acquire_lease + _register_lease_release_trap + git push -u + ls-remote verify, emitsSOLEUR_FEATURE_PUSH_FAILEDmarker on stdout when push fails;cleanup_merged_worktreesacquirescleanup-mergedlock (5s timeout) with RETURN trap, nestedfetch-prunelock, reap loop checksis_lease_active+ 10-min recent-commit grace + clock-skew abs guard before existing dirty-status guard. - Edit:
.claude/hooks/pre-merge-rebase.sh— 4 stderr emissions routed throughheadless_or_stderr;git merge origin/mainwrapped inacquire_lock rebase-main 60with EXIT trap; command-detection regex extended to match---separator wrapped forms (closes hook-bypass class). - Edit:
.claude/hooks/lib/log-rotation.sh+.claude/hooks/lib/incidents.sh— stderr emissions routed throughheadless_or_stderrwith lazy-source guard. - Edit:
.claude/hooks/session-rules-loader.sh— booleanHEADLESS_MODEexport ([[ ! -t 0 && -n $CLAUDECODE ]]) for downstream consumers. - Edit:
plugins/soleur/skills/{one-shot,brainstorm,work}/SKILL.md— invokeworktree-manager.sh featurewithSOLEUR_SKILL_NAME+SOLEUR_EXPECTED_DURATION_MINenv to wire the session lease. - Edit:
plugins/soleur/skills/{ship,merge-pr,schedule,product-roadmap}/SKILL.md—gh pr merge --autowrapped inwith_lock merge-main 600 --, withrc=99retry guidance. - Edit:
plugins/soleur/skills/work/SKILL.md— explicit Phase Exitrelease_leaseblock. - Edit:
plugins/soleur/skills/{plan,review}/SKILL.md— Sharp Edges entries for "shell wrappers can bypass PreToolUse hook regex" (routed from compound learning).
Tests
.claude/hooks/lib/session-state.test.sh(T1–T8)plugins/soleur/skills/git-worktree/test/lease-protects-active.test.sh(2026-04-21 reproducer; verified RED→GREEN with commit-date 2025-01-01 to bypass recent-commit grace and isolate the lease guard).claude/hooks/pre-merge-rebase-headless.test.shplugins/soleur/test/concurrent-ship.test.sh(static lock-wiring assertion across 4 SKILL.md files + smoke serialization test).claude/hooks/session-rules-loader-headless.test.shtest/pre-merge-rebase.test.ts— stripCLAUDECODEfrom cleanEnv so spawned hooks use the foreground stderr branch.claude/hooks/log-rotation.test.shTest 14 — updated for new stderr format
v3.87.9 — 2026-05-12
Web Platform
feat: pseudonymizeuserIdat Sentry + pino emit boundary inapps/web-platform/server/observability.ts(HMAC-SHA256, fail-closed sentinel, optional rotation-lookup pepper arg).feat: migrate 2 directSentry.captureMessage23505-fallback sites inws-handler.tstowarnSilentFallback.chore: addSENTRY_USERID_PEPPER+peppertosensitive-keys.tsredaction list.chore: explicitisolate: trueon vitest unit project for module-init env-var isolation.
Legal
docs: Article 30 PA8 §(c) — disclose HMAC-SHA256 pseudonymization at helper boundaries with forward-reference to #3698 for the 27-site direct-pino-emit migration.docs: Article 30 PA8 §(f) — append Recital 26 retention-only Art. 17 clarification.
Plan Skill
docs: Sharp Edges — centralizing helper / boundary / redaction layer transforms require two-clause ACs (helper-routed AND direct-bypass) AND scoped disclosure language. See2026-05-12-centralized-at-helper-boundary-transforms-overclaim-in-acs-and-disclosures.md.
v3.87.8 — 2026-05-12
Plugin
plugins/soleur/skills/work/SKILL.mdPhase 4 — entry-guard subsection between Playwright-First Audit and Invocation Mode. Asserts at least one commit beyond the upstream branch before emitting the handoff marker; distinct exit codes (2 = pause-and-commit, 1 = halt-and-investigate); detached-HEAD guard.plugins/soleur/skills/plan/SKILL.mdandplugins/soleur/skills/deepen-plan/SKILL.md— matching loader-class-fit checklist bullets with cross-mirror HTML comments. Pins grep at the canonical class-selection range.plugins/soleur/skills/compound/SKILL.mdstep 8[CRITICAL]warning — appended Why-line trim semantics directive (with Correct/Over-trimmed examples) and pre-demotion class-fit reminder.AGENTS.docs.mdcq-agents-md-why-single-linerule — extended[skill-enforced:]tag suffix to name the two enforcement dimensions; trimmedRule count advisory.and second(compound step 8)parenthetical for headroom (594 → 578 B / 600 cap).
Knowledge base
knowledge-base/project/learnings/2026-05-12-agents-md-trim-loader-class-fit-verification.md— captures (a) loader-class-fit verification at plan time, (b) push semantic detail into[skill-enforced:]tag suffix instead of rule body. Generalization: AGENTS.md is the index, not the spec — let the enforcer own the semantics.knowledge-base/project/plans/2026-05-12-chore-agents-md-trim-workflow-hardening-plan.md— implementation plan.knowledge-base/project/specs/feat-one-shot-3682-agents-md-trim-workflow-hardening/session-state.md— session-state forwarded from the plan+deepen subagent.
v3.87.7 — 2026-05-12
Plugin
- Rule registry: 1 wg-* demoted core→rest, 1 wg-* body-trimmed in core, 2 hr-* body-trimmed in core, 4 Why-line trims.
plugins/soleur/skills/work/SKILL.md: added Type-widening cross-consumer grep bullet in §Phase 0.
Web Platform
apps/web-platform/test/pdf-text-extract.test.ts:beforeAllpre-warms pdfjs-dist (fixes 7s cold-start flake; subsequent tests run at warm ~9ms).
Knowledge-base
- Plan + learning + session-state files documenting the trim strategy and 3 session errors → workflow improvement follow-up at #3682.
v3.87.6 — 2026-05-12
Plugin
- Plugin-mirror DPD §4.2 Resend Legal-Basis column trimmed to match the canonical surface; Last-Updated annotation rewritten to reference §2.3(j) instead of workflow tokens.
Canonical legal docs
- Canonical DPD §4.2 Resend Legal-Basis column trimmed; Last-Updated annotation refreshed.
v3.87.5 — 2026-05-12
- refactor(cc-dispatcher): cluster drain (#3639 + #3640 + #3641 + #3642)
v3.87.4 — 2026-05-12
Plugin
- New plan/SKILL.md Sharp Edges: precondition-grep on producing scope, parametrized-test ↔ component-prop-boundary cross-check, single-enum FR enumeration.
- New review/SKILL.md Defect Class: single-literal gate over multi-member union/enum, with spawn-prompt enumeration takeaway.
v3.87.3 — 2026-05-12
- docs: defer #2724 mcp-server-builder (brainstorm)
v3.87.2 — 2026-05-12
- Forward-ports plugin-mirror legal docs at
plugins/soleur/docs/pages/legal/*to match canonical disclosures on Web Platform push notifications, Resend transactional email, KB-sharing lawful basis, and Article 30 register activity #11. Documentation-only; no code, schema, or processing changes. Public docs-site atsoleur.ai/legal/*will now reflect the same Web Platform processing activities already disclosed atapp.soleur.ai/legal/*.
Common Questions
Frequently Asked Questions
How often is Soleur updated?
Soleur ships continuously — updates are released when ready and tagged with semantic versioning. There is no fixed release schedule. Changes range from new agents and skills to bug fixes and documentation improvements.
How do I upgrade Soleur?
Run claude plugin install soleur to get the latest version. The plugin manager handles the update automatically. Check the changelog or GitHub releases page for details on what changed.
Does Soleur use semantic versioning?
Yes. Soleur follows semantic versioning — major versions for breaking changes, minor versions for new agents or skills, and patch versions for bug fixes and documentation updates. Version labels are set during PR review and applied automatically at merge.