heyspex 0.2.6 → 0.2.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (85) hide show
  1. package/bin/hs.mjs +85 -25
  2. package/bin/spexcode.mjs +31 -0
  3. package/dev-factory/lib/local-firecrawl.mjs +294 -0
  4. package/dev-factory/lib/seat-context.mjs +20 -4
  5. package/dev-factory/model-catalog.json +222 -222
  6. package/dev-factory/spexcrawl/firecrawl-cli.mjs +755 -0
  7. package/dist/cli/hs-connect.mjs +20 -2
  8. package/dist/cli/hs-defer.mjs +19 -1
  9. package/dist/cli/hs-index-rebuild.mjs +19 -1
  10. package/dist/cli/hs-index-reconcile.mjs +19 -1
  11. package/dist/cli/hs-init.mjs +2 -2
  12. package/dist/cli/hs-install.mjs +2 -2
  13. package/dist/cli/hs-join.mjs +20 -2
  14. package/dist/cli/hs-next-launch.mjs +89 -10
  15. package/dist/cli/hs-spawn.mjs +27 -1
  16. package/dist/cli/hs-vault-pull.mjs +19 -1
  17. package/dist/cli/hs-vault-push.mjs +19 -1
  18. package/dist/cli/hs-vault.mjs +21 -7
  19. package/dist/cli/hs-workspace.mjs +19 -1
  20. package/dist/cli-templates/customer-vault/specs/entity-model.md +1728 -1728
  21. package/dist/cli-templates/customer-vault/specs/protocols/canonical-frontmatter-templates.md +464 -464
  22. package/dist/cli-templates/customer-vault/specs/protocols/destructive-action-checklist.md +122 -122
  23. package/dist/cli-templates/customer-vault/specs/protocols/memory-protocol.md +46 -46
  24. package/dist/cli-templates/customer-vault/specs/protocols/spec-hierarchy.md +530 -530
  25. package/dist/cli-templates/customer-vault/specs/protocols/spec-summary-authoring.md +83 -83
  26. package/dist/cli-templates/harness-commands/claude/hs-backfill.md +28 -28
  27. package/dist/cli-templates/harness-commands/claude/hs-capture.md +62 -62
  28. package/dist/cli-templates/harness-commands/claude/hs-defer.md +29 -29
  29. package/dist/cli-templates/harness-commands/claude/hs-ground.md +30 -30
  30. package/dist/cli-templates/harness-commands/claude/hs-next.md +29 -29
  31. package/dist/cli-templates/harness-commands/claude/hs-promote.md +70 -70
  32. package/dist/cli-templates/harness-commands/claude/hs-push.md +35 -35
  33. package/dist/cli-templates/harness-commands/claude/hs-qc.md +27 -27
  34. package/dist/cli-templates/harness-commands/claude/hs-res.md +20 -8
  35. package/dist/cli-templates/harness-commands/claude/hs-resolve.md +23 -23
  36. package/dist/cli-templates/harness-commands/claude/hs-view.md +28 -28
  37. package/dist/cli-templates/harness-commands/claude/kill-ports.md +32 -32
  38. package/dist/cli-templates/harness-commands/claude/prototype.md +91 -91
  39. package/dist/cli-templates/harness-commands/cursor/hs-backfill.md +22 -22
  40. package/dist/cli-templates/harness-commands/cursor/hs-capture.md +56 -56
  41. package/dist/cli-templates/harness-commands/cursor/hs-defer.md +23 -23
  42. package/dist/cli-templates/harness-commands/cursor/hs-ground.md +24 -24
  43. package/dist/cli-templates/harness-commands/cursor/hs-next.md +23 -23
  44. package/dist/cli-templates/harness-commands/cursor/hs-promote.md +64 -64
  45. package/dist/cli-templates/harness-commands/cursor/hs-push.md +29 -29
  46. package/dist/cli-templates/harness-commands/cursor/hs-qc.md +21 -21
  47. package/dist/cli-templates/harness-commands/cursor/hs-res.md +20 -8
  48. package/dist/cli-templates/harness-commands/cursor/hs-resolve.md +17 -17
  49. package/dist/cli-templates/harness-commands/cursor/hs-view.md +23 -23
  50. package/dist/cli-templates/harness-commands/cursor/kill-ports.md +26 -26
  51. package/dist/cli-templates/harness-commands/cursor/prototype.md +86 -86
  52. package/docs/copilot-plugin-install.md +7 -0
  53. package/docs/mcp-client-config.md +6 -0
  54. package/package.json +7 -2
  55. package/plugins/heyspex/README.md +6 -0
  56. package/plugins/heyspex/bin/launch-mcp.mjs +17 -0
  57. package/plugins/heyspex/hooks/hooks.json +418 -418
  58. package/scripts/claude-hooks/_intent-classifier-semantic.mjs +2 -2
  59. package/scripts/hs-companion.mjs +38 -8
  60. package/scripts/lib/companion-install.mjs +768 -0
  61. package/scripts/lib/customer-kit.mjs +5 -3
  62. package/scripts/lib/hs-companion-settings.mjs +1 -0
  63. package/scripts/lib/hs-source-push.mjs +386 -386
  64. package/spexharness/doctrine/baseline/SPEXCODE-DOCTRINE.baseline.json +29 -29
  65. package/spexharness/src/adapters/copilot-models.mjs +179 -0
  66. package/spexharness/src/adapters/harness-detect.mjs +148 -0
  67. package/spexharness/src/gates/directive-obligation-gate.decide.mjs +132 -132
  68. package/spexharness/src/gates/vault-write-tier-guard.decide.mjs +153 -125
  69. package/spexharness/src/seat-context.mjs +10 -5
  70. package/spexharness/src/session-bootstrap.mjs +6 -3
  71. package/vendor/heyspex-mcp/cli.mjs +6 -1
  72. package/vendor/heyspex-mcp/config-seed.yaml +15 -15
  73. package/vendor/heyspex-mcp/dev-factory-overlay.mjs +142 -0
  74. package/vendor/heyspex-mcp/memory-tools.mjs +523 -523
  75. package/vendor/heyspex-mcp/on-deck-scheduler.mjs +1708 -1708
  76. package/vendor/heyspex-mcp/procedure-handlers.mjs +327 -327
  77. package/vendor/heyspex-mcp/procedure-tools.mjs +1209 -1181
  78. package/vendor/heyspex-mcp/research-tools.mjs +22 -2
  79. package/vendor/heyspex-mcp/seat-assign-cli.mjs +242 -0
  80. package/vendor/heyspex-mcp/seat-assignment-rules.mjs +96 -0
  81. package/vendor/heyspex-mcp/seat-assignments-client.mjs +265 -0
  82. package/vendor/heyspex-mcp/seat-defaults-cli.mjs +45 -0
  83. package/vendor/heyspex-mcp/seat-defaults.mjs +232 -0
  84. package/vendor/heyspex-mcp/seat-identity.mjs +171 -0
  85. package/vendor/heyspex-mcp/vault-io.mjs +720 -720
@@ -7,89 +7,89 @@ description: Build an HTML/frontend prototype for the HeySpex Console. Files MUS
7
7
 
8
8
  **Usage:** `/prototype <slug> [--from-spec HS-XXXX] [--bump] [--variant <name>]`
9
9
 
10
- This skill is the **implementation** of `specs/protocols/prototype-lifecycle-protocol.md`. The protocol is the SSOT — when they conflict, the protocol wins and this skill is the bug. Fetch it with `heyspex_get_procedure({ name: "prototype-lifecycle-protocol" })` when you need the full rules.
11
-
12
- It applies to:
13
-
14
- - explicit `/prototype` invocation
15
- - any natural-language "build me an HTML prototype / mock / preview / canvas" ask
16
- - `/frontend-design` invocations in this repo (the plugin builds the artifact; this skill governs placement)
17
-
18
- ## The contract — no exceptions
19
-
20
- **Required output paths** (both files, same commit):
21
-
22
- 1. `spex-console/public/design-previews/<slug>-v<N>[-<variant>].html` — the self-contained prototype.
23
- 2. `spex-console/public/design-previews/<slug>-v<N>[-<variant>].meta.json` — the sidecar.
24
-
25
- Anything outside this folder — including a stray top-level `prototypes/` directory — is **invisible** to the console. The route at `spex-console/src/app/api/ui-design/prototypes/route.ts` reads this folder flat (no recursion, no nested folders). A prototype that doesn't show up in the Prototypes surface does not exist for the user.
26
-
27
- ## Naming
28
-
29
- - **`<slug>`** (lineage slug) — kebab-case, describes the surface (`capture-canvas`, `shipped-surface`, `review-inbox`). May contain hyphens. **Match an existing lineage if you're iterating on a known surface** — grep `spex-console/public/design-previews/` before inventing a new slug.
30
- - **`-v<N>`** — version, starts at `-v1`. **Bump rather than overwrite.** The console groups versions into a lineage with full history. If `--bump`, increment from the highest existing `-v<N>` for that slug.
31
- - **`-<variant>`** (optional) — sibling variant within a version (e.g. `-v2-alt`, `-v2-minimal`, `-v2-terminal`). May contain hyphens. The console nests variants under their parent version and shows a `+N variants at vK` chip on the lineage card. Variants are for "A/B explorations of the same version", not new lineages.
32
- - **No `index.html`, no nested folders, no dated filenames.** Just `<slug>-v<N>[-<variant>].html`.
33
-
34
- ## meta.json schema
35
-
36
- Validate against `specs/schemas/prototype-meta.schema.json`. Required: `title` + `status`. Always set `surface_area` and 1–4 `tags` on new sidecars (the console's filter rail depends on them — leaving them empty makes the prototype harder to find).
37
-
38
- ```json
39
- {
40
- "title": "Human-readable name (e.g. 'Capture canvas v2')",
41
- "description": "One-paragraph summary: what it demonstrates, key interactions, aesthetic direction, technical notes. The console hides this on the card and shows it in the drawer Notes tab — write for that context.",
42
- "status": "draft",
43
- "surface_area": "capture | on-deck | preloader | shell | review | roadmap | other",
44
- "tags": ["kebab-case", "1-to-4"],
45
- "updated_at": "2026-06-03T18:17:00.000Z",
46
- "design_doc": "specs/ui/<slug>-design.md (optional but required for promotion to accepted)",
47
- "linked_specs": [
48
- "HS-XXXX-CAP-...",
49
- "HS-XXXX-EPIC-..."
50
- ],
51
- "parent": "<slug>-v<N-1>.html (optional, when this iterates on a prior version)",
52
- "embeds": ["other-prototype-slug (optional)"]
53
- }
54
- ```
55
-
56
- - **`status` MUST be `"draft"` at create time.** Promotion to `"accepted"` runs through the console's `/api/ui-design/prototypes/<slug>/promote` route and requires both a linked `design_doc` AND a review entry under `specs/reviews/`. The skill does not write `accepted` — refuse if the user asks. (`"archived"` is for superseded versions; usually set later, not at create time.)
57
- - **Compute `updated_at` as `new Date().toISOString()`** at write time.
58
- - **`linked_specs`** accepts vault basenames (no `.md` extension) and `HS-*` IDs. Always include the capture/epic/task the prototype embodies. Pull from `--from-spec` if provided. Never invent IDs.
59
- - Reference siblings in this folder for examples — `shipped-surface-v1.meta.json` (thorough) or `on-deck-v2.meta.json` (minimal).
60
-
61
- ## Workflow
62
-
63
- When this skill is invoked or matched:
64
-
65
- 1. **Resolve lineage slug.** Match an existing slug if iterating on a known surface; otherwise pick a new kebab-case slug.
66
- 2. **Resolve version.** Default `-v1`. If a file with the same slug already exists, default to bumping to the next integer; honour explicit `--bump`. **Never silently overwrite** — if the target file exists and `--bump` was not passed, surface the conflict and ask.
67
- 3. **Resolve variant.** `--variant <name>` produces `<slug>-v<N>-<name>.html`. Without it, you produce the base variant.
68
- 4. **Pull source spec context.** If `--from-spec HS-XXXX` is passed or the user references a spec, Read it first so the prototype reflects real content, not invented filler.
69
- 5. **Aesthetic.** Defer to the user's brief (e.g. "Claude-in-PowerShell terminal aesthetic" overrides defaults). Otherwise honour console design-system tokens — fetch via `heyspex_design_*` MCP tools, do not grep `spex-console/DESIGN.md`. Recall UI memories first: `heyspex_recall_memories({ tags: ["ui", "console", "design-system"] })`.
70
- 6. **Decide `surface_area` and `tags`.** Pick `surface_area` from the enum based on what the prototype shows. Pick 1–4 lowercase kebab-case `tags` covering the dominant patterns (e.g. `empty-state`, `dark-mode`, `keyboard-nav`).
71
- 7. **Write both files in the same commit.** HTML at `spex-console/public/design-previews/<slug>-v<N>[-<variant>].html`, sidecar at the matching `.meta.json` path. Single self-contained HTML file (inline CSS/JS).
72
- 8. **Validate the sidecar shape** against the schema before saving. Required: `title` + `status`. `status` MUST be `"draft"`. `tags` MUST match `^[a-z0-9-]+$`. `surface_area` MUST be in the enum. `linked_specs[]` items MUST match `^HS-[A-Z0-9]+-` (family keys contain digits, e.g. `HS-9HVY-CAP`). Fix and re-write if any fail.
73
- 9. **Confirm.** After writing, report the gallery URL (`/design-previews/<slug>-v<N>[-<variant>].html`). The console's UI-Design → Prototypes surface picks it up via `/api/ui-design/prototypes` and groups it into the matching lineage automatically.
74
-
75
- ## Anti-patterns — do not do these
76
-
77
- - Do **not** create a new `prototypes/` folder at the repo root.
78
- - Do **not** nest as `<slug>/index.html`.
79
- - Do **not** overwrite an existing `<slug>-v<N>[-<variant>].html` — bump or use a new variant.
80
- - Do **not** ship without a sibling sidecar.
81
- - Do **not** write `status: "accepted"` from this skill — promotion runs through the console's `/promote` route only.
82
- - Do **not** invent linked specs. Only reference `HS-*` IDs that exist in the vault.
83
- - Do **not** leave `surface_area` and `tags` empty on new sidecars — the console's filter rail depends on them.
84
- - Do **not** Read `spex-console/DESIGN.md` for token lookups; use `heyspex_design_get_token` / `heyspex_design_get_pattern` MCP tools.
85
-
86
- ## Reference
87
-
88
- - **Protocol (SSOT):** `specs/protocols/prototype-lifecycle-protocol.md` — fetch with `heyspex_get_procedure({ name: "prototype-lifecycle-protocol" })`
89
- - **Schema (SSOT):** `specs/schemas/prototype-meta.schema.json`
90
- - **Discovery route:** `spex-console/src/app/api/ui-design/prototypes/route.ts`
91
- - **Surface component:** `spex-console/src/components/surfaces/ui-design-surface.tsx`
92
- - **Lineage parser:** `spex-console/src/lib/prototype-lineage.ts`
93
- - **Folder:** `spex-console/public/design-previews/`
94
- - **Thorough sidecar example:** `shipped-surface-v1.meta.json`
95
- - **Minimal sidecar example:** `on-deck-v2.meta.json`
10
+ This skill is the **implementation** of `specs/protocols/prototype-lifecycle-protocol.md`. The protocol is the SSOT — when they conflict, the protocol wins and this skill is the bug. Fetch it with `heyspex_get_procedure({ name: "prototype-lifecycle-protocol" })` when you need the full rules.
11
+
12
+ It applies to:
13
+
14
+ - explicit `/prototype` invocation
15
+ - any natural-language "build me an HTML prototype / mock / preview / canvas" ask
16
+ - `/frontend-design` invocations in this repo (the plugin builds the artifact; this skill governs placement)
17
+
18
+ ## The contract — no exceptions
19
+
20
+ **Required output paths** (both files, same commit):
21
+
22
+ 1. `spex-console/public/design-previews/<slug>-v<N>[-<variant>].html` — the self-contained prototype.
23
+ 2. `spex-console/public/design-previews/<slug>-v<N>[-<variant>].meta.json` — the sidecar.
24
+
25
+ Anything outside this folder — including a stray top-level `prototypes/` directory — is **invisible** to the console. The route at `spex-console/src/app/api/ui-design/prototypes/route.ts` reads this folder flat (no recursion, no nested folders). A prototype that doesn't show up in the Prototypes surface does not exist for the user.
26
+
27
+ ## Naming
28
+
29
+ - **`<slug>`** (lineage slug) — kebab-case, describes the surface (`capture-canvas`, `shipped-surface`, `review-inbox`). May contain hyphens. **Match an existing lineage if you're iterating on a known surface** — grep `spex-console/public/design-previews/` before inventing a new slug.
30
+ - **`-v<N>`** — version, starts at `-v1`. **Bump rather than overwrite.** The console groups versions into a lineage with full history. If `--bump`, increment from the highest existing `-v<N>` for that slug.
31
+ - **`-<variant>`** (optional) — sibling variant within a version (e.g. `-v2-alt`, `-v2-minimal`, `-v2-terminal`). May contain hyphens. The console nests variants under their parent version and shows a `+N variants at vK` chip on the lineage card. Variants are for "A/B explorations of the same version", not new lineages.
32
+ - **No `index.html`, no nested folders, no dated filenames.** Just `<slug>-v<N>[-<variant>].html`.
33
+
34
+ ## meta.json schema
35
+
36
+ Validate against `specs/schemas/prototype-meta.schema.json`. Required: `title` + `status`. Always set `surface_area` and 1–4 `tags` on new sidecars (the console's filter rail depends on them — leaving them empty makes the prototype harder to find).
37
+
38
+ ```json
39
+ {
40
+ "title": "Human-readable name (e.g. 'Capture canvas v2')",
41
+ "description": "One-paragraph summary: what it demonstrates, key interactions, aesthetic direction, technical notes. The console hides this on the card and shows it in the drawer Notes tab — write for that context.",
42
+ "status": "draft",
43
+ "surface_area": "capture | on-deck | preloader | shell | review | roadmap | other",
44
+ "tags": ["kebab-case", "1-to-4"],
45
+ "updated_at": "2026-06-03T18:17:00.000Z",
46
+ "design_doc": "specs/ui/<slug>-design.md (optional but required for promotion to accepted)",
47
+ "linked_specs": [
48
+ "HS-XXXX-CAP-...",
49
+ "HS-XXXX-EPIC-..."
50
+ ],
51
+ "parent": "<slug>-v<N-1>.html (optional, when this iterates on a prior version)",
52
+ "embeds": ["other-prototype-slug (optional)"]
53
+ }
54
+ ```
55
+
56
+ - **`status` MUST be `"draft"` at create time.** Promotion to `"accepted"` runs through the console's `/api/ui-design/prototypes/<slug>/promote` route and requires both a linked `design_doc` AND a review entry under `specs/reviews/`. The skill does not write `accepted` — refuse if the user asks. (`"archived"` is for superseded versions; usually set later, not at create time.)
57
+ - **Compute `updated_at` as `new Date().toISOString()`** at write time.
58
+ - **`linked_specs`** accepts vault basenames (no `.md` extension) and `HS-*` IDs. Always include the capture/epic/task the prototype embodies. Pull from `--from-spec` if provided. Never invent IDs.
59
+ - Reference siblings in this folder for examples — `shipped-surface-v1.meta.json` (thorough) or `on-deck-v2.meta.json` (minimal).
60
+
61
+ ## Workflow
62
+
63
+ When this skill is invoked or matched:
64
+
65
+ 1. **Resolve lineage slug.** Match an existing slug if iterating on a known surface; otherwise pick a new kebab-case slug.
66
+ 2. **Resolve version.** Default `-v1`. If a file with the same slug already exists, default to bumping to the next integer; honour explicit `--bump`. **Never silently overwrite** — if the target file exists and `--bump` was not passed, surface the conflict and ask.
67
+ 3. **Resolve variant.** `--variant <name>` produces `<slug>-v<N>-<name>.html`. Without it, you produce the base variant.
68
+ 4. **Pull source spec context.** If `--from-spec HS-XXXX` is passed or the user references a spec, Read it first so the prototype reflects real content, not invented filler.
69
+ 5. **Aesthetic.** Defer to the user's brief (e.g. "Claude-in-PowerShell terminal aesthetic" overrides defaults). Otherwise honour console design-system tokens — fetch via `heyspex_design_*` MCP tools, do not grep `spex-console/DESIGN.md`. Recall UI memories first: `heyspex_recall_memories({ tags: ["ui", "console", "design-system"] })`.
70
+ 6. **Decide `surface_area` and `tags`.** Pick `surface_area` from the enum based on what the prototype shows. Pick 1–4 lowercase kebab-case `tags` covering the dominant patterns (e.g. `empty-state`, `dark-mode`, `keyboard-nav`).
71
+ 7. **Write both files in the same commit.** HTML at `spex-console/public/design-previews/<slug>-v<N>[-<variant>].html`, sidecar at the matching `.meta.json` path. Single self-contained HTML file (inline CSS/JS).
72
+ 8. **Validate the sidecar shape** against the schema before saving. Required: `title` + `status`. `status` MUST be `"draft"`. `tags` MUST match `^[a-z0-9-]+$`. `surface_area` MUST be in the enum. `linked_specs[]` items MUST match `^HS-[A-Z0-9]+-` (family keys contain digits, e.g. `HS-9HVY-CAP`). Fix and re-write if any fail.
73
+ 9. **Confirm.** After writing, report the gallery URL (`/design-previews/<slug>-v<N>[-<variant>].html`). The console's UI-Design → Prototypes surface picks it up via `/api/ui-design/prototypes` and groups it into the matching lineage automatically.
74
+
75
+ ## Anti-patterns — do not do these
76
+
77
+ - Do **not** create a new `prototypes/` folder at the repo root.
78
+ - Do **not** nest as `<slug>/index.html`.
79
+ - Do **not** overwrite an existing `<slug>-v<N>[-<variant>].html` — bump or use a new variant.
80
+ - Do **not** ship without a sibling sidecar.
81
+ - Do **not** write `status: "accepted"` from this skill — promotion runs through the console's `/promote` route only.
82
+ - Do **not** invent linked specs. Only reference `HS-*` IDs that exist in the vault.
83
+ - Do **not** leave `surface_area` and `tags` empty on new sidecars — the console's filter rail depends on them.
84
+ - Do **not** Read `spex-console/DESIGN.md` for token lookups; use `heyspex_design_get_token` / `heyspex_design_get_pattern` MCP tools.
85
+
86
+ ## Reference
87
+
88
+ - **Protocol (SSOT):** `specs/protocols/prototype-lifecycle-protocol.md` — fetch with `heyspex_get_procedure({ name: "prototype-lifecycle-protocol" })`
89
+ - **Schema (SSOT):** `specs/schemas/prototype-meta.schema.json`
90
+ - **Discovery route:** `spex-console/src/app/api/ui-design/prototypes/route.ts`
91
+ - **Surface component:** `spex-console/src/components/surfaces/ui-design-surface.tsx`
92
+ - **Lineage parser:** `spex-console/src/lib/prototype-lineage.ts`
93
+ - **Folder:** `spex-console/public/design-previews/`
94
+ - **Thorough sidecar example:** `shipped-surface-v1.meta.json`
95
+ - **Minimal sidecar example:** `on-deck-v2.meta.json`
@@ -52,6 +52,13 @@ npm install ./heyspex-<version>.tgz
52
52
  npx hs login
53
53
  ```
54
54
 
55
+ - For research (`/hs-res`) only: Docker Desktop running a self-hosted Firecrawl stack on this
56
+ machine (official steps: `SELF_HOST.md` in github.com/firecrawl/firecrawl: clone it, add a
57
+ `.env` with `PORT=3002` and `USE_DB_AUTHENTICATION=false`, then
58
+ `docker compose build && docker compose up -d`). No env var or API key: the packaged Firecrawl
59
+ CLI finds it through `docker ps` / localhost:3002. Check it with
60
+ `node node_modules/heyspex/dev-factory/spexcrawl/firecrawl-cli.mjs search "test" --json`.
61
+
55
62
  ## 2. Pick ONE: the plugin or the repo hooks (never both)
56
63
 
57
64
  Copilot reads hooks from an installed plugin and from `.github/hooks/` in the repo. With both,
@@ -42,6 +42,12 @@ name, which is unambiguous:
42
42
  npx --yes --package heyspex heyspex-mcp
43
43
  ```
44
44
 
45
+ **Research prerequisite (`/hs-res` only).** Docker Desktop running a self-hosted Firecrawl stack
46
+ on this machine (official steps: `SELF_HOST.md` in github.com/firecrawl/firecrawl: clone it, add a
47
+ `.env` with `PORT=3002` and `USE_DB_AUTHENTICATION=false`, then
48
+ `docker compose build && docker compose up -d`). No env var or API key: the packaged Firecrawl CLI
49
+ finds it through `docker ps` / localhost:3002.
50
+
45
51
  **What the agent kit injects at session start.** With the kit hooks installed (`hs install` /
46
52
  `hs connect`, or the plugin), the `inject-doctrine` SessionStart hook adds the **baseline
47
53
  edition of SpexCode Doctrine** to each session: a short list of general working principles
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "heyspex",
3
- "version": "0.2.6",
3
+ "version": "0.2.7",
4
4
  "description": "HeySpex CLI + MCP server — connect Claude Code, Cursor, and any MCP client to your HeySpex spec vault",
5
5
  "keywords": [
6
6
  "heyspex",
@@ -66,6 +66,8 @@
66
66
  "dev-factory/lib/model-catalog.mjs",
67
67
  "dev-factory/model-catalog.json",
68
68
  "dev-factory/spexcrawl/spexcrawl-cli.mjs",
69
+ "dev-factory/spexcrawl/firecrawl-cli.mjs",
70
+ "dev-factory/lib/local-firecrawl.mjs",
69
71
  "docs/mcp-client-config.md",
70
72
  "docs/copilot-plugin-install.md",
71
73
  "docs/driving-heyspex-from-copilot.md",
@@ -97,6 +99,7 @@
97
99
  "scripts/lib/heyspex-home.mjs",
98
100
  "scripts/hs-companion.mjs",
99
101
  "scripts/lib/hs-companion-settings.mjs",
102
+ "scripts/lib/companion-install.mjs",
100
103
  "scripts/hs-next.mjs",
101
104
  "scripts/hs-mode.mjs",
102
105
  "scripts/heyspex-mode.mjs",
@@ -189,6 +192,7 @@
189
192
  "scripts": {
190
193
  "prepack": "node scripts/sync-skills.mjs && node scripts/build-cli-bundle.mjs && node scripts/prepack-closure-gate.mjs && node scripts/pack-manifest.mjs strip",
191
194
  "postpack": "node scripts/pack-manifest.mjs restore",
195
+ "prepublishOnly": "node scripts/install-qc.mjs",
192
196
  "build:cli": "node scripts/build-cli-bundle.mjs",
193
197
  "setup": "node scripts/heyspex-doctor.mjs --fix",
194
198
  "doctor": "node scripts/heyspex-doctor.mjs",
@@ -254,8 +258,9 @@
254
258
  "test:harness": "node --test spexharness/**/*.test.mjs",
255
259
  "verify:package": "node scripts/verify-mcp-package.mjs",
256
260
  "smoke:packed-install": "node scripts/packed-install.smoke.mjs",
261
+ "install:qc": "node scripts/install-qc.mjs",
257
262
  "verify:onboarding": "node scripts/verify-onboarding-scenario.mjs --fake",
258
263
  "sweep": "node scripts/sweep.mjs"
259
264
  },
260
- "//files": "PUBLISHED SURFACE - every entry is verified by `node scripts/verify-mcp-package.mjs`. It must cover the STATIC import closure of vendor/heyspex-mcp/cli.mjs, plus (since [[HS-LGG2-WW9R-TASK-ship-the-hook-runtime-in-the-npm]]) the customer hook kit: scripts/claude-hooks/_run.mjs, every HOOK_SCOPES customer hook (scripts/lib/customer-kit.mjs) and their static closure under spexharness/src, dev-factory/lib and scripts/ - the hookTargets check names any file that falls out - plus the run-time data files in customer-kit.mjs CUSTOMER_HOOK_DATA (only the baseline edition of SpexCode Doctrine, never the learned spexharness/doctrine/SPEXCODE-DOCTRINE.json; [[HS-A2PO-WW9R-TASK-owner-ruling-does-inject-doctrine-ship]]) - and nothing else. SpexFleet internals (dev-factory/router.mjs, cloud-clients.mjs, cost-tracker.mjs, spexcrawl/) are deliberately absent - research-tools.mjs reaches them through the lazy dev-factory-bridge.mjs. Do not add a path here without re-running the verifier; npm publish is a one-way door ([[HS-ZJSP-0JNK-TASK-ship-the-heyspex-mcp-server-as-an]] / [[HS-8DET-0JNK-TASK-confirm-the-open-core-boundary-and]]). `dist/cli/*.mjs` + `dist/cli-templates/**` are a SEPARATE published surface (`hs-init`, `hs-install`, `hs-claim`, `hs-check`, `hs-env`, `hs-connect`, `hs-join`, `hs-vault`, `hs-workspace`, `hs-defer`, `hs-vault-pull`, `hs-vault-push`, `hs-dev`, `hs-index-rebuild`, `hs-index-reconcile`, `hs-handoff`, `hs-pin`, `hs-events`, `hs-export-events`, `hs-prereq`, `hs-trash`, `hs-trust`, `hs-next-launch`, `hs-revalidate`, `hs-test`, `hs-spawn` bundled by `scripts/build-cli-bundle.mjs`'s `ENTRIES` array, regenerated fresh every `prepack` - `dist/` itself stays git-ignored) - see that script's doc comment for the entry scope decision and [[HS-JOQX-0JNK-TASK-published-package-runs-hs-init-and-hs]]."
265
+ "//files": "PUBLISHED SURFACE - every entry is verified by `node scripts/verify-mcp-package.mjs`. It must cover the STATIC import closure of vendor/heyspex-mcp/cli.mjs, plus (since [[HS-LGG2-WW9R-TASK-ship-the-hook-runtime-in-the-npm]]) the customer hook kit: scripts/claude-hooks/_run.mjs, every HOOK_SCOPES customer hook (scripts/lib/customer-kit.mjs) and their static closure under spexharness/src, dev-factory/lib and scripts/ - the hookTargets check names any file that falls out - plus the run-time data files in customer-kit.mjs CUSTOMER_HOOK_DATA (only the baseline edition of SpexCode Doctrine, never the learned spexharness/doctrine/SPEXCODE-DOCTRINE.json; [[HS-A2PO-WW9R-TASK-owner-ruling-does-inject-doctrine-ship]]) - and nothing else. SpexFleet internals (dev-factory/router.mjs, cloud-clients.mjs, cost-tracker.mjs, spexcrawl/ except the named research clients spexcrawl-cli.mjs and firecrawl-cli.mjs) are deliberately absent - research-tools.mjs reaches them through the lazy dev-factory-bridge.mjs. Do not add a path here without re-running the verifier; npm publish is a one-way door ([[HS-ZJSP-0JNK-TASK-ship-the-heyspex-mcp-server-as-an]] / [[HS-8DET-0JNK-TASK-confirm-the-open-core-boundary-and]]). `dist/cli/*.mjs` + `dist/cli-templates/**` are a SEPARATE published surface (`hs-init`, `hs-install`, `hs-claim`, `hs-check`, `hs-env`, `hs-connect`, `hs-join`, `hs-vault`, `hs-workspace`, `hs-defer`, `hs-vault-pull`, `hs-vault-push`, `hs-dev`, `hs-index-rebuild`, `hs-index-reconcile`, `hs-handoff`, `hs-pin`, `hs-events`, `hs-export-events`, `hs-prereq`, `hs-trash`, `hs-trust`, `hs-next-launch`, `hs-revalidate`, `hs-test`, `hs-spawn` bundled by `scripts/build-cli-bundle.mjs`'s `ENTRIES` array, regenerated fresh every `prepack` - `dist/` itself stays git-ignored) - see that script's doc comment for the entry scope decision and [[HS-JOQX-0JNK-TASK-published-package-runs-hs-init-and-hs]]."
261
266
  }
@@ -45,6 +45,12 @@ npx hs install --target . --plugin-apply # Claude Code
45
45
 
46
46
  `setup copilot --check` shows which route is active; `--uninstall` removes the hooks file and prints `copilot plugin uninstall heyspex`.
47
47
 
48
+ Research prerequisite (`/hs-res` only): Docker Desktop running a self-hosted Firecrawl stack on this machine
49
+ (official steps: `SELF_HOST.md` in github.com/firecrawl/firecrawl: clone it, add a `.env` with `PORT=3002` and
50
+ `USE_DB_AUTHENTICATION=false`, then `docker compose build && docker compose up -d`). No env var or API key: the
51
+ packaged Firecrawl CLI finds it through `docker ps` / localhost:3002. Check it with
52
+ `node node_modules/heyspex/dev-factory/spexcrawl/firecrawl-cli.mjs search "test" --json`.
53
+
48
54
  Fallback, by hand: `claude plugin marketplace add ./node_modules/heyspex` /
49
55
  `copilot plugin marketplace add ./node_modules/heyspex`, then `... plugin install heyspex@heyspex-marketplace`.
50
56
  Restart the session (`/restart` in Copilot), then check `copilot plugin list` and `npx hs doctor`.
@@ -106,4 +106,21 @@ try {
106
106
  // Older server tree without the helper: its own resolver is the only line of defence.
107
107
  }
108
108
 
109
+ // HS-2K22 (epic HS-C65J): stamp HEYSPEX_HARNESS for the server so seat defaults follow the harness
110
+ // this plugin was loaded by (Claude Code → Claude models, Copilot → `auto`). Claude Code and
111
+ // Copilot CLI both load this plugin's ONE .mcp.json, so the manifest cannot carry a static value;
112
+ // the stamp comes from positive env markers only (CLAUDE_PLUGIN_ROOT is ambiguous: Copilot expands
113
+ // it too). An explicit HEYSPEX_HARNESS is never overwritten; no marker → nothing is stamped.
114
+ try {
115
+ if (!process.env.HEYSPEX_HARNESS) {
116
+ const { harnessStampFor } = await import(
117
+ pathToFileURL(resolve(dirname(entry), "..", "..", "spexharness", "src", "adapters", "harness-detect.mjs")).href
118
+ );
119
+ const stamp = harnessStampFor(process.env);
120
+ if (stamp) process.env.HEYSPEX_HARNESS = stamp;
121
+ }
122
+ } catch {
123
+ // Older package without the detector: the server detects on its own.
124
+ }
125
+
109
126
  await import(pathToFileURL(entry).href);