Update VISION to the 9P architecture and editing model

The vision predated the 9P pivot and the GUI direction. Correct it:

- Architecture: clients (GUI, CLI, Emacs/vim, agents) speak 9P to
  ork-server; drop the C FFI layer entirely.
- Replace "keyboard-first, mouse optional" with "the document is the
  control surface": actions live on objects, mouse and keyboard equal,
  no menu trees or button walls.
- Add an explicit Editing Model: structured render, per-section
  raw-text editing with reparse-on-commit, and direct-manipulation
  structural edits that each map to one 9P operation.
- Refresh milestones (v0.1 parser/CLI and v0.2 9P server/client done;
  GUI is next) and the rationale (add the "Why 9P" section).
This commit is contained in:
Levi Neely 2026-09-30 22:21:10 +02:00
parent 943c05b61c
commit 7ee65a4a2d
1 changed files with 76 additions and 32 deletions

108
VISION.md
View File

@ -8,7 +8,7 @@ Existing alternatives fall short:
- **Organice** (web): Clunky, slow, limited offline
- **Orgzly** (Android): Mobile-only, sync issues
- **VS Code extensions**: No proper AST, just syntax highlighting
- **Logseq/Obsidian**: Different formats, not org-mode
- **Logseq/Obsidian**: Nice editing UX, but their own formats — not org-mode
None of these integrate with the Linux desktop. None feel native.
@ -36,14 +36,38 @@ Org files on disk are the source of truth. No database. No proprietary format. E
**2. Parse properly**
Use tree-sitter for a real AST. No regex hacks. Handle malformed files gracefully with error recovery.
**3. Keyboard-first**
Every action reachable by keyboard. Mouse optional. Emacs-inspired bindings where sensible.
**3. The document is the control surface**
Actions live on the objects, not in menus. A TODO keyword, a priority cookie, a tag, a timestamp, a headline — each is manipulable in place. Cycle a keyword by clicking it or by pressing a key on it; refile a subtree by dragging it or by a command. Mouse and keyboard are equal citizens; neither is primary. No nested menu trees, no walls of buttons — the affordances are in the rendered document itself.
**4. Desktop-native**
**4. Structure and text, one view**
The document renders as structure but is never a read-only render. Content is edited as raw org text in place (see the editing model below); structure is edited by direct manipulation of the rendered objects. Both paths issue the same operations against the same files.
**5. Desktop-native**
Use Qt/QML. Respect system themes. Integrate with KDE services (KRunner, Akonadi calendar, notifications).
**5. CLI for automation**
The `ork` CLI enables scripting, agent integration, and headless workflows.
**6. One path to the data**
The GUI, the CLI, and any other client all reach org files through the same `ork-server` 9P interface. No client has a privileged path; a mouse gesture and a CLI command produce the identical write. This also makes the `ork` CLI a first-class tool for scripting, agent integration, and headless workflows.
## Editing Model
The document is rendered as styled structure (Logseq-like), not plain text and not a read-only view.
**Content editing.** Clicking into a section's headline or body turns *that region* into an editable raw-org-text buffer. Everything else stays rendered. On leaving the region (blur/commit), only that section is reparsed and re-rendered — parsing work is bounded to what you touched, and happens on commit, never per keystroke. A commit is one 9P write to that section's file (`headline`, `body`, ...).
**Structural editing.** Structure is manipulated directly on the rendered objects, without entering text-edit mode. Each gesture is exactly one 9P operation:
| Gesture | Operation |
|---|---|
| Drag headline up/down among siblings | `move up` / `move down` |
| Drag headline onto another | `refile --parent` |
| Drag to indent / outdent | `demote` / `promote` |
| Click a TODO keyword | `set keyword` (cycles via `/keywords`) |
| Click a priority cookie | `set priority` |
| Click a tag or the tag area | `tag` (add/remove) |
| Click a timestamp | `set scheduled` / `set deadline` |
| Toggle a `[ ]` checkbox | body edit |
The GUI holds no org logic of its own — it is a direct-manipulation and in-place-editing surface over the operations the server already exposes.
## Architecture
@ -51,9 +75,14 @@ The `ork` CLI enables scripting, agent integration, and headless workflows.
┌─────────────────────────────────────────────────┐
│ Qt/QML UI │
│ (document view, agenda, capture, search) │
├─────────────────────────────────────────────────┤
│ orkmode-core (Rust) │
│ (document ops, queries, mutations, sync) │
└─────────────────────────────────────────────────┘
│ ▲
│ 9P (unix socket) │ same protocol
▼ │
┌─────────────────────────────────────────────────┐
│ ork-server (Rust) │
│ 9P namespace: docs, sections, fields, agenda, │
│ query, ctl (rm/move/promote/demote/refile/...) │
├─────────────────────────────────────────────────┤
│ org-parser (Rust) │
│ (tree-sitter AST, incremental parsing) │
@ -61,58 +90,73 @@ The `ork` CLI enables scripting, agent integration, and headless workflows.
│ org-ast (Rust) │
│ (type definitions, spans, serialization) │
└─────────────────────────────────────────────────┘
↑ ↑
C FFI for Qt CLI (ork)
▲
│ 9P (unix socket / tcp)
│
ork CLI · Emacs/vim (edit files directly) · agents
```
Every client — GUI, CLI, automation — speaks 9P to `ork-server`. The server owns all org logic and reads/writes the real `.org` files, so external editors (Emacs, vim) stay interchangeable.
## Milestones
### v0.1 — Parser & CLI (current)
### v0.1 — Parser & CLI ✅
- [x] Tree-sitter parser integration
- [x] Core AST types
- [x] CLI for querying and basic mutations
- [x] JSON output for tooling
### v0.2 — Read-only UI
- [ ] Qt/QML document viewer
- [ ] Headline folding/cycling
- [ ] Syntax highlighting
- [ ] Basic navigation
### v0.2 — 9P server & client ✅
- [x] `ork-server`: org files exposed as a 9P namespace (docs, sections, fields)
- [x] Read/write section fields (keyword, priority, tags, planning, properties, body)
- [x] `ork` reworked as a pure 9P client
- [x] Structural ops via `ctl` (rm, move, promote, demote, refile, archive, lint)
- [x] `query` and agenda views (todos, today, week)
### v0.3 — Editing
- [ ] Inline text editing
- [ ] TODO state cycling
- [ ] Tag editing
- [ ] Property editing
### v0.3 — Read-only UI
- [ ] Qt/QML document view rendering the 9P namespace
- [ ] Headline folding/cycling
- [ ] Structural styling (keywords, priorities, tags, timestamps as distinct objects)
- [ ] Navigation
### v0.4 — Editing (the editing model)
- [ ] In-place raw-text editing per section, reparse-on-commit
- [ ] Direct manipulation: click keyword/priority/tag/timestamp → 9P op
- [ ] Drag to move / refile / promote / demote
- [ ] Checkbox toggling
- [ ] Undo/redo
### v0.4 — Agenda
- [ ] Agenda view (day/week)
- [ ] TODO list view
- [ ] Tag/property filtering
### v0.5 — Agenda & search UI
- [ ] Agenda view (day/week) over `/agenda`
- [ ] TODO list and `query`-backed filtering
- [ ] Scheduled/deadline display
### v0.5 — KDE Integration
### v0.6 — KDE Integration
- [ ] KRunner plugin (search headlines)
- [ ] System notifications for deadlines
- [ ] Akonadi calendar integration
- [ ] Global capture hotkey
### Future
- Clock/time tracking (`clock` ctl verbs + LOGBOOK)
- Code block execution
- Diagram rendering (mermaid, plantuml)
- Table formula evaluation
- Capture templates
- Clock/time tracking
- Mobile companion (Kirigami)
## Why Rust + Qt?
## Why Rust + Qt + 9P?
**Rust** for the parser/core:
**Rust** for the parser, AST, and server:
- Memory safety without GC
- Excellent tree-sitter bindings
- Easy C FFI for Qt integration
- Fast incremental parsing
- Fast parsing
**9P** as the interface between server and clients:
- Language-agnostic — the GUI need not be Rust
- Process isolation — a GUI crash never corrupts the core
- One uniform path for GUI, CLI, and agents
- Trivially inspectable and scriptable
**Qt/QML** for the UI:
- Native KDE integration