carry forward ADRs, Claude Code config, and changelog discipline
Ports the patterns that crystallized during the short-lived claudian plugin project (discarded in favour of this Flutter rebuild): - ADRs 0001-0004 capture decisions that survive the host change — CLI-first over MCP, Go for the sidecar, pql as a supporter tool that becomes a clide-managed subsystem when present, and the ignore-file strategy that wires all file-enumerating surfaces through one knob in .pql/config.yaml. - .claude/settings.json and the git-commit and skill-create skills come over with naming updated for clide. The git-commit skill's "no Conventional Commits" convention supersedes the Python-era clide style under legacy/; the Keep-a-Changelog discipline and the project.yaml-version-and-changelog-bumped-together rule apply going forward. - CHANGELOG.md starts fresh at the repo root to track the Flutter rebuild. The Python changelog is preserved under legacy/. .gitignore narrows from `.claude/` to just `.claude/settings.local.json` so project-level config and skills travel with the repo. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,34 @@
|
||||
# ADR 0001 — CLI-first, not MCP
|
||||
|
||||
**Status:** accepted
|
||||
**Date:** 2026-04-20 (ported from the claudian lineage)
|
||||
|
||||
## Context
|
||||
|
||||
Clide exposes capabilities to Claude Code (panes, terminals, git,
|
||||
pql queries, canvas, graph). The two mainstream options for that
|
||||
interface are:
|
||||
|
||||
1. A Model Context Protocol (MCP) server the agent connects to.
|
||||
2. A plain Bash CLI the agent calls from its shell, matching the
|
||||
contract `pql` already follows.
|
||||
|
||||
## Decision
|
||||
|
||||
Claude talks to Clide exclusively via Bash (`clide ...`). No MCP
|
||||
server. No protocol layer in Claude's face. The CLI uses the same
|
||||
exit-code + stderr-JSON contract as pql.
|
||||
|
||||
## Consequences
|
||||
|
||||
- Same mental model as pql for the agent — one tool-use pattern
|
||||
covers both.
|
||||
- No MCP runtime to host, authenticate, or keep in sync with client
|
||||
versions.
|
||||
- User/Claude parity is easier to enforce: every CLI subcommand must
|
||||
have a UI affordance in the Flutter app and vice versa.
|
||||
- Claude Code's `Bash(clide *)` allow rule is the only configuration
|
||||
Clide needs on the agent side.
|
||||
- If an MCP-only integration becomes compelling later (e.g. a
|
||||
multi-agent scenario), nothing here precludes adding one that
|
||||
shells out to the same CLI.
|
||||
@@ -0,0 +1,44 @@
|
||||
# ADR 0002 — Sidecar language: Go
|
||||
|
||||
**Status:** accepted
|
||||
**Date:** 2026-04-20 (ported from the claudian lineage)
|
||||
|
||||
## Context
|
||||
|
||||
The Clide sidecar owns PTYs, subprocesses, file watchers, git
|
||||
shelling-out, and the IPC server. It ships as a single static binary
|
||||
that also serves as the `clide` CLI in one-shot mode. The Flutter
|
||||
desktop app talks to it over IPC; Claude talks to it via the CLI.
|
||||
Language candidates were Go and Rust.
|
||||
|
||||
Related hard constraint: **no heavy lifting in the UI layer.** The
|
||||
Flutter app stays focused on rendering and interaction. Everything
|
||||
heavy (PTYs, subprocesses, file watching, git, pql invocations)
|
||||
lives in the sidecar. Reason: keep the UI layer thin and the
|
||||
security-sensitive surface auditable in one language.
|
||||
|
||||
## Decision
|
||||
|
||||
The sidecar/CLI is written in Go.
|
||||
|
||||
Rationale:
|
||||
|
||||
- **Matches pql.** pql is Go; Clide wraps pql and reaches into its
|
||||
idioms constantly. Shared toolchain and shared patterns cut
|
||||
cognitive overhead.
|
||||
- **Static binary.** Single artifact, trivial cross-compile, no
|
||||
runtime dependencies on the user's machine.
|
||||
- **PTY story is fine.** `creack/pty` covers what we need; Rust's
|
||||
crates are marginally nicer but not decisive.
|
||||
- **Muscle memory.** Build pipeline, `project.yaml` conventions,
|
||||
goreleaser setup, exit-code contract, diagnostic format — all
|
||||
already established in pql and portable one-to-one.
|
||||
|
||||
## Consequences
|
||||
|
||||
- Module path: `git.schweitz.net/jpmschweitzer/clide/sidecar`.
|
||||
- Layout mirrors pql: `cmd/clide/main.go`, `internal/cli`,
|
||||
`internal/version` (ldflag-stamped `Version`, `Commit`, `Date`),
|
||||
`internal/diag` (exit codes + stderr-JSON diagnostics).
|
||||
- Same Makefile shape: version read from `project.yaml` via awk,
|
||||
stamped via `-ldflags -X`.
|
||||
@@ -0,0 +1,61 @@
|
||||
# ADR 0003 — pql as supporter tool; Clide wraps, never duplicates
|
||||
|
||||
**Status:** accepted
|
||||
**Date:** 2026-04-20 (ported from the claudian lineage)
|
||||
|
||||
## Context
|
||||
|
||||
[`pql`](https://github.com/postmeridiem/pql) is a pre-existing Go
|
||||
CLI that indexes a markdown-bearing directory tree into SQLite and
|
||||
exposes its semantics (frontmatter, wikilinks, tags, headings,
|
||||
bases) through a query surface. Clide needs those capabilities for
|
||||
its Query panel, canvas drivers, graph view, and any feature that
|
||||
needs to know structure.
|
||||
|
||||
## Decision
|
||||
|
||||
Two complementary rules.
|
||||
|
||||
### 1. Wrap, don't duplicate.
|
||||
|
||||
Clide never re-implements backlinks, ranking, frontmatter parsing,
|
||||
or wikilink resolution for query purposes. If a capability is
|
||||
missing in pql, it is added upstream in pql's repo and Clide bumps
|
||||
the dependency.
|
||||
|
||||
The only place Clide contains pql logic is
|
||||
`sidecar/internal/pql/` — pure shell-outs to the `pql` binary, no
|
||||
logic beyond invocation and result rendering.
|
||||
|
||||
### 2. pql is a Clide subsystem when Clide is present in the repo.
|
||||
|
||||
Broader than "wrap, don't duplicate." When Clide is loaded in a
|
||||
repo, it owns pql's lifecycle and the config keys it cares about.
|
||||
On load, Clide writes its current state into `.pql/config.yaml` —
|
||||
no conditional sync, no "did anything change" logic.
|
||||
|
||||
Clide only stomps the keys it manages (starting with `ignore_files:`
|
||||
— see ADR 0004). Other pql config keys are left alone so pql's
|
||||
config surface can grow independently.
|
||||
|
||||
Clide does **not** touch pql's index/cache data under `<repo>/.pql/`
|
||||
— that stays pql's private store. Only the config file is Clide's
|
||||
to edit.
|
||||
|
||||
In repos without Clide, pql works standalone, unaffected. The rule:
|
||||
direct-pql users get vanilla pql; Clide users get pql managed by
|
||||
Clide.
|
||||
|
||||
## Consequences
|
||||
|
||||
- One source of truth for markdown semantics (pql).
|
||||
- Clide's `sidecar/internal/pql/` package is deliberately thin.
|
||||
- Any new query capability the UI wants goes through a pql upstream
|
||||
PR, not a local workaround.
|
||||
- User never has to learn pql's config file to get consistent
|
||||
behavior — Clide manages it.
|
||||
- The arrow Clide → pql is never inverted: pql stays ignorant of
|
||||
its wrapper, never hardcodes Clide filenames.
|
||||
- pql is also the **only** query engine. Obsidian-style inline
|
||||
"bases" (YAML query tables embedded in markdown) are explicitly
|
||||
not supported; queries live at the repo level where they belong.
|
||||
@@ -0,0 +1,73 @@
|
||||
# ADR 0004 — Ignore file strategy
|
||||
|
||||
**Status:** accepted
|
||||
**Date:** 2026-04-20 (ported from the claudian lineage)
|
||||
|
||||
## Context
|
||||
|
||||
Clide's working assumption is that the git repo *is* the workspace
|
||||
— no separate "vault" concept layered on top. Every file-enumerating
|
||||
surface in Clide (pql query panels, canvas drivers, graph view,
|
||||
sidecar file watchers, pane lists, file tree) needs to skip the
|
||||
obvious junk — `vendor/`, `node_modules/`, `dist/`, build artifacts
|
||||
— or results drown in noise.
|
||||
|
||||
## Decision
|
||||
|
||||
One mechanism everywhere: the `ignore_files:` list in
|
||||
`.pql/config.yaml`. An ordered list of gitignore-shaped files, later
|
||||
entries win on per-pattern conflicts.
|
||||
|
||||
### Default
|
||||
|
||||
pql defaults to `ignore_files: [.gitignore]`. Most repos already
|
||||
keep exclusions there, so zero config in a code repo; in a
|
||||
notes-only directory `.gitignore` doesn't exist and the default is
|
||||
a safe no-op.
|
||||
|
||||
### Clide sync
|
||||
|
||||
Per ADR 0003's "pql is a Clide subsystem when present" rule, Clide
|
||||
writes the list on load:
|
||||
|
||||
- If `.clideignore` exists in the repo:
|
||||
`ignore_files: [.gitignore, .clideignore]`. Clide-specific deltas
|
||||
(including `!pattern` negations) layer on top of gitignore.
|
||||
- Otherwise: `ignore_files: [.gitignore]` (matches the pql default).
|
||||
|
||||
No conditional sync. Clide only stomps `ignore_files:`; other pql
|
||||
config keys are left alone.
|
||||
|
||||
### `.clideignore` semantics
|
||||
|
||||
- Carries **only** the Clide-specific deviations from `.gitignore`.
|
||||
Never duplicate gitignore's contents.
|
||||
- Supports `!pattern` negations to un-ignore specific entries (e.g.
|
||||
`!.github/` to expose workflow docs in query results).
|
||||
|
||||
### Walker magic: none except `.git/`
|
||||
|
||||
Git self-hides `.git/` — that's the only invisible exclusion in the
|
||||
stack. Every other tool is explicit: pql adds `.pql/` to
|
||||
`.gitignore` at install time, and Clide adds any private dirs it
|
||||
introduces (e.g. `.clide/`) to `.gitignore` on install. Exclusion
|
||||
flows through the normal `ignore_files:` chain; no hardcoded walker
|
||||
exceptions for tool-owned dirs.
|
||||
|
||||
### Same list, same rules, everywhere
|
||||
|
||||
Sidecar consumers (watchers, canvas, pane list, file tree, graph
|
||||
view) read the same key from `.pql/config.yaml` and apply identical
|
||||
precedence, so Claude and the user always see the same filtered
|
||||
surface.
|
||||
|
||||
## Consequences
|
||||
|
||||
- Users get one config knob, in a file they might already know (pql
|
||||
users) or never need to touch (Clide-only users).
|
||||
- `.clideignore` is short by design — it's deltas, not a full list.
|
||||
- Removing Clide from a repo leaves pql working with vanilla
|
||||
defaults (Clide's last-written `ignore_files:` stays until pql or
|
||||
the user rewrites it; worth reconsidering during uninstall design).
|
||||
- Upstream pql work: the `ignore_files:` list is already the shape
|
||||
pql has landed on (plural, ordered, defaults to `[.gitignore]`).
|
||||
Reference in New Issue
Block a user