owfadev 0.0.1 → 0.3.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.
Files changed (99) hide show
  1. package/.agents/skills/asset-read/SKILL.md +39 -0
  2. package/.agents/skills/check/SKILL.md +130 -0
  3. package/.agents/skills/docs/SKILL.md +24 -0
  4. package/.agents/skills/map/SKILL.md +72 -0
  5. package/.agents/skills/plugin/SKILL.md +74 -0
  6. package/.agents/skills/profile/SKILL.md +75 -0
  7. package/.agents/skills/query/SKILL.md +48 -0
  8. package/.agents/skills/save/SKILL.md +94 -0
  9. package/.agents/skills/wiki_plugin_kernel/SKILL.md +104 -0
  10. package/.meta/VERSION +1 -0
  11. package/.meta/command/asset-read/SKILL.md +39 -0
  12. package/.meta/command/check/SKILL.md +130 -0
  13. package/.meta/command/docs/SKILL.md +24 -0
  14. package/.meta/command/map/SKILL.md +72 -0
  15. package/.meta/command/plugin/SKILL.md +74 -0
  16. package/.meta/command/profile/SKILL.md +75 -0
  17. package/.meta/command/query/SKILL.md +48 -0
  18. package/.meta/command/save/SKILL.md +94 -0
  19. package/.meta/command/wiki_plugin_kernel/SKILL.md +104 -0
  20. package/.meta/docs/agent-behavior.md +68 -0
  21. package/.meta/docs/agents-example.md +34 -0
  22. package/.meta/docs/conversion.md +24 -0
  23. package/.meta/docs/deployment.md +311 -0
  24. package/.meta/docs/developer.md +33 -0
  25. package/.meta/docs/distribution.md +132 -0
  26. package/.meta/docs/intro.md +56 -0
  27. package/.meta/docs/log-example.md +19 -0
  28. package/.meta/docs/map.md +23 -0
  29. package/.meta/docs/mechanics.md +180 -0
  30. package/.meta/docs/naming.md +113 -0
  31. package/.meta/docs/packages.md +130 -0
  32. package/.meta/docs/quickstart.md +79 -0
  33. package/.meta/docs/research-landscape.md +132 -0
  34. package/.meta/docs/research-user-profile.md +27 -0
  35. package/.meta/docs/sandbox.md +40 -0
  36. package/.meta/docs/usage.md +45 -0
  37. package/.meta/plugins/core/calendar/PLUGIN.md +35 -0
  38. package/.meta/plugins/core/calendar/PLUGIN.yaml +21 -0
  39. package/.meta/plugins/core/cron/PLUGIN.md +38 -0
  40. package/.meta/plugins/core/cron/PLUGIN.yaml +24 -0
  41. package/.meta/plugins/core/device/PLUGIN.md +38 -0
  42. package/.meta/plugins/core/device/PLUGIN.yaml +21 -0
  43. package/.meta/plugins/core/device/scripts/check.py +29 -0
  44. package/.meta/plugins/core/domain/PLUGIN.md +43 -0
  45. package/.meta/plugins/core/domain/PLUGIN.yaml +8 -0
  46. package/.meta/plugins/core/hot/PLUGIN.md +40 -0
  47. package/.meta/plugins/core/hot/PLUGIN.yaml +15 -0
  48. package/.meta/plugins/core/index/PLUGIN.md +39 -0
  49. package/.meta/plugins/core/index/PLUGIN.yaml +18 -0
  50. package/.meta/plugins/core/instance-git/PLUGIN.md +39 -0
  51. package/.meta/plugins/core/instance-git/PLUGIN.yaml +15 -0
  52. package/.meta/plugins/core/instance-git/scripts/check.py +90 -0
  53. package/.meta/plugins/core/language/PLUGIN.md +38 -0
  54. package/.meta/plugins/core/language/PLUGIN.yaml +23 -0
  55. package/.meta/plugins/core/language/scripts/check.py +23 -0
  56. package/.meta/plugins/core/link/PLUGIN.md +39 -0
  57. package/.meta/plugins/core/link/PLUGIN.yaml +16 -0
  58. package/.meta/plugins/core/link/scripts/check.py +122 -0
  59. package/.meta/plugins/core/log/PLUGIN.md +58 -0
  60. package/.meta/plugins/core/log/PLUGIN.yaml +18 -0
  61. package/.meta/plugins/core/log/scripts/check.py +21 -0
  62. package/.meta/plugins/core/mapping/PLUGIN.md +32 -0
  63. package/.meta/plugins/core/mapping/PLUGIN.yaml +24 -0
  64. package/.meta/plugins/core/mapping/scripts/check.py +90 -0
  65. package/.meta/plugins/core/notes/PLUGIN.md +42 -0
  66. package/.meta/plugins/core/notes/PLUGIN.yaml +19 -0
  67. package/.meta/plugins/core/sessions/PLUGIN.md +63 -0
  68. package/.meta/plugins/core/sessions/PLUGIN.yaml +20 -0
  69. package/.meta/plugins/core/sessions/scripts/check.py +33 -0
  70. package/.meta/plugins/core/structure/PLUGIN.md +29 -0
  71. package/.meta/plugins/core/structure/PLUGIN.yaml +18 -0
  72. package/.meta/plugins/core/structure/scripts/check.py +32 -0
  73. package/.meta/plugins/core/tag/PLUGIN.md +37 -0
  74. package/.meta/plugins/core/tag/PLUGIN.yaml +18 -0
  75. package/.meta/plugins/core/tag/scripts/check.py +28 -0
  76. package/.meta/plugins/core/tmp/PLUGIN.md +26 -0
  77. package/.meta/plugins/core/tmp/PLUGIN.yaml +16 -0
  78. package/.meta/plugins/core/todo/PLUGIN.md +33 -0
  79. package/.meta/plugins/core/todo/PLUGIN.yaml +22 -0
  80. package/.meta/plugins/core/trust/PLUGIN.md +70 -0
  81. package/.meta/plugins/core/trust/PLUGIN.yaml +23 -0
  82. package/.meta/plugins/core/trust/scripts/check.py +77 -0
  83. package/.meta/plugins/core/user-profile/PLUGIN.md +39 -0
  84. package/.meta/plugins/core/user-profile/PLUGIN.yaml +30 -0
  85. package/.meta/plugins/core/vault/PLUGIN.md +28 -0
  86. package/.meta/plugins/core/vault/PLUGIN.yaml +13 -0
  87. package/.meta/plugins/core/wiki/PLUGIN.md +37 -0
  88. package/.meta/plugins/core/wiki/PLUGIN.yaml +8 -0
  89. package/.meta/protocol/actions.md +42 -0
  90. package/.meta/protocol/experiments.md +40 -0
  91. package/.meta/protocol/registry.yaml +75 -0
  92. package/.meta/scripts/pipeline.py +428 -0
  93. package/.meta/scripts/wiki_plugin_kernel.py +1846 -0
  94. package/.meta/scripts/wikilib.py +79 -0
  95. package/LICENSE +21 -21
  96. package/README.md +98 -15
  97. package/bin/owfa.js +540 -0
  98. package/package.json +36 -7
  99. package/templates/AGENTS.template.md +19 -0
@@ -0,0 +1,180 @@
1
+ # Mechanics in Detail
2
+
3
+ > Audience: members and contributors who will modify the framework. The authoritative source of mechanical rules is the kernel reference skill and the `.meta/` source code. This document expands the master outline by one level — principles, instance walkthroughs, and hands-on procedures — without copying rule text; where it conflicts with the source, the source prevails. Written 2026-10-04.
4
+
5
+ ## 0. One Source, Five Projections
6
+
7
+ Each plugin is one directory, living at `.meta/plugins/<id>/`. `PLUGIN.yaml` is the machine-readable body — the manifest. From the manifest, the kernel script mechanically projects into five places:
8
+
9
+ | Projection | Landing point | Source key | Who reads it |
10
+ |---|---|---|---|
11
+ | AGENTS injection region | `<!-- plugin:<id> v<x> -->` marker block | `inject` | The agent of every session; constitution-level disclosure |
12
+ | check inspection block | the `check-inject` block inside the check command | `checks` | The check command; semantic items |
13
+ | command usage block | the `cmd-inject` block inside each command | `usage`, in consumes order | Command execution sites; write-side rules |
14
+ | registry plugin section | `.meta/protocol/registry.yaml` | `fields` | Commands consulting the field vocabulary before writing pages |
15
+ | skill copy | `.agents/skills/<command>/` | command and connector masters | Deployment-side agents |
16
+
17
+ The key property is idempotent rebuilding. Hand-editing inside marker blocks is forbidden — a rebuild overwrites; prose outside the blocks belongs to humans. There is no second source of truth: changing a rule means changing the manifest, after which the single command `all` converges everything. The whole class of documentation-drift problems is eliminated wholesale — projections and the body cannot disagree, because they are not two separate things.
18
+
19
+ Walk through one real sample. In bb-quiz's manifest, `inject:` is a single one-line disclosure stating what the quiz self-test does and where its products land. After `all` runs, that line appears verbatim in the AGENTS injection region inside the `<!-- plugin:bb-quiz v0.2 -->` block. What agents read day to day is the projection; the manifest body is touched only when (un)installing plugins.
20
+
21
+ ## 1. Plugin Shape
22
+
23
+ One plugin, one directory, three pieces:
24
+
25
+ - `PLUGIN.yaml` — the manifest, the body
26
+ - `PLUGIN.md` — pure documentation: design summary, Structure, Invariants, Changelog. The why of the design lives here; mechanical commonality belongs to the kernel reference
27
+ - `scripts/check.py` — optional attached audit. Defines `check(ctx)` returning `[{level, message}]`, read-only with zero side effects; the shape is statically validated via AST
28
+
29
+ Seven required manifest keys, illustrated with real values from bb-quiz v0.2:
30
+
31
+ | Key | Semantics | Instance |
32
+ |---|---|---|
33
+ | `id` / `version` / `updated` | Identity and version; advance along the changelog without skipping numbers | `bb-quiz` / `0.2` / `2026-10-04` |
34
+ | `depends` | Dependency list | `[bb-track, bb-map]` |
35
+ | `attachment` | Territory declaration: owning means writing, borrowing means read-only consumption | see below |
36
+ | `fields` | The plugin's own page fields; enter the registry's global vocabulary | `quiz`, the exam-paper block mapping |
37
+ | `inject` | The source of the injection-region line; constitution-level disclosure | see the AGENTS bb-quiz block |
38
+
39
+ Four optional keys. `commands` declares the commands this plugin drives; `usage` is the write-side rule list; `checks` is the inspection rules; `bridge` is the bridge declaration, which only global pieces may hold.
40
+
41
+ A fifth optional key `inject_tier` (full|member, default full) carries the **tier law** (issue #12 layer discipline): member exits the AGENTS injection region — exposure rides on the family root's roster line, the skill catalog, and on-demand reads of the manifest, and validate requires a member to reach a full-tier domain root through depends. The projected region carries a byte budget (15 KiB), keeping the A layer pointer-dense: pointers and red lines, never procedures or formats (contract in `protocol/experiments.md`).
42
+
43
+ attachment deserves a closer look. bb-quiz declares three entries:
44
+
45
+ - `bb/<term>/<course>/notes/testing/` is the exam-paper sub-region, owned by this plugin. Each test run adds a question set plus answers; grading is appended on the answer page
46
+ - `wiki/bb/<term>/<course>/user.md` is the cognition profile, owned by bb-track. This plugin reads it only; grading writes back through bb-track's write rules
47
+ - `courseware/` and `assessments/` belong to bb-map. This plugin reads them only, taking sm-N anchors, the terminology table, and known assignments
48
+
49
+ The first is ownership; the latter two are borrows: the territory belongs to another plugin, and write paths must pass through its rules. attachment is the framework's property registry. Who owns which paths, who read-only consumes whom — visible at a glance, mechanically checkable.
50
+
51
+ ## 2. Dependencies and Injection Order
52
+
53
+ `depends` declares dependencies. validate checks two things: dependencies exist, and there are no cycles — cycles are detected via DFS.
54
+
55
+ A domain piece is any plugin whose depends chain reaches `domain`. Those connecting to domain directly are domain bases — the five pieces vault, lark, project, email, bb; pieces inside a domain belong to it transitively, without connecting directly. bb-quiz does not connect to domain directly: it arrives via `bb-quiz → bb-track → bb-map → bb → domain`, and is thus a domain piece.
56
+
57
+ Injection order = dependency topology plus alphabetical order within a batch: dependees are injected first; same-batch pieces sort by name. Look at the bb family's depends and the real order in the injection region:
58
+
59
+ | Plugin | depends | Effect |
60
+ |---|---|---|
61
+ | bb | `[domain, wiki, trust, log]` | Domain base, injected first within the family |
62
+ | bb-map | `[bb, wiki]` | Mapping law, after bb |
63
+ | bb-track | `[bb, bb-map, trust, wiki]` | Cognition profile, after bb-map |
64
+ | bb-quiz / bb-teach | `[bb-track, bb-map]` | Collection channels; same batch sorted by name — quiz before teach |
65
+
66
+ This guarantees one thing: when a consumer-side plugin is injected, the disclosures it consumes are already present. bb-teach's injection line says "discipline, see the bb-track block" — that block is necessarily above it. There is one more domain discipline: a domain must be discoverable inside the wiki, via declaration page or injection line; domain pieces create no root containers.
67
+
68
+ ## 3. Projection Walkthrough
69
+
70
+ Suppose you want to add one discipline to bb-quiz's write-side rules — here is what happens:
71
+
72
+ 1. Edit the `usage:` list in `.meta/plugins/bb-quiz/PLUGIN.yaml` and add a line. While at it, bump `version` and refresh `updated`; add a line to PLUGIN.md's Changelog
73
+ 2. Run `python .meta/scripts/wiki_plugin_kernel.py all`. In sequence: validate goes first — failure blocks, fix and rerun; if the inject line changed too, the AGENTS injection region is rebuilt; the cmd-inject blocks of the two command SKILL masters bb-quiz and bb-track are rebuilt — the usage appears in every command whose consumes includes bb-quiz; the registry plugin section is rebuilt; skill copies are synced
74
+ 3. Self-review the diff. Changes should land only in the manifest, the two command SKILL masters, and the `.agents/skills/` copies; if inject or fields changed, AGENTS and registry change as well. Any change beyond these is an anomaly
75
+ 4. Commit in the format `plugin: bb-quiz …`; one commit does one thing
76
+
77
+ This is the everyday feel of "one source, five projections": you wrote one thing, and five places agree automatically.
78
+
79
+ ## 4. Command Binding
80
+
81
+ owner and commands are mutual declarations. A command's SKILL.md frontmatter writes `owner: <plugin-id>`, or `framework` to mean explicitly ownerless; a plugin manifest writes `commands: [command names]`. A one-sided declaration on either side is a validate error — preventing unowned commands and plugins falsely claiming commands alike.
82
+
83
+ Usage lands on commands by two routes. **Pull side**: a command's frontmatter writes `consumes: [plugin list]`, declaring which plugins' usage it pulls; owner-driven commands must fill it in and include all owners. **Source-side routing**: a plugin manifest writes `usage_routes: [command name list]`, declaring which additional commands its usage lands on — installing the plugin lands the projection, with no need to edit destination commands. Presence-as-registration is honored on the push side: (un)installing a single file takes effect. validate checks that routing targets are present, that routing plugins carry usage, and that duplication with consumes is an error.
84
+
85
+ Disclosure order is presentation order: owner blocks first, in consumes order; routed blocks in the middle, in dependency topology plus alphabetical order; the remaining consumes bring up the rear.
86
+
87
+ First-case walkthrough: the bb-track command, this cognition hub. The bb-track command declares only `consumes: [bb-track, trust, log]`; bb-teach and bb-quiz each declare `usage_routes: [bb-track]` in their manifests. After `all`, the bb-track command's SKILL.md contains five `<!-- usage:<id> -->` sub-blocks: bb-track's own write rules, the full usage of the two collection channels bb-quiz and bb-teach, and the write-side rules of trust and log. The effect: any agent stepping into the bb-track command site gets — in one place, with zero retrieval — how teaching and quizzing are used, how grading flows back, and what to do after writes. To establish a third collection channel later, the new plugin only needs well-written usage plus a routing declaration; the projection arrives automatically and the hub command changes not one character.
88
+
89
+ Usage routing is inspectable at any time via `ls`: every plugin carrying usage lists the commands it lands on; those with no landing are marked as the contract-documentation surface — e.g. email's write-side contract, declared ahead of use.
90
+
91
+ ## 5. The Bridge Law
92
+
93
+ Global pieces are cross-cutting services and destinations: trust, log, todo, calendar, notes, user-profile. They may declare bridges; a domain piece holding a bridge is an error.
94
+
95
+ A must-attach bridge is written in the manifest as `bridge: 必依`: every domain base must have a depends edge to the piece; a missing edge is a validate error. log is an instance — the `log` edge in bb's depends in the section 2 table is forced by the must-attach bridge: any domain's activity must leave a trace. This is a topology-completeness invariant, not a style suggestion.
96
+
97
+ An on-demand bridge is written as `bridge: 按需`: absence is tolerated. user-profile's cognition bridge is an instance — bb-track registers one line only if the profile is present when it creates the archive; if absent it skips, creating nothing on the profile's behalf and raising no error.
98
+
99
+ Why consumes cannot replace bridges — the 2026-10-04 ruling gives two hard reasons:
100
+
101
+ 1. Must-attach completeness checking is a topological constraint. "All five domain bases, not one may lack an edge" is a global graph invariant; consumes is a single command's list and cannot express global completeness
102
+ 2. Writes across territories happen in every command execution. todo derivation, calendar derivation, notes emergence — none of them pass through some single-point command container; there is nowhere to hang consumes
103
+
104
+ Division of labor: the bridge holds validation and declaration — who may attach, cardinality, completeness checking, absence tolerance; disclosure distribution belongs to projection — the authoritative source of the integration format is usage, arriving at consumption sites via cmd-inject.
105
+
106
+ ## 6. The Derived Layer
107
+
108
+ The kernel governs the framework area — plugins and projections; pipeline governs the data area — wiki derived pages. The commands are `python .meta/scripts/pipeline.py index / tags / hot / log / verify`:
109
+
110
+ - **index / tags**: directory indexes and the tag reverse index. Pure-function rebuilds that only aggregate, never inventing structure; when an index list overflows the window, split the subdirectory into its own index — the cure is more subdirectories, not editing the index
111
+ - **hot**: the recent-change hot cache. At most 25 entries, within 5 days, each entry under 200 characters; agents read it first on entering the vault
112
+ - **log**: run-log line writing and rolling archive. Window at most 100 entries; overflow is mechanically archived to `wiki/archive/<month>/log.md`
113
+ - **verify**: post-write consistency check. The post-write pipelines of commands like map and save end with it
114
+
115
+ Derived pages and projections are two applications of one philosophy: projections derive from manifests — no second source on the framework side; derived pages derive from vault content — no second source on the data side. Hand-editing a derived page is futile; the next rebuild overwrites it.
116
+
117
+ ## 7. (Un)install Lifecycle
118
+
119
+ The semantic flow of (un)installing goes through the plugin command, where the agent does the semantic part; the mechanical steps are this CLI. Since the split (2026-10-12) **packages are the install unit and this lifecycle is kernel-driven** — the authoritative accounts live in [packages.md](packages.md) (package model, the migrations algebra, the uninstall contract) and in `.meta/command/plugin/SKILL.md` (the wizard protocol). What follows is the historical per-plugin flow, retained for the record; the install steps still describe authoring a new plugin inside the framework repo.
120
+
121
+ Install, five steps: prepare the three pieces under `.meta/plugins/<id>/`; `validate` — errors block; `all` — projections arrive; smoke test — `audit <id>`, plus a walk-through of the key flows per PLUGIN.md; log a plugin line.
122
+
123
+ Upgrade, three steps: edit the plugin, bump `version`, add a Changelog line; `all`; log line. Package-level upgrades (`kernel upgrade`) additionally stage semantic migrations — see packages.md.
124
+
125
+ Uninstall: superseded by the package-level `kernel uninstall <pkg> --yes` (four-clear + residual scan + teardown staging, see packages.md). The old per-plugin flow — `validate` blocks dependents → move the directory out (archived, physical deletion belongs to humans) → `all` — applied before packages existed.
126
+
127
+ Discipline: script errors always block, warnings only report; versions advance along the changelog — no pre-reserving or skipping numbers.
128
+
129
+ ## 8. How Domains Grow
130
+
131
+ The framework sets no whitelist for information sources outside the wiki. Integration is answering the same contract, and growth follows the same path. Follow the bb family through — it is the most complete family.
132
+
133
+ ### The Contract's Six Questions
134
+
135
+ Designing a domain is answering the questions one by one. The answers land in the domain base's territory declaration and injection line:
136
+
137
+ | Question | The bb family's answer |
138
+ |---|---|
139
+ | Where is the external territory | bb.cuhk.edu.cn, connector bb-cli purely read-only |
140
+ | Landing strategy | Isomorphic two sides: `bb/` workspace plus `wiki/bb/` territory |
141
+ | Identity proof | Term-name and course-code directories, plus machine ids in the bb block mapping |
142
+ | wiki-side territory | `wiki/bb/<term>/<course>/`, bb-map's four-bucket projection |
143
+ | Write model | Fetched artifacts append-only; notes/ human-led, ai products append-only without overwrite |
144
+ | Trust model | machine-confirmed ceiling; stale_after = fetch date + TTL |
145
+
146
+ ### Three Write Models
147
+
148
+ Landing is essentially a write-model choice, with three archetypes:
149
+
150
+ - **Final-state asset → append-only store**. Once landed, the body no longer changes — e.g. vault assets, bb materialized courseware. The command side is append-only; deletion and modification belong to humans
151
+ - **Process container → full read-write**. The agent works inside it — e.g. `projects/`, ai products in bb notes/
152
+ - **Truth lives elsewhere → pointer**. The source changes and no local copy is needed — e.g. lark pointer pages, bb media defaulting to pointers. stale_after governs freshness; the agent is the synchronizer
153
+
154
+ ### Projection Density
155
+
156
+ Projection density decreases as translation cost rises, in three grades. **Mirror**: a 1:1 proxy, e.g. mapping. **Pointer**: token plus url plus snapshot excerpts, e.g. lark. **Disclosure-only**: one injection line plus on-demand live pulls, e.g. email retrieval. The default posture is borrowing vault or pointers; self-standing containers are the exception — when: the write model forks, or the structure is rigidly dictated by the source. bb stands alone for its rigid two-sided structure.
157
+
158
+ ### The Growth Path
159
+
160
+ After the contract: the **domain base** establishes the territory — bb is isomorphic two sides plus notes/ cohabitation; the **in-domain piece family** follows — bb-map's projection law, bb-track's cognition profile, shapes growing heavier; **consumer-side collection channels** close it out — bb-teach and bb-quiz, zero territory, pure workflow, usage hung on hub commands via source-side routing. The in-family dependency chain `bb-quiz → bb-track → bb-map → bb` is the mechanical expression of this path — see section 2.
161
+
162
+ ### Material and Archives
163
+
164
+ A two-way split inside the domain. Process products live in the domain workspace: fetched artifacts, human notes, ai notes, exam papers and grading. Settled conclusions live in the wiki territory: projection pages, cognition readings. The wiki takes distillates, not process. This line is isomorphic to the global discipline, only landed inside the domain.
165
+
166
+ ### Connectors
167
+
168
+ Connectors live in `connectors/` — the domain's deployment-side CLI de-facto interface plus usage disclosure: `connectors/<name>/SKILL.md` lands as the `.agents/skills/` copy via kernel `deploy`. The difference from commands: commands are pure wiki operations, masters in `.meta/command/`; connectors are data-fetching channels to external systems — credentials stay on the local machine, never committed, never persisted to disk. Domain plugins declare territory and discipline; connectors provide the de-facto interface. Discipline and tooling are separate.
169
+
170
+ ## 9. Scenario Quick Reference
171
+
172
+ | You want to | Action |
173
+ |---|---|
174
+ | Change write-side rules / inspection rules / the injection line | Edit the corresponding manifest key, run `all` |
175
+ | Attach a new plugin's usage to a command | That plugin's manifest writes `usage`; the command's frontmatter consumes adds the id; run `all` |
176
+ | Edit a connector skill | Edit the `connectors/*/SKILL.md` master, run `deploy` or `all` |
177
+ | Quick health check | `validate` plus `audit`; full audit via the check command |
178
+ | (Un)install a plugin | The plugin command does semantics, this CLI does mechanics |
179
+ | Rebuild data-area derived pages | `pipeline.py index` or `tags`; hot and log are maintained as writes happen |
180
+ | Integrate a new external source | Answer the contract's six questions, see section 8; write a connector; the plugin command installs the domain base and in-domain pieces |
@@ -0,0 +1,113 @@
1
+ # The name
2
+
3
+ > **OWFA — One Workspace For All (agents).**
4
+ > Public framework: **OWFA Core** (proposed; `vault-wiki` retires from the public surface) · installer: **OWFA CLI** · GitHub: **owfadev** · npm: `owfa` (application pending) or `owfadev` (fallback).
5
+
6
+ This page exists because a name is a contract with the people who type it. It records what the words commit to, which layers must not be collapsed, where the name actually resolves, and what happens if a registry refuses the string.
7
+
8
+ ## The line
9
+
10
+ Use the expansion exactly as written. Do not expand it as *One Wiki For All* or *One Web For All* in any public text — the first is a different (smaller) claim, the second belongs to an unrelated GitHub organization. When the acronym has to stand alone, pair it with the parenthetical once per document, then use `OWFA`.
11
+
12
+ - 中文:**一个工作区,装下你所有的 agent。**
13
+ - 一句话:OWFA gives every agent you use one workspace to re-enter — your assets, your wiki, your instructions — instead of re-introducing yourself every session.
14
+ - Agent-facing: "This is an OWFA workspace: `vault/` holds real assets, `wiki/` holds the md world, `.meta/` + `.agents/skills/` are the framework body. Read AGENTS.md, then work from the indexes."
15
+
16
+ ## What each word commits to
17
+
18
+ **One** — one directory, one place a new session re-enters. Not one app that swallows every tool, and not one vendor account. The unit is a workspace the human owns and every agent reads.
19
+
20
+ **Workspace** — the outer object: `vault/` + `wiki/` + `AGENTS.md` + the framework body. The wiki is the *inner* markdown world; the workspace is what the user actually owns, moves, backs up, and points agents at. Naming the workspace rather than the wiki is deliberate: the contribution is the re-entry surface, not markdown as a format.
21
+
22
+ **For all (agents)** — all *your* agents: across harnesses (ZCode, Claude Code, Cursor, dsh…), across sessions, across time. It does **not** mean all people, all data, or a hosted service. The parenthetical is part of the name, not a footnote — it is what keeps the claim true. Humans stay the owner and the audit anchor; agents are the ones that re-enter with zero priors.
23
+
24
+ The name answers the project's actual starting pain: an agent that must be re-introduced every session. "One workspace for all agents" is that pain inverted.
25
+
26
+ ## Layers — do not collapse them
27
+
28
+ | Layer | Name | Lives in | Job |
29
+ |---|---|---|---|
30
+ | Product | **OWFA** | README, npm page, docs | the brand |
31
+ | Framework | **OWFA Core** (proposed) | `.meta/` + `.agents/skills/` | the body that is installed into a workspace |
32
+ | Installer | **OWFA CLI** | `bin/owfa.js` (npm package) | fetch the tree, `init`, `upgrade`, `doctor`, `add` |
33
+ | Engine | **kernel** | `.meta/scripts/wiki_plugin_kernel.py` | validate / inject / registry / deploy / install mechanics |
34
+ | Plugin tier | **core** | `.meta/plugins/core/` | the 21 framework plugins |
35
+ | Extension | **package** | `.meta/plugins/domains/<pkg>/` | domain families (cuhksz, lark, email, bili, project…) |
36
+ | Unit | **instance** | the user's directory | a deployed workspace |
37
+
38
+ The call chain is the reason the names must stay distinct:
39
+
40
+ ```
41
+ npx owfa init
42
+ └─ bin/owfa.js CLI: fetch payload, copy trees, write AGENTS.md, call the engine
43
+ └─ kernel validate → inject → registry → deploy
44
+ └─ core plugins the structural contracts projected into AGENTS.md
45
+ ```
46
+
47
+ Two rules fall out:
48
+
49
+ - **CLI ≠ kernel.** The CLI is replaceable delivery (npm today, pipx or curl tomorrow); the kernel is deterministic mechanics with a fixed contract. Renaming the kernel to "OWFA CLI" would collapse the two and make the npm channel appear to own semantics it does not own.
50
+ - **`core` is the plugin tier.** If the framework is publicly called *OWFA Core*, do **not** also name the repository `core`: one word, two referents. The repo is `owfadev/owfa` for now; if it ever splits, `owfadev/core` (framework body) and `owfadev/cli` (installer) can take the word, and only then does `core` mean the repo.
51
+
52
+ `vault-wiki` is retired from the public surface: public copy says OWFA (or OWFA Core), the repo target is `owfadev/owfa`. The old string survives in history, old links and technical identifiers; there is no big-bang rename of the kernel, plugin directories or package IDs.
53
+
54
+ ## Two names, two jobs
55
+
56
+ | Name | Job | Where it appears |
57
+ |---|---|---|
58
+ | `vault-wiki` | historical / technical alias — what the code was called | old links, commit history, registry rows until the move |
59
+ | OWFA / OWFA Core | public name — what the project is | README first line, npm page, docs |
60
+ | `owfadev` | namespace — where the name resolves | GitHub org, npm fallback package |
61
+
62
+ A name that exists only in slides is a slogan; a name that resolves in a package manager is an address. The address layer is the one that has to be settled mechanically, not rhetorically.
63
+
64
+ ## Namespaces — the actual collision
65
+
66
+ - **GitHub `owfa` is taken** by an unrelated, dormant organization ("One Web For All", 0 public repos). We do not claim it, link it, or wait for it.
67
+ - **GitHub `owfadev` is available** (checked 2026-10-25). It is the project's org target. The repository target is `owfadev/owfa`; the current `AIE3905-Wuwa/vault-wiki` stays in place until the org exists and the team agrees to the move. A move is a migration either way: transfer the repo into a new org, or rename the current org (`AIE3905-Wuwa` is project-only — 9 repos, 3 members — so renaming is viable if the course no longer depends on the name). Both paths need the same URL/registry sweep; renaming releases the old org name and 404s the old org profile/API, while transferring leaves the course org intact. **Update 2026-10-26: the team agreed — direct org rename (plan B) to `owfadev` with the repository renamed to `owfa`; execution follows `migration.md`.**
68
+ - **npm `owfa` is frozen.** `npm view owfa` returns 404, but 404 means "no published package", **not** "publishable": npm holds the name back under its similarity policy (too close to `ow` / `ora`; reported by the maintainer when publishing). The only path is an application to npm support.
69
+ - **The fallback is `owfadev`** — it returns 404 on npm (no published package, no freeze reported; unlike `owfa`, confirm at the first publish), matching the GitHub org. The package can expose both bins (`owfa` and `owfadev`), so `npx owfadev init` works today and `owfa init` works after a global install. If the application is granted, `owfa` becomes the primary package; `owfadev` stays as an alias or is deprecated, never deleted.
70
+
71
+ A 404 is not a claim. A frozen name is claimed by an application **plus** a working fallback, not by announcing the command early.
72
+
73
+ ## Sequence — why GitHub first
74
+
75
+ 1. **Create `owfadev` and move the repo** (`owfadev/owfa`), update metadata and links. This is the public home a reviewer can inspect.
76
+ 2. **Apply to npm** with the org, the repo, the docs and the fallback as evidence that this is a project, not a typo-squat.
77
+ 3. **Publish the fallback first if the application is slow**; switch the primary package to `owfa` if and when it is granted. The brand never blocks on the registry string.
78
+
79
+ The order is not bureaucratic: npm support evaluates a project by its public home, and a repo that is about to move is weak evidence. Settle the home, then ask for the address.
80
+
81
+ ## What OWFA is not
82
+
83
+ - Not a SaaS or hosted product; every workspace is local and the framework has no telemetry.
84
+ - Not "for all people" and not a claim of access to all data; the scope is *your* workspace and *your* agents.
85
+ - Not the GitHub org named `owfa`, and not affiliated with "One Web For All".
86
+ - Not a replacement for the kernel, the CLI, or the `core` plugin tier as separate concepts.
87
+
88
+ ## Objections, answered
89
+
90
+ 1. **"It overclaims — it sounds like a universal product."**
91
+ The scope is bounded twice: *your* workspace, *your* agents. The docs never say all data or all people. A slogan fails when it cannot be falsified; this one has a mechanical test — install it and see whether a fresh agent re-enters without being re-introduced.
92
+
93
+ 2. **"'Workspace' is vague; the thing is a wiki."**
94
+ The wiki is the medium; the workspace is the owned unit of re-entry. The product's value is that a new session knows where to look, not that files end in `.md`.
95
+
96
+ 3. **"The GitHub org is taken and npm froze the name, so the name is not ours."**
97
+ The brand and the address are separate. The org target `owfadev` is ours; the npm fallback `owfadev` is publishable; `owfa` is an application, not a dependency. If the string is denied, the project still ships, and the README says which command works.
98
+
99
+ 4. **"Then rename the repo and all packages."**
100
+ No. The repo target is `owfadev/owfa`; package IDs, plugin directories and the kernel stay as they are. `core` stays the plugin tier. This is the `ripgrep`/`rg` pattern at the namespace level.
101
+
102
+ 5. **"It is still just a slogan."**
103
+ It is a CLI with a working fallback channel; the command runs under `owfadev` even before `owfa` is granted. That is the difference between a position paper and a channel.
104
+
105
+ ## Where the name is enforced
106
+
107
+ - `package.json` — `"name": "owfa"` (target) with `"bin": { "owfa": "bin/owfa.js" }`; the fallback is the same file with `"name": "owfadev"` and bins `owfa` + `owfadev`
108
+ - `README.md` — first line, the *Name* section, and the install note (never announce a command the registry does not serve)
109
+ - `templates/AGENTS.template.md` — the identity paragraph a new instance starts from
110
+ - `.meta/docs/distribution.md` — the channel's version invariant, fallback and release runbook
111
+ - `scripts/verify-release.js` — the release gate (name/bin agreement, version rides `.meta/VERSION`, tag matches)
112
+
113
+ Update 2026-10-26: the repository itself is renamed to `owfa` (`owfadev/owfa`), and the public copy uses OWFA / OWFA Core; `vault-wiki` survives only in history and old links. Nothing in the kernel, plugin IDs, or registry depends on the brand.
@@ -0,0 +1,130 @@
1
+ # Packages
2
+
3
+ > Design record of the split-improvement phase (2026-10-12 → 10-13: binding round issue #20, discovery/download/update, teardown). Mechanism and — more importantly — the reasons behind each decision. Authoritative mechanics live in the kernel (`wiki_plugin_kernel.py`) and in the `PKG.yaml` declarations; this page explains why they are shaped this way.
4
+
5
+ ## Layout: directory == package
6
+
7
+ `.meta/plugins/` is two-level:
8
+
9
+ ```
10
+ .meta/plugins/
11
+ ├── core/ # 20 framework plugins (the two roots + cross-cutting pieces)
12
+ │ ├── wiki/ …
13
+ └── domains/ # one directory per package = the install unit
14
+ ├── cuhksz/ # PKG.yaml + 8 plugin masters
15
+ ├── lark/ # PKG.yaml + 4 plugin masters
16
+ ├── email/ bili/ project/
17
+ ```
18
+
19
+ The **directory boundary == tier boundary == package boundary** — the same structure fact expressed once. Projections stay id-keyed and flat (`.meta/command/`, `.agents/skills/`, registry, the AGENTS injection region): packages regroup masters, not projections, so deploy/inject/registry needed no redesign.
20
+
21
+ | Unit | Members | Connectors | Depends |
22
+ |---|---|---|---|
23
+ | framework (core) | 20, incl. the explicit vault/mapping/structure exception — the default domain is constitutional infrastructure, the mapping proxy layer belongs to the wiki body | — | — |
24
+ | cuhksz | cuhksz · bb · bb-map · bb-track · bb-teach · bb-quiz · sis · registry | bb-cli, sis-cli | framework |
25
+ | lark | lark · lark-docs · lark-im · lark-calendar | lark-cli (external) | framework |
26
+ | email | email | mail-cli | framework |
27
+ | bili | bili | bili-cli | framework |
28
+ | project | project | — | framework |
29
+
30
+ Why the vault-exception matters: a naive "all domains are packages" split would ship the default domain out of the framework — but every instance boots on vault/mapping/structure before any package exists. Exceptions are declared, not discovered.
31
+
32
+ ## PKG.yaml
33
+
34
+ ```yaml
35
+ schema_version: 1
36
+ id: cuhksz
37
+ version: 0.1 # release ordinal, rides the git tag — NOT tied to member versions
38
+ compat: ">= 0.2" # framework version floor, checked against .meta/VERSION
39
+ members: [cuhksz, bb, bb-map, bb-quiz, bb-teach, bb-track, sis, registry]
40
+ connectors: # tri-state:
41
+ - name: bb-cli # in-repo: path (code ships with the package)
42
+ path: connectors/bb-cli
43
+ - name: lark-cli # external: maintained outside (declaration only)
44
+ external: true
45
+ - name: gh # system: a preinstalled binary (capability + version expectation, no code)
46
+ system: true
47
+ expect: ">= 2.0"
48
+ depends: [framework] # v1 flat graph — no package-to-package edges
49
+ uninstall: # declaration, never executable hooks
50
+ retains: [wiki/cuhksz/, cuhksz/] # data zones never touched by the kernel
51
+ credentials: [~/.bb-cli/, ~/.sis-cli/] # prompted, never auto-deleted
52
+ bridges: [profile#domain-cognition] # semantic registration points to check
53
+ processes: [] # long-running executors to stop
54
+ ```
55
+
56
+ ## Invariants
57
+
58
+ **Authoring side (D1): `members` == the maximal family closure.** The kernel computes the closure (depends chains reaching the package root) and diffs it against the declaration both ways — drift is a validate error.
59
+
60
+ *Why declare at all, when the closure is computable?* Because **the depends graph is live and a package is a versioned anchor**. A closure-derived package would silently change contents as the graph evolves — the same tag would ship different things at different times. The declared roster pins contents to the version; reconciliation turns structural drift into a commit-time error instead of an install-time surprise. Redundant, but self-verifying — the third application of the owner×commands dual-declaration pattern.
61
+
62
+ **Site side (D5): v1 requires full presence** — every member on disk. The subset grammar is fixed now so it never breaks the validator later: `installed ⊆ members`, non-empty, dependency-closed, root mandatory. Prunability classes:
63
+
64
+ | Class | Example | Rule |
65
+ |---|---|---|
66
+ | leaf consumers | bb-teach, bb-quiz | freely prunable — nothing depends on them |
67
+ | structural members | bb, bb-map, bb-track | prunable only together with their dependents (the closure rule enforces it) |
68
+ | family root | cuhksz | never prunable — owns territory, identity page, roster line |
69
+ | connectors | bb-cli | prunable when no installed member consumes it |
70
+
71
+ `--without` is a reserved parameter (v1 reports not-yet-open). Its promise is semantic — zero injection, zero skill surface, zero credentials — not physical: a cached clone of reviewed code is not an exposure surface, so sparse download stays an optimization outside the contract. Family-root roster lines are capability catalogs; **skill presence is the call-time truth** (tolerant degradation, no dynamic reassembly of inject text).
72
+
73
+ ## Versions (D2)
74
+
75
+ `.meta/VERSION` anchors the framework (`0.2`, git tag `v0.2`); the kernel contract changes (manifest fields, projection rules) are what bump it. Package versions are release ordinals riding their own tags; **member plugins keep their own changelog versions and the two levels never lockstep** — a package is a distribution unit, not a semantic one.
76
+
77
+ ## Kernel surface
78
+
79
+ | Command | What it does |
80
+ |---|---|
81
+ | `validate` | full graph + package reconciliation (closure diff, presence, flat graph, compat vs VERSION) |
82
+ | `validate --scope <pkg>` | single-package tolerant mode (D3): deps absent outside the package degrade to warnings — the CI shape for package repos post-split, run with a framework checkout alongside |
83
+ | `pkg` | package inventory: members, connectors, implicit core remainder |
84
+ | `residual <pkg>` | D6 residual scan: greps handwritten AGENTS region + profile/language/calendar/todo/cron anchors for member references (the kernel-managed injection region is skipped — it is cleaned mechanically) |
85
+ | `install <pkg>[@tag]` | resolve the [registry](https://github.com/owfadev/registry) index (members reconciled against PKG.yaml) → trust gate → clone → copy masters/connectors/commands → converge. `install <owner/repo> --yes` installs an unindexed repository (trust: unknown); `--path <dir>` installs a local one (channel C) |
86
+ | `uninstall <pkg> --yes` | D6 four-clear (masters/commands/connectors/skills) + convergence + residual scan + retains/credentials reminders — data never touched |
87
+ | `list-remote` | index table with installed marks |
88
+ | `plan <pkg>` | dependency disclosure before a package lands |
89
+ | `migrate [<pkg>] [--clear] [--force]` | pending semantic migrations: status / clear (author verify + teardown residual gate; use-and-delete) — see [Migrations](#migrations-the-algebra-0--x--y--0) below |
90
+ | `upgrade` | reconciliation report (local vs index); applying runs a **silent reinstall** per package (never cascaded) — member deltas, changelog excerpts, chained migration staging |
91
+
92
+ *Why scope mode exists before the split:* after the split the framework repo and each package repo no longer contain the full graph — validate would be blind exactly where it matters most. Absence-tolerance turns "plugin missing" from an error into a listed warning, keeping every repo self-checkable.
93
+
94
+ ## Uninstall contract (D6)
95
+
96
+ No executable uninstall hooks — that would be a **third execution surface** (after inject text and connectors), running at a privileged moment; the security model declines. Instead the package *declares* its deletion semantics (`uninstall:` above) and the flow is: kernel mechanical four-clear (directory / injection / registry / projections) → residual scan output → agent semantic finish per the declaration (credential reminders, process stops, bridge registration lines) behind a confirmation gate. **Data and credentials are never auto-deleted** — the freedom to delete belongs to the human; retained data zones lapse into the deprecated posture.
97
+
98
+ ## Migrations: the algebra 0 → x → y → 0
99
+
100
+ Package state changes are **semantic migrations carried by declarations, not hooks**. Three kinds close the algebra:
101
+
102
+ | Kind | Files | Staged when | Lives until |
103
+ |---|---|---|---|
104
+ | init (0→x) | `migrations/init.md` (+ optional `init.py`) | fresh install | verify-clean `--clear` |
105
+ | migrate (x→y) | `migrations/x-to-y.md`, frozen at release | an upgrade landing that version | verify-clean `--clear` |
106
+ | teardown (x→0) | `migrations/teardown.md` | **every install, dormant**; consumed at uninstall | residual-clean `--clear` |
107
+
108
+ Mechanics: the kernel stages declarations into `.meta/migrations/<pkg>/` (kernel zone — never inside the package dir), keeps a ledger (`pending.json`), and raises the **tri-face warning**: a banner on every kernel invocation · `validate` stays red — mechanical blessing is withheld until the semantic step is done · a kernel-managed block lands in the AGENTS injection region so every session sees it. Clearing runs the author's `verify(ctx)` — AST-gated (read-only, stdlib-only) — then deletes the staged files (**use-and-delete**: declarations are useful precisely once; assertions that hold forever belong in the package's `scripts/check.py` — the judgment split rule).
109
+
110
+ **Sweep symmetry** keeps the ledger honest without a cron: migrate-kind entries die with the package (uninstall sweeps them), teardown-kind entries die with reinstall (install sweeps them). The dormant `PKG.yaml` copy in the staging directory doubles as a **presence marker**: after a manual `rm -rf` of a package directory, the marker lets the kernel sweep the full mechanical residue — commands, connectors, skills, ledger, banner. Self-healing with no hooks.
111
+
112
+ **Teardown gate**: teardown declares semantic deletions; with no author script the kernel scans the anchor surfaces (the AGENTS handwritten region, profile / language / calendar / todo / cron pages — the kernel-managed injection region is skipped) for member references — word-boundary, deliberately broad: a layout line naming the territory, a cognition registration line, a calendar source key are all references the human side must finish deleting. Clean anchors clear; hits block `--clear` (override `--force`, on your own judgment). The kernel journal (`.meta/kernel-journal.log`, rolling cap of 500 lines, git-tracked) records the mechanical chain — install / warn+ / clear / uninstall / sweep; mechanical facts only, semantic narrative stays in the instance wiki's log.
113
+
114
+ ## Manifest schema
115
+
116
+ `schema_version: 1` on PLUGIN.yaml and PKG.yaml. One format migration shared with the upcoming behavior contracts (#34: owns/trigger/emits/never) — versioning the schema once avoids a second format churn when #34 lands.
117
+
118
+ ## Decision ledger
119
+
120
+ | # | Decision | One-line reason |
121
+ |---|---|---|
122
+ | D1 | declared roster + closure reconciliation | live graph vs versioned anchor; drift → commit-time error |
123
+ | D2 | package version ≠ member versions | distribution unit ≠ semantic unit; lockstep is a trap |
124
+ | D3 | scope/tolerant validate in the binding round | the split is only safe if repos can self-check without the full graph |
125
+ | D4 | instance-local packages live in `domains/` too | one semantic: package directory == install unit; zero-index private packages |
126
+ | D5 | subset grammar fixed now, `--without` opens on demand | validator format never breaks; first real subset user triggers it |
127
+ | D6 | declarative uninstall, no hooks | third execution surface declined; deletion knowledge becomes reviewable data |
128
+ | D7 | migrations are declarations closing 0→x→y→0; teardown ships dormant with every install | semantic change rides reviewable files; the x→0 case must be declared *before* the package is gone |
129
+ | D8 | sweep symmetry + dormant PKG.yaml presence marker | ledger truth without a cron; manual `rm -rf` still self-heals (no hooks anywhere) |
130
+ | D9 | teardown gate = residual scan by default, author scripts optional | D6's no-hooks principle extended to deletion *verification* — zero-script packages still get a semantic gate |
@@ -0,0 +1,79 @@
1
+ # Quickstart
2
+
3
+ > The five-minute path. Full guide — components, channels, packages, upgrades, troubleshooting: [deployment.md](deployment.md). The channel's design and release record: [distribution.md](distribution.md).
4
+ > Status: npm `owfa` is under application (frozen on similarity grounds); until the registry serves it, the git channel works today. The fallback package `owfadev` carries the same CLI once published.
5
+
6
+ ## 1. Prerequisites
7
+
8
+ - **Python 3.9+** — the framework and kernel are pure stdlib; no pip, no venv.
9
+ - **Node 16.7+** — only for the npm channel (the CLI is Node).
10
+ - **An agent** that reads `AGENTS.md` and `.agents/skills/` (ZCode, Claude Code, Cursor, dsh…).
11
+ - **git** recommended — instance snapshots and the upgrade rollback path.
12
+
13
+ ## 2. One command (npm channel)
14
+
15
+ | Item | Requirement |
16
+ |---|---|
17
+ | Python | 3.9+, pure standard library, zero dependencies |
18
+ | agent | A coding assistant that can read AGENTS.md and `.agents/skills/`, e.g. ZCode |
19
+ | Obsidian | Optional, viewer only |
20
+
21
+ ## Three postures
22
+
23
+ **0. One command (npm channel).** `npx owfa init <your-vault>` — fetches the framework, creates the directories, writes the AGENTS shell (or appends only the injection region to an existing one), and converges the projections. Then `cd <your-vault> && npx owfa doctor`. This is the same deployment as ①–⑤ below, mechanized; the manual steps remain the reference, the offline path and the developer path. Optional packages: `npx owfa init <dir> --packages cuhksz,lark`; later `npx owfa upgrade` replaces the framework trees and preserves the kernel's migration state. Details: [distribution.md](distribution.md).
24
+
25
+ The manual steps below serve A and B; posture 0 skips them.
26
+
27
+ **A. Just using it (clone-as-instance).** A clone of this repository *is* your instance: `git clone https://github.com/owfadev/owfa.git <your-vault>`, optionally `rm -rf <your-vault>/.git && git init` to own the history, then do steps ③–⑤ below (AGENTS.md shell, four directories, converge). Packages install on demand from the registry — `kernel install <pkg> --yes`. No development intent needed; you never touch the framework internals.
28
+
29
+ **B. Developing (template + instance).** Keep a clone of this repository as the *template* — development, experiments and upstream updates happen there, following [CONTRIBUTING.md](../../CONTRIBUTING.md). Separately deploy a real *instance* (your actual vault — posture A's steps, or the embedding steps below); when the template gains updates, review the diff and sync selectively into the instance, then converge — see the "Template + instance workflow" section of CONTRIBUTING.md. To develop is to run a real instance: the framework is validated in actual use, not in the abstract.
30
+
31
+ ## Five deployment steps
32
+
33
+ **① Get the framework**: `git clone https://github.com/owfadev/owfa.git`, or download the ZIP and unzip it (the old personal-repo address redirects).
34
+
35
+ **② Copy two trees** to the target vault root: `.meta/` and `.agents/skills/`. Plugin masters, command masters and copies, protocol artifacts, and mechanical scripts all live there. The clone ships **core 20 only** — no domain packages. Packages are added per need from the registry: `python3 .meta/scripts/wiki_plugin_kernel.py install <pkg> --yes` (see [packages.md](packages.md)); offline alternative — copy a package's `domains/<pkg>/` directory in and rerun `all`.
36
+
37
+ **③ Write the target vault's AGENTS.md**: draft the shell yourself—one identity paragraph plus a layout description; copy the injection region marker block verbatim from [agents-example.md](agents-example.md), not a single character changed—from `<!-- wiki-inject:start -->` to `<!-- wiki-inject:end -->`—it is the sole source of the structural contract. If the target vault already has an AGENTS.md, paste in only the injection region block.
38
+
39
+ **④ Create four empty directories**: `vault/`, `wiki/notes/`, `wiki/sessions/`, `wiki/vault/`. Derived pages need no hand-creation—index, tags, hot, and log are built by the pipeline on first run; the root index's `format_version` is also rendered by the pipeline.
40
+
41
+ **⑤ Converge the projections**, run at the target vault root:
42
+
43
+ ```
44
+ python .meta/scripts/wiki_plugin_kernel.py all
45
+
46
+ The npm name `owfa` is under application (similarity freeze); until it is granted the fallback package serves the same CLI: `npx owfadev init my-workspace`, `npx owfadev doctor`, etc. — substitute `owfadev` for `owfa` in every command above.
47
+ ```
48
+
49
+ `init` copies `.meta/` + `.agents/skills/`, creates `vault/` and the three wiki directories, writes or appends `AGENTS.md`, and runs the kernel. Existing content is untouched. Optional packages: `npx owfa init my-workspace --packages cuhksz,lark`.
50
+
51
+ Already have a workspace? `init` refuses if `.meta/` exists; use `npx owfa upgrade` (or `--force` to re-copy the framework trees).
52
+
53
+ ## 3. Manual five steps (git or offline)
54
+
55
+ 1. **Get the framework**: `git clone https://github.com/owfadev/owfa.git my-workspace` — a clone is a valid instance (the pre-rename `AIE3905-Wuwa/vault-wiki` URL redirects). To embed into an existing vault, clone the template elsewhere and copy `.meta/` + `.agents/skills/` into the target root.
56
+ 2. **Write `AGENTS.md`**: one identity paragraph, one layout paragraph, and the injection markers verbatim from [agents-example.md](agents-example.md). Existing `AGENTS.md`? Paste in only the marker block.
57
+ 3. **Create four directories**: `vault/`, `wiki/notes/`, `wiki/sessions/`, `wiki/vault/`.
58
+ 4. **Converge**:
59
+ ```bash
60
+ python .meta/scripts/wiki_plugin_kernel.py all
61
+ ```
62
+ 5. **Verify**: drop a file into `vault/`, open an agent at the root, say "map", then "check".
63
+
64
+ There is no separate kernel install: the kernel is `.meta/scripts/wiki_plugin_kernel.py` inside the tree; Python 3.9+ runs it. On Windows use `py -3` or set `OWFA_PYTHON`.
65
+
66
+ ## 4. Next
67
+
68
+ ```bash
69
+ owfa list # registry catalog: packages, versions, installed marks
70
+ owfa add cuhksz # install a domain package (stops at a semantic migration if one is staged)
71
+ owfa pkg # what is installed here
72
+ owfa upgrade # later: replace the framework trees, preserve instance state
73
+ ```
74
+
75
+ These assume a global install (`npm i -g owfa` or `npm i -g owfadev`); without one, use `npx owfa …` / `npx owfadev …`.
76
+
77
+ - Package lifecycle, trust levels, offline installs, uninstall: [deployment.md](deployment.md#7-packages--finding-and-installing).
78
+ - Daily use: [usage.md](usage.md); mechanics: [mechanics.md](mechanics.md).
79
+ - Developing the framework itself: [CONTRIBUTING.md](../../CONTRIBUTING.md).