dsh-env-manager-plugin 0.0.0-stage → 0.1.0
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.
- package/LICENSE +21 -0
- package/README.md +249 -2
- package/client.js +2581 -0
- package/cordis.patch.yml +4 -0
- package/docs/00-project/current-state.md +246 -0
- package/docs/00-project/glossary.md +215 -0
- package/docs/00-project/project-brief.md +114 -0
- package/docs/00-project/roadmap.md +89 -0
- package/docs/01-architecture/DSH_Environment_Service_Memory_Skill_Brainstorm.md +493 -0
- package/docs/01-architecture/api-verification.md +416 -0
- package/docs/01-architecture/architecture-overview.md +222 -0
- package/docs/01-architecture/data-model.md +930 -0
- package/docs/01-architecture/decisions/ADR-0001-plugin-as-bundle.md +29 -0
- package/docs/01-architecture/decisions/ADR-0002-file-based-storage.md +25 -0
- package/docs/01-architecture/decisions/ADR-0003-skill-router-over-search.md +25 -0
- package/docs/01-architecture/decisions/ADR-0004-typescript-host-js-client.md +31 -0
- package/docs/01-architecture/decisions/ADR-0005-layered-rule-resolution.md +36 -0
- package/docs/01-architecture/decisions/ADR-0006-credentials-as-references.md +30 -0
- package/docs/01-architecture/decisions/ADR-0007-session-scoped-default-environment.md +28 -0
- package/docs/01-architecture/decisions/ADR-0008-memory-bridge-not-second-store.md +31 -0
- package/docs/01-architecture/decisions/ADR-0009-client-host-http-transport.md +87 -0
- package/docs/01-architecture/decisions/ADR-0010-environment-plane-model.md +87 -0
- package/docs/01-architecture/decisions/ADR-0011-k8s-node-execution-model.md +92 -0
- package/docs/01-architecture/design.md +666 -0
- package/docs/01-architecture/detailed-design.md +961 -0
- package/docs/01-architecture/implementation-plan.md +323 -0
- package/docs/01-architecture/module-boundaries.md +306 -0
- package/docs/01-architecture/security-model.md +227 -0
- package/docs/01-architecture/storage-contract.md +224 -0
- package/docs/01-architecture/tool-contract.md +438 -0
- package/docs/01-architecture/ui-design.md +587 -0
- package/docs/02-harness/agent-behavior.md +36 -0
- package/docs/02-harness/change-snapshot-policy.md +29 -0
- package/docs/02-harness/client-ui-integration.md +110 -0
- package/docs/02-harness/context-policy.md +43 -0
- package/docs/02-harness/harness-standard.md +91 -0
- package/docs/02-harness/task-execution-policy.md +26 -0
- package/docs/02-harness/verification-policy.md +97 -0
- package/docs/03-openspec/archive-rule.md +25 -0
- package/docs/03-openspec/bugfix-rule.md +30 -0
- package/docs/03-openspec/design-rule.md +33 -0
- package/docs/03-openspec/openspec-usage-guide.md +31 -0
- package/docs/03-openspec/proposal-rule.md +70 -0
- package/docs/03-openspec/spec-rule.md +33 -0
- package/docs/03-openspec/tasks-rule.md +31 -0
- package/docs/04-development/coding-style.md +67 -0
- package/docs/04-development/dependency-policy.md +43 -0
- package/docs/04-development/development-guide.md +85 -0
- package/docs/04-development/directory-convention.md +105 -0
- package/docs/04-development/local-run-guide.md +55 -0
- package/docs/04-development/testing-guide.md +102 -0
- package/docs/05-domain/deployment-template.md +76 -0
- package/docs/05-domain/environment-template.md +165 -0
- package/docs/05-domain/operation-binding-template.md +55 -0
- package/docs/05-domain/operation-record-template.md +55 -0
- package/docs/05-domain/prompt-template.md +90 -0
- package/docs/05-domain/rule-template.md +73 -0
- package/docs/05-domain/service-template.md +39 -0
- package/docs/06-operations/deployment-guide.md +54 -0
- package/docs/06-operations/release.md +188 -0
- package/docs/06-operations/security-policy.md +53 -0
- package/docs/06-operations/troubleshooting.md +91 -0
- package/docs/07-templates/adr-template.md +21 -0
- package/docs/07-templates/bugfix-template.md +11 -0
- package/docs/07-templates/case-template.md +15 -0
- package/docs/07-templates/design-template.md +29 -0
- package/docs/07-templates/proposal-template.md +19 -0
- package/docs/07-templates/spec-template.md +15 -0
- package/docs/07-templates/tasks-template.md +12 -0
- package/docs/99-archive/README.md +13 -0
- package/docs/README.md +142 -0
- package/icon.svg +4 -0
- package/index.js +8 -0
- package/lib/app/app.d.ts +67 -0
- package/lib/app/app.js +494 -0
- package/lib/app/app.js.map +1 -0
- package/lib/config.d.ts +55 -0
- package/lib/config.js +42 -0
- package/lib/config.js.map +1 -0
- package/lib/domain/constants.d.ts +21 -0
- package/lib/domain/constants.js +59 -0
- package/lib/domain/constants.js.map +1 -0
- package/lib/domain/errors.d.ts +20 -0
- package/lib/domain/errors.js +22 -0
- package/lib/domain/errors.js.map +1 -0
- package/lib/domain/schemas.d.ts +28 -0
- package/lib/domain/schemas.js +445 -0
- package/lib/domain/schemas.js.map +1 -0
- package/lib/domain/types.d.ts +412 -0
- package/lib/domain/types.js +2 -0
- package/lib/domain/types.js.map +1 -0
- package/lib/index.d.ts +18 -0
- package/lib/index.js +89 -0
- package/lib/index.js.map +1 -0
- package/lib/logger.d.ts +8 -0
- package/lib/logger.js +13 -0
- package/lib/logger.js.map +1 -0
- package/lib/memory/bridge.d.ts +18 -0
- package/lib/memory/bridge.js +13 -0
- package/lib/memory/bridge.js.map +1 -0
- package/lib/registry/integrity.d.ts +10 -0
- package/lib/registry/integrity.js +204 -0
- package/lib/registry/integrity.js.map +1 -0
- package/lib/registry/registry.d.ts +14 -0
- package/lib/registry/registry.js +182 -0
- package/lib/registry/registry.js.map +1 -0
- package/lib/resolver/merge.d.ts +23 -0
- package/lib/resolver/merge.js +90 -0
- package/lib/resolver/merge.js.map +1 -0
- package/lib/resolver/resolve.d.ts +18 -0
- package/lib/resolver/resolve.js +288 -0
- package/lib/resolver/resolve.js.map +1 -0
- package/lib/resolver/template.d.ts +10 -0
- package/lib/resolver/template.js +42 -0
- package/lib/resolver/template.js.map +1 -0
- package/lib/router/params.d.ts +3 -0
- package/lib/router/params.js +83 -0
- package/lib/router/params.js.map +1 -0
- package/lib/router/router.d.ts +11 -0
- package/lib/router/router.js +204 -0
- package/lib/router/router.js.map +1 -0
- package/lib/session/session.d.ts +16 -0
- package/lib/session/session.js +64 -0
- package/lib/session/session.js.map +1 -0
- package/lib/skill.d.ts +17 -0
- package/lib/skill.js +56 -0
- package/lib/skill.js.map +1 -0
- package/lib/storage/atomic.d.ts +10 -0
- package/lib/storage/atomic.js +107 -0
- package/lib/storage/atomic.js.map +1 -0
- package/lib/storage/paths.d.ts +10 -0
- package/lib/storage/paths.js +50 -0
- package/lib/storage/paths.js.map +1 -0
- package/lib/storage/records.d.ts +16 -0
- package/lib/storage/records.js +112 -0
- package/lib/storage/records.js.map +1 -0
- package/lib/storage/sessions.d.ts +17 -0
- package/lib/storage/sessions.js +65 -0
- package/lib/storage/sessions.js.map +1 -0
- package/lib/tools/tools.d.ts +14 -0
- package/lib/tools/tools.js +472 -0
- package/lib/tools/tools.js.map +1 -0
- package/lib/transport/http.d.ts +3 -0
- package/lib/transport/http.js +217 -0
- package/lib/transport/http.js.map +1 -0
- package/locale/en.json +6 -0
- package/locale/zh.json +6 -0
- package/package.json +97 -4
|
@@ -0,0 +1,110 @@
|
|
|
1
|
+
# Client UI Integration
|
|
2
|
+
|
|
3
|
+
This note records the **host-side contract** a DSH bundle must follow when it adds a
|
|
4
|
+
sidebar entry and a main panel. It is derived from the installed
|
|
5
|
+
`@deepseek-ai/dsh-client-ui-sidebar` implementation (not from a mock), and from the
|
|
6
|
+
working `dsh-image-router` bundle.
|
|
7
|
+
|
|
8
|
+
Runtime source of truth:
|
|
9
|
+
|
|
10
|
+
- `@deepseek-ai/dsh-client-ui-sidebar/lib/client.js`, function `PanelRow`.
|
|
11
|
+
- The live slot catalog: `cordis_inspect_query` → `Slots.listSubTree` with root
|
|
12
|
+
`sidebar.panellist`, and root `main`.
|
|
13
|
+
- Skill reference: `cordis-plugin-development/references/ui-plugin.md` and
|
|
14
|
+
`references/practices.md` (plugin UI is part of the Harness UI).
|
|
15
|
+
|
|
16
|
+
## Sidebar entry
|
|
17
|
+
|
|
18
|
+
The sidebar owns the row. A plugin contributes only the row's **icon** and **label**;
|
|
19
|
+
it must not draw a button, row background, tooltip, margin, or hit area.
|
|
20
|
+
|
|
21
|
+
### Registration
|
|
22
|
+
|
|
23
|
+
```js
|
|
24
|
+
ctx.slots.inject('sidebar.panellist', () =>
|
|
25
|
+
ctx.slots.register(
|
|
26
|
+
{
|
|
27
|
+
name: 'sidebar.panellist',
|
|
28
|
+
id: 'dsh-env-manager', // row key; also the main panel key
|
|
29
|
+
order: 40,
|
|
30
|
+
label: () => t('title'), // thunk, re-read on locale projection
|
|
31
|
+
},
|
|
32
|
+
SidebarGlyph,
|
|
33
|
+
),
|
|
34
|
+
)
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
Rules:
|
|
38
|
+
|
|
39
|
+
1. `sidebar.panellist` is a **list** slot. Its registration fields are `id` (required),
|
|
40
|
+
`order`, and `label`. `id` must be unique; reusing a shipped id replaces that row.
|
|
41
|
+
2. `name` is the common slots registration field. Include it; the live sidebar
|
|
42
|
+
registers only entries that carry their slot name.
|
|
43
|
+
3. `label` is the row text and tooltip. Use a thunk when the text is localized so the
|
|
44
|
+
owner can re-read it without re-registering.
|
|
45
|
+
4. The second argument is the glyph component. The owner renders it inside
|
|
46
|
+
`span.panelGlyph` and passes exactly `{ size, active }`.
|
|
47
|
+
|
|
48
|
+
### Glyph contract
|
|
49
|
+
|
|
50
|
+
The owner passes:
|
|
51
|
+
|
|
52
|
+
- `size`: `16` when the sidebar is wide (`wide ? 16 : 18`);
|
|
53
|
+
- `active`: whether this row is the selected panel.
|
|
54
|
+
|
|
55
|
+
The glyph must:
|
|
56
|
+
|
|
57
|
+
- render an inline `<svg>` with `viewBox="0 0 20 20"`,
|
|
58
|
+
`width={size}`, `height={size}`;
|
|
59
|
+
- default defensively to `20` if `size` is missing or invalid;
|
|
60
|
+
- use `fill="none"` and `stroke="currentColor"` (shipped icons are monochrome line
|
|
61
|
+
icons; they inherit light/dark theme colors);
|
|
62
|
+
- use `opacity: 0.72` when `active === false`;
|
|
63
|
+
- set `aria-hidden="true"` and omit `aria-label`/tooltip — the row button owns the
|
|
64
|
+
accessible name from `label`;
|
|
65
|
+
- avoid fixed pixel width/height, background, border, border-radius, margin, or padding.
|
|
66
|
+
|
|
67
|
+
A filled colored square at `48×48` is the common failure mode: it overflows the
|
|
68
|
+
`panelGlyph` box, ignores the `size` prop, and looks like a different navigation
|
|
69
|
+
control from the shipped rows.
|
|
70
|
+
|
|
71
|
+
## Main panel
|
|
72
|
+
|
|
73
|
+
```js
|
|
74
|
+
ctx.slots.inject('main', () =>
|
|
75
|
+
ctx.slots.register(
|
|
76
|
+
{ name: 'main', key: 'dsh-env-manager', inject: () => ({}) },
|
|
77
|
+
Panel,
|
|
78
|
+
),
|
|
79
|
+
)
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
- `main` is a **keyed** root slot. `key` must equal the sidebar `id`.
|
|
83
|
+
- A sidebar id without a matching `main` key opens an empty page; a `main` key without
|
|
84
|
+
the sidebar id is unreachable.
|
|
85
|
+
- The panel owns its own layout, header, and content. It fills the same region as
|
|
86
|
+
`conversation`.
|
|
87
|
+
|
|
88
|
+
## Styling and localization
|
|
89
|
+
|
|
90
|
+
- Use theme tokens (`--dsw-alias-*`) and `currentColor`; do not hard-code brand colors
|
|
91
|
+
in the sidebar glyph.
|
|
92
|
+
- The host row supplies `.panelRow`, `.panelActive`, hover, focus, tooltip, and
|
|
93
|
+
`aria-current`.
|
|
94
|
+
- Register the locale namespace best-effort, and make the sidebar `label` read the
|
|
95
|
+
active locale. Do not re-register the row to change language.
|
|
96
|
+
|
|
97
|
+
## Verification
|
|
98
|
+
|
|
99
|
+
After installing or changing the plugin:
|
|
100
|
+
|
|
101
|
+
1. `Slots.listSubTree('sidebar.panellist')` must list the id with `active: true` and the
|
|
102
|
+
expected order.
|
|
103
|
+
2. `Slots.listSubTree('main')` must list the same key as an occupant.
|
|
104
|
+
3. Toggle the sidebar between wide and collapsed; the glyph must render at `16` and
|
|
105
|
+
`18` pixels respectively, with no clipping or colored background.
|
|
106
|
+
4. Switch `en`/`zh`; the row label must change without a reload or duplicate row.
|
|
107
|
+
5. Select the row and confirm the panel replaces the conversation region.
|
|
108
|
+
|
|
109
|
+
Client changes are picked up by HMR while the Web client watcher is running; a newly
|
|
110
|
+
installed bundle may need one page refresh before its module is present.
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
# Context Policy
|
|
2
|
+
|
|
3
|
+
## What to Load Automatically
|
|
4
|
+
|
|
5
|
+
For any non-trivial change, load:
|
|
6
|
+
|
|
7
|
+
- `docs/00-project/project-brief.md`
|
|
8
|
+
- `docs/00-project/current-state.md`
|
|
9
|
+
- `docs/01-architecture/design.md`
|
|
10
|
+
- `docs/01-architecture/detailed-design.md`
|
|
11
|
+
- `docs/01-architecture/module-boundaries.md`
|
|
12
|
+
- `docs/02-harness/harness-standard.md`
|
|
13
|
+
|
|
14
|
+
## What to Load by Task Type
|
|
15
|
+
|
|
16
|
+
### Adding or changing a tool
|
|
17
|
+
|
|
18
|
+
- `docs/01-architecture/tool-contract.md`
|
|
19
|
+
- `docs/01-architecture/detailed-design.md` §11
|
|
20
|
+
- `docs/04-development/coding-style.md`
|
|
21
|
+
- `docs/05-domain/operation-binding-template.md` (if routing related)
|
|
22
|
+
|
|
23
|
+
### Changing rule resolution
|
|
24
|
+
|
|
25
|
+
- `docs/01-architecture/design.md` §6
|
|
26
|
+
- `docs/01-architecture/module-boundaries.md`
|
|
27
|
+
- `docs/05-domain/rule-template.md`
|
|
28
|
+
|
|
29
|
+
### Changing the HTTP transport or the UI
|
|
30
|
+
|
|
31
|
+
- `docs/01-architecture/ui-design.md`
|
|
32
|
+
- `docs/01-architecture/decisions/ADR-0009-client-host-http-transport.md`
|
|
33
|
+
- `docs/01-architecture/security-model.md` §2, §4, §6
|
|
34
|
+
- `docs/04-development/coding-style.md`
|
|
35
|
+
|
|
36
|
+
### Checking a DSH runtime assumption
|
|
37
|
+
|
|
38
|
+
- `docs/01-architecture/api-verification.md`
|
|
39
|
+
|
|
40
|
+
### Deployment changes
|
|
41
|
+
|
|
42
|
+
- `docs/06-operations/deployment-guide.md`
|
|
43
|
+
- `docs/06-operations/security-policy.md`
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
# Harness Standard
|
|
2
|
+
|
|
3
|
+
## Purpose
|
|
4
|
+
|
|
5
|
+
The harness ensures that AI-assisted development remains aligned with the project architecture, constraints, and verification expectations.
|
|
6
|
+
|
|
7
|
+
## Harness Layers
|
|
8
|
+
|
|
9
|
+
### 1. Context Layer
|
|
10
|
+
|
|
11
|
+
Defines what the agent must know before work.
|
|
12
|
+
|
|
13
|
+
Includes:
|
|
14
|
+
|
|
15
|
+
- project brief
|
|
16
|
+
- current state
|
|
17
|
+
- design documents
|
|
18
|
+
- module boundaries
|
|
19
|
+
- storage contract
|
|
20
|
+
|
|
21
|
+
### 2. Constraint Layer
|
|
22
|
+
|
|
23
|
+
Defines what the agent must not violate.
|
|
24
|
+
|
|
25
|
+
Includes:
|
|
26
|
+
|
|
27
|
+
- no plain-text credentials in registry files
|
|
28
|
+
- no arbitrary JavaScript/shell execution in rule templates
|
|
29
|
+
- no auto-apply of production rule or skill changes
|
|
30
|
+
- no unbounded evidence storage
|
|
31
|
+
- no hidden durable state outside documented files
|
|
32
|
+
|
|
33
|
+
### 3. Execution Layer
|
|
34
|
+
|
|
35
|
+
Defines how work should be implemented.
|
|
36
|
+
|
|
37
|
+
Includes:
|
|
38
|
+
|
|
39
|
+
- small changes
|
|
40
|
+
- testable modules
|
|
41
|
+
- tools as thin wrappers over services
|
|
42
|
+
- business logic in resolver/router modules
|
|
43
|
+
- file-based state
|
|
44
|
+
- clear output file contracts
|
|
45
|
+
|
|
46
|
+
### 4. Verification Layer
|
|
47
|
+
|
|
48
|
+
Defines how work is validated.
|
|
49
|
+
|
|
50
|
+
Includes:
|
|
51
|
+
|
|
52
|
+
- unit tests for resolvers and routers
|
|
53
|
+
- fixture-based storage tests
|
|
54
|
+
- manual Web/Desktop UI checklist
|
|
55
|
+
- output file contract validation
|
|
56
|
+
- regression tests for bugfixes
|
|
57
|
+
|
|
58
|
+
### 5. Continuity Layer
|
|
59
|
+
|
|
60
|
+
Defines how future agents resume work.
|
|
61
|
+
|
|
62
|
+
Includes:
|
|
63
|
+
|
|
64
|
+
- update `current-state.md`
|
|
65
|
+
- update relevant docs
|
|
66
|
+
- preserve ADRs
|
|
67
|
+
- archive completed OpenSpec changes
|
|
68
|
+
- avoid hidden assumptions
|
|
69
|
+
|
|
70
|
+
## Required Agent Behavior
|
|
71
|
+
|
|
72
|
+
Before implementation:
|
|
73
|
+
|
|
74
|
+
1. Read the relevant docs.
|
|
75
|
+
2. Identify affected modules.
|
|
76
|
+
3. Identify storage contract impact.
|
|
77
|
+
4. Identify tests to add.
|
|
78
|
+
5. Keep scope small.
|
|
79
|
+
|
|
80
|
+
During implementation:
|
|
81
|
+
|
|
82
|
+
1. Prefer minimal changes.
|
|
83
|
+
2. Avoid unrelated refactoring.
|
|
84
|
+
3. Keep logic testable.
|
|
85
|
+
4. Preserve file-based architecture.
|
|
86
|
+
|
|
87
|
+
After implementation:
|
|
88
|
+
|
|
89
|
+
1. Run or specify tests.
|
|
90
|
+
2. Update docs if needed.
|
|
91
|
+
3. Update `docs/00-project/current-state.md`.
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
# Task Execution Policy
|
|
2
|
+
|
|
3
|
+
## Scope
|
|
4
|
+
|
|
5
|
+
Each task should be small enough to implement, test and review in one focused session.
|
|
6
|
+
|
|
7
|
+
## Task Format
|
|
8
|
+
|
|
9
|
+
Use the Tasks rule in `docs/03-openspec/tasks-rule.md`.
|
|
10
|
+
|
|
11
|
+
## Execution Order
|
|
12
|
+
|
|
13
|
+
1. Read context
|
|
14
|
+
2. Propose plan
|
|
15
|
+
3. Implement
|
|
16
|
+
4. Test
|
|
17
|
+
5. Update docs and current-state.md
|
|
18
|
+
|
|
19
|
+
## Stopping Conditions
|
|
20
|
+
|
|
21
|
+
Stop and report when:
|
|
22
|
+
|
|
23
|
+
- the task scope becomes unclear
|
|
24
|
+
- a storage contract change is required but not documented
|
|
25
|
+
- a security or approval policy implication is discovered
|
|
26
|
+
- tests fail and cannot be fixed within the task scope
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
# Verification Policy
|
|
2
|
+
|
|
3
|
+
Every implementation task must include at least one of:
|
|
4
|
+
|
|
5
|
+
- unit tests for pure logic
|
|
6
|
+
- integration tests for storage / registry / tools
|
|
7
|
+
- a manual UI checklist
|
|
8
|
+
- a contract check against a fixture
|
|
9
|
+
|
|
10
|
+
## Required by module
|
|
11
|
+
|
|
12
|
+
### `domain`
|
|
13
|
+
|
|
14
|
+
- Valid record accepted; unknown field rejected
|
|
15
|
+
- Id pattern and `schemaVersion` enforced
|
|
16
|
+
- Discriminated union rejects mismatched runtime/location
|
|
17
|
+
- `parseRecordInput` accepts omitted timestamps; `finalizeRecord` stamps them
|
|
18
|
+
|
|
19
|
+
### `storage`
|
|
20
|
+
|
|
21
|
+
- Atomic write/read round trip
|
|
22
|
+
- No temp file left after success or a caught failure
|
|
23
|
+
- Missing directory handled
|
|
24
|
+
- Invalid YAML skipped with diagnostic, file kept
|
|
25
|
+
- Backup pruning (max 5)
|
|
26
|
+
|
|
27
|
+
### `registry`
|
|
28
|
+
|
|
29
|
+
- Load and lookup
|
|
30
|
+
- Duplicate id detection
|
|
31
|
+
- Broken reference detection for every reference kind
|
|
32
|
+
- Reload after write reflects the change
|
|
33
|
+
- Concurrent loads share one in-flight scan
|
|
34
|
+
|
|
35
|
+
### `resolver`
|
|
36
|
+
|
|
37
|
+
- Layer precedence
|
|
38
|
+
- Field-level merge
|
|
39
|
+
- Provenance for the worked example
|
|
40
|
+
- Undefined variable, cycle, path traversal, type mismatch, malformed template
|
|
41
|
+
- Only runtime-applicable log source and class location resolved
|
|
42
|
+
|
|
43
|
+
### `router`
|
|
44
|
+
|
|
45
|
+
- Every match level
|
|
46
|
+
- Highest-level selection
|
|
47
|
+
- Same-level conflict
|
|
48
|
+
- Skill availability: present, missing, source mismatch, provider mismatch,
|
|
49
|
+
registry unavailable or incomplete
|
|
50
|
+
- Production policy and approval defaults
|
|
51
|
+
- Parameter mapping failures
|
|
52
|
+
|
|
53
|
+
### `session`
|
|
54
|
+
|
|
55
|
+
- Set, get, clear
|
|
56
|
+
- Cross-session isolation
|
|
57
|
+
- Corrupt state treated as "no default", `persisted: false`
|
|
58
|
+
|
|
59
|
+
### `app`
|
|
60
|
+
|
|
61
|
+
- Save→get round trip
|
|
62
|
+
- Delete refused while referenced
|
|
63
|
+
- Dry-run writes nothing
|
|
64
|
+
- UI actor production denial
|
|
65
|
+
|
|
66
|
+
### `tools`
|
|
67
|
+
|
|
68
|
+
- Returned value matches the declared `output.schema`
|
|
69
|
+
- Expected failures throw `EnvManagerError` with the right code
|
|
70
|
+
- No credential value in serialized output
|
|
71
|
+
- `env_validate` is read-only
|
|
72
|
+
- Approval denial changes nothing on disk
|
|
73
|
+
|
|
74
|
+
### `transport`
|
|
75
|
+
|
|
76
|
+
- Header, origin, method and size rejection
|
|
77
|
+
- Status mapping for each error class
|
|
78
|
+
- Production UI write denied by default
|
|
79
|
+
- No stack trace or file path in the response body
|
|
80
|
+
|
|
81
|
+
### Client UI (manual)
|
|
82
|
+
|
|
83
|
+
- Panels load with empty and populated registries
|
|
84
|
+
- Create/edit/delete round trip through the HTTP API
|
|
85
|
+
- Rule preview shows provenance
|
|
86
|
+
- Conflict warning appears for same-level bindings
|
|
87
|
+
- Production actions are visually distinct and confirmed
|
|
88
|
+
- Locale switches between `en` and `zh`
|
|
89
|
+
- Full checklist: `docs/01-architecture/ui-design.md` §12
|
|
90
|
+
|
|
91
|
+
## Evidence to record
|
|
92
|
+
|
|
93
|
+
For each completed task, `current-state.md` should state what was verified and what remains manual.
|
|
94
|
+
|
|
95
|
+
## Regression rule
|
|
96
|
+
|
|
97
|
+
A bugfix must add a test that fails before the fix and passes after it, unless the defect is UI-only.
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# Archive Rule
|
|
2
|
+
|
|
3
|
+
Completed or superseded proposals and designs must be archived in `docs/99-archive/`.
|
|
4
|
+
|
|
5
|
+
## When to Archive
|
|
6
|
+
|
|
7
|
+
- A proposal is implemented and verified.
|
|
8
|
+
- A design is superseded by a new one.
|
|
9
|
+
- A spike or experiment is abandoned.
|
|
10
|
+
|
|
11
|
+
## Format
|
|
12
|
+
|
|
13
|
+
Prefix archived files with date:
|
|
14
|
+
|
|
15
|
+
```text
|
|
16
|
+
docs/99-archive/YYYY-MM-DD-proposal-name.md
|
|
17
|
+
```
|
|
18
|
+
|
|
19
|
+
## Content
|
|
20
|
+
|
|
21
|
+
Each archived file must include:
|
|
22
|
+
|
|
23
|
+
- Original title and date
|
|
24
|
+
- Reason for archiving
|
|
25
|
+
- Link to the current approach (if superseded)
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
# Bugfix Rule
|
|
2
|
+
|
|
3
|
+
A bugfix addresses a specific, reproducible defect.
|
|
4
|
+
|
|
5
|
+
## Required Sections
|
|
6
|
+
|
|
7
|
+
### 1. Symptom
|
|
8
|
+
|
|
9
|
+
What went wrong.
|
|
10
|
+
|
|
11
|
+
### 2. Root Cause
|
|
12
|
+
|
|
13
|
+
Why it happened.
|
|
14
|
+
|
|
15
|
+
### 3. Fix
|
|
16
|
+
|
|
17
|
+
What changed.
|
|
18
|
+
|
|
19
|
+
### 4. Regression Test
|
|
20
|
+
|
|
21
|
+
Test that prevents recurrence.
|
|
22
|
+
|
|
23
|
+
### 5. Verification
|
|
24
|
+
|
|
25
|
+
How to confirm the fix.
|
|
26
|
+
|
|
27
|
+
## Rules
|
|
28
|
+
|
|
29
|
+
- Include a regression test unless the bug is UI-only.
|
|
30
|
+
- Update `current-state.md` if the bug affects implemented features.
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# Design Rule
|
|
2
|
+
|
|
3
|
+
A design document explains how a feature will be built.
|
|
4
|
+
|
|
5
|
+
## Required Sections
|
|
6
|
+
|
|
7
|
+
### 1. Overview
|
|
8
|
+
|
|
9
|
+
What is being designed and why.
|
|
10
|
+
|
|
11
|
+
### 2. Data Flow
|
|
12
|
+
|
|
13
|
+
Step-by-step flow with input/output boundaries.
|
|
14
|
+
|
|
15
|
+
### 3. Module Allocation
|
|
16
|
+
|
|
17
|
+
Which modules are involved and what each owns.
|
|
18
|
+
|
|
19
|
+
### 4. Schema Changes
|
|
20
|
+
|
|
21
|
+
New or changed YAML/JSON schemas.
|
|
22
|
+
|
|
23
|
+
### 5. Security Considerations
|
|
24
|
+
|
|
25
|
+
Credential handling, approval policies, production access.
|
|
26
|
+
|
|
27
|
+
### 6. Error Handling
|
|
28
|
+
|
|
29
|
+
Expected failure modes and responses.
|
|
30
|
+
|
|
31
|
+
### 7. Verification Plan
|
|
32
|
+
|
|
33
|
+
Tests and manual checks.
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
# OpenSpec Usage Guide
|
|
2
|
+
|
|
3
|
+
Use OpenSpec artifacts to plan and track changes.
|
|
4
|
+
|
|
5
|
+
## Artifact Types
|
|
6
|
+
|
|
7
|
+
- **Proposal**: Why and what we will change.
|
|
8
|
+
- **Design**: How we will build it.
|
|
9
|
+
- **Spec**: Detailed implementation contract.
|
|
10
|
+
- **Tasks**: Small, verifiable work items.
|
|
11
|
+
- **Bugfix**: Specific defect resolution.
|
|
12
|
+
|
|
13
|
+
## Workflow
|
|
14
|
+
|
|
15
|
+
1. Create a proposal in `docs/03-openspec/proposals/` (or similar).
|
|
16
|
+
2. Once accepted, write a design in `docs/01-architecture/designs/` (or update `design.md`).
|
|
17
|
+
3. Turn the design into a spec.
|
|
18
|
+
4. Break into tasks.
|
|
19
|
+
5. Implement, verify, archive.
|
|
20
|
+
|
|
21
|
+
## Naming
|
|
22
|
+
|
|
23
|
+
- Proposals: `proposal-{short-name}.md`
|
|
24
|
+
- Designs: `design-{short-name}.md`
|
|
25
|
+
- Specs: `spec-{short-name}.md`
|
|
26
|
+
- Tasks: embedded in implementation issue or PR description
|
|
27
|
+
- Bugfixes: `bugfix-{short-name}.md`
|
|
28
|
+
|
|
29
|
+
## Review
|
|
30
|
+
|
|
31
|
+
Every OpenSpec artifact should be reviewed before implementation.
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
# Proposal Rule
|
|
2
|
+
|
|
3
|
+
A proposal must explain why the change is needed and what it changes.
|
|
4
|
+
|
|
5
|
+
## Required Sections
|
|
6
|
+
|
|
7
|
+
### 1. Problem
|
|
8
|
+
|
|
9
|
+
Describe the user-visible or engineering problem.
|
|
10
|
+
|
|
11
|
+
### 2. Goal
|
|
12
|
+
|
|
13
|
+
Describe the intended outcome.
|
|
14
|
+
|
|
15
|
+
### 3. Scope
|
|
16
|
+
|
|
17
|
+
List what is included.
|
|
18
|
+
|
|
19
|
+
### 4. Out of Scope
|
|
20
|
+
|
|
21
|
+
List what is explicitly excluded.
|
|
22
|
+
|
|
23
|
+
### 5. Affected Modules
|
|
24
|
+
|
|
25
|
+
Choose from:
|
|
26
|
+
|
|
27
|
+
- tools
|
|
28
|
+
- domain
|
|
29
|
+
- config
|
|
30
|
+
- storage
|
|
31
|
+
- registry
|
|
32
|
+
- resolver
|
|
33
|
+
- router
|
|
34
|
+
- session
|
|
35
|
+
- memory-bridge
|
|
36
|
+
- client
|
|
37
|
+
- docs
|
|
38
|
+
|
|
39
|
+
### 6. Storage Impact
|
|
40
|
+
|
|
41
|
+
State whether the change affects:
|
|
42
|
+
|
|
43
|
+
- `data/environments/*.yaml`
|
|
44
|
+
- `data/services/*.yaml`
|
|
45
|
+
- `data/deployments/*.yaml`
|
|
46
|
+
- `data/rules/*.yaml`
|
|
47
|
+
- `data/operations/*.yaml`
|
|
48
|
+
- `data/sessions/*.json`
|
|
49
|
+
- `schemaVersion` (record compatibility)
|
|
50
|
+
|
|
51
|
+
### 7. Constraints
|
|
52
|
+
|
|
53
|
+
Must confirm:
|
|
54
|
+
|
|
55
|
+
- No plain-text credentials introduced.
|
|
56
|
+
- No arbitrary code execution in rule templates.
|
|
57
|
+
- No auto-apply of production changes.
|
|
58
|
+
- File-based source of truth remains unchanged.
|
|
59
|
+
|
|
60
|
+
### 8. Risks
|
|
61
|
+
|
|
62
|
+
List implementation risks.
|
|
63
|
+
|
|
64
|
+
### 9. Verification
|
|
65
|
+
|
|
66
|
+
Describe how to verify.
|
|
67
|
+
|
|
68
|
+
## Proposal Quality Bar
|
|
69
|
+
|
|
70
|
+
A good proposal is small enough to implement and test in one focused change.
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# Spec Rule
|
|
2
|
+
|
|
3
|
+
A spec document turns a proposal into actionable implementation details.
|
|
4
|
+
|
|
5
|
+
## Required Sections
|
|
6
|
+
|
|
7
|
+
### 1. Objectives
|
|
8
|
+
|
|
9
|
+
Clear, measurable outcomes.
|
|
10
|
+
|
|
11
|
+
### 2. Functional Requirements
|
|
12
|
+
|
|
13
|
+
What the system must do.
|
|
14
|
+
|
|
15
|
+
### 3. Non-functional Requirements
|
|
16
|
+
|
|
17
|
+
Performance, security, compatibility constraints.
|
|
18
|
+
|
|
19
|
+
### 4. Interface Definitions
|
|
20
|
+
|
|
21
|
+
Tool names, parameters, return values, events.
|
|
22
|
+
|
|
23
|
+
### 5. Data Definitions
|
|
24
|
+
|
|
25
|
+
Schemas for inputs, outputs and storage records.
|
|
26
|
+
|
|
27
|
+
### 6. Acceptance Criteria
|
|
28
|
+
|
|
29
|
+
Specific conditions that must be met.
|
|
30
|
+
|
|
31
|
+
### 7. Open Questions
|
|
32
|
+
|
|
33
|
+
Unresolved items to confirm before implementation.
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
# Tasks Rule
|
|
2
|
+
|
|
3
|
+
Tasks must be small and verifiable.
|
|
4
|
+
|
|
5
|
+
## Task Format
|
|
6
|
+
|
|
7
|
+
```markdown
|
|
8
|
+
- [ ] Task name
|
|
9
|
+
- Files:
|
|
10
|
+
- Behavior:
|
|
11
|
+
- Tests:
|
|
12
|
+
- Verification:
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
## Rules
|
|
16
|
+
|
|
17
|
+
- Do not combine unrelated modules in one task.
|
|
18
|
+
- Do not add broad refactoring tasks.
|
|
19
|
+
- Every implementation task must include tests or manual verification.
|
|
20
|
+
- Docs must be updated when behavior or storage contract changes.
|
|
21
|
+
- `docs/00-project/current-state.md` must be updated at the end.
|
|
22
|
+
|
|
23
|
+
## Good Task Example
|
|
24
|
+
|
|
25
|
+
```markdown
|
|
26
|
+
- [ ] Implement environment registry storage
|
|
27
|
+
- Files: src/storage/environment.js, tests/storage/environment.test.js
|
|
28
|
+
- Behavior: read/write environment records atomically
|
|
29
|
+
- Tests: create, read, update, missing file
|
|
30
|
+
- Verification: npm test tests/storage/environment.test.js
|
|
31
|
+
```
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
# Coding Style
|
|
2
|
+
|
|
3
|
+
## TypeScript (Host)
|
|
4
|
+
|
|
5
|
+
- `strict: true`; do not disable it locally.
|
|
6
|
+
- Prefer `interface` for records, `type` for unions and aliases.
|
|
7
|
+
- No `any` at module boundaries. Use `unknown` and validate.
|
|
8
|
+
- Validate all external input (YAML, tool arguments) with Zod.
|
|
9
|
+
- Prefer `readonly` for data that must not be mutated.
|
|
10
|
+
- Pure functions (`resolver`, `router`, `domain`) return discriminated unions for
|
|
11
|
+
expected failures:
|
|
12
|
+
|
|
13
|
+
```ts
|
|
14
|
+
type ResolveResult =
|
|
15
|
+
| { ok: true; context: ServiceContext }
|
|
16
|
+
| { ok: false; diagnostics: Diagnostic[] };
|
|
17
|
+
```
|
|
18
|
+
|
|
19
|
+
- Tool and HTTP boundaries throw `EnvManagerError extends HarnessError`; they never
|
|
20
|
+
return an `{ ok: false }` value. Catch unexpected errors and wrap them as
|
|
21
|
+
`INTERNAL_ERROR` with a redacted message.
|
|
22
|
+
- No floating promises. Await or return them.
|
|
23
|
+
|
|
24
|
+
## Purity
|
|
25
|
+
|
|
26
|
+
- `resolver` and `router` are pure: no I/O, no clock, no randomness, no globals.
|
|
27
|
+
- Inject dependencies (`SkillDirectory`, `CredentialDirectory`) as parameters.
|
|
28
|
+
- Storage and registry may hold state; keep it inside instances, not module scope.
|
|
29
|
+
|
|
30
|
+
## Naming
|
|
31
|
+
|
|
32
|
+
| Kind | Style | Example |
|
|
33
|
+
|---|---|---|
|
|
34
|
+
| files | kebab-case | `service-context.ts` |
|
|
35
|
+
| types/interfaces | PascalCase | `DeploymentBinding` |
|
|
36
|
+
| functions | camelCase | `resolveContext` |
|
|
37
|
+
| constants | UPPER_SNAKE_CASE | `WRITE_OPERATIONS` |
|
|
38
|
+
| record ids | kebab-case | `deploy-001` |
|
|
39
|
+
|
|
40
|
+
## Error handling
|
|
41
|
+
|
|
42
|
+
- Every failure carries a `code` from the diagnostics catalogue.
|
|
43
|
+
- Messages are user-facing and must not include secrets.
|
|
44
|
+
- Never swallow an error silently. If it is expected, convert it to a diagnostic.
|
|
45
|
+
|
|
46
|
+
## JavaScript (Client)
|
|
47
|
+
|
|
48
|
+
- ES modules; the artifact is the module-loader wrapper.
|
|
49
|
+
- `React.createElement` (`h(...)`), no JSX.
|
|
50
|
+
- No global side effects at module load beyond `load({...})`.
|
|
51
|
+
- Register slots with `ctx.slots.inject` (it owns cleanup); wrap any other listener or
|
|
52
|
+
disposable in `ctx.effect` and return its cleanup.
|
|
53
|
+
- Route visible text through the client locale service.
|
|
54
|
+
|
|
55
|
+
## Formatting
|
|
56
|
+
|
|
57
|
+
- 2 spaces
|
|
58
|
+
- single quotes
|
|
59
|
+
- no semicolons
|
|
60
|
+
- trailing commas in multi-line literals
|
|
61
|
+
- LF line endings
|
|
62
|
+
|
|
63
|
+
## Comments
|
|
64
|
+
|
|
65
|
+
- JSDoc on exported functions and non-obvious invariants.
|
|
66
|
+
- Explain why, not what.
|
|
67
|
+
- Reference the design section when implementing a non-trivial rule, e.g. `// design §6.4`.
|