@rayul/kordis 0.13.1 → 0.14.1

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.
@@ -0,0 +1,484 @@
1
+ ---
2
+ name: memgineering-setup
3
+ description: Use when installing or configuring memgineering, when moving a brain between a machine and an account, when renaming or deleting a hosted brain, or whenever the user asks WHICH of their AI tools can see this memory. Triggers include "set up memgineering", "connect my notes", "rename my brain", "delete that brain", "does my other AI see this too", "which of my tools can read this", "will it work in the app on my phone", "no brain is linked".
4
+ type: skill
5
+ allowed-tools: Bash(memgineering:*)
6
+ ---
7
+
8
+ # Setting memgineering up
9
+
10
+ ## Which tools this actually reaches, today
11
+
12
+ Answer this from here, not from a guess. The line is capability, not brand, so
13
+ it does not move as products come and go:
14
+
15
+ | | |
16
+ | ----------------------------------------- | ------------------------------------------------------------------------------------------------------------- |
17
+ | **Any tool that can run a shell command** | Reads and writes the same brain. Nothing has to be built for a tool that does not exist yet. |
18
+ | **Any tool that cannot** | **Not yet.** There is no connector. A hosted brain is reachable in principle and is not wired up in practice. |
19
+
20
+ `memgineering setup` writes its guidance into the agent tools it finds on the
21
+ machine, and `setup --dry-run` names the ones it actually found rather than
22
+ guessing from a list.
23
+
24
+ So when someone names a tool and asks whether it remembers too, work it out from
25
+ that line and answer **not yet, and here is what does** — not a hedge, not a
26
+ promise. "You are signed in, so it works everywhere" is the specific wrong
27
+ answer: the account syncs the brain between machines, it does not add a surface
28
+ that can read it.
29
+
30
+ ## 1. Register with the agents
31
+
32
+ **Default: open the screen.** `memgineering setup --web` starts a setup session,
33
+ prints a short pairing code, opens memgineering.com/setup in their browser, and
34
+ RETURNS — in seconds, with the screen still up. It does not block until they
35
+ finish, so run it and keep going in the same turn.
36
+
37
+ ```
38
+ memgineering setup --web # the screen; the normal answer
39
+ memgineering setup --web --print-url # no browser here — hand over the link
40
+ ```
41
+
42
+ Three things to do after running it:
43
+
44
+ 1. Tell them, in their language, that their browser has a setup screen open.
45
+ 2. Show them the pairing code it printed. The screen's first question is
46
+ whether they started this, and it asks them to compare that code — the
47
+ defence against somebody being sent a setup link.
48
+ 3. Stop. Nothing installs until they finish on the screen, and this machine
49
+ picks it up on its own when they do. There is nothing to poll and nothing
50
+ to wait for.
51
+
52
+ The screen asks everything `--agent` takes from flags — sign in, where the
53
+ memory lives, which brain, which tools, auto-update, the session hook — with
54
+ the recommended answer pre-selected. A person who is already signed in to
55
+ memgineering.com does not sign in again: that session IS the identity, and one
56
+ sign-in covers both halves (below).
57
+
58
+ **Only when they ask you to decide for them**, answer from flags instead:
59
+
60
+ ```
61
+ memgineering setup --agent \
62
+ --tools claude,codex \ # default: everything detected
63
+ --auto-update on \ # default: on, and recommended
64
+ --hook on \ # session-start summary + rules before an edit
65
+ --error-telemetry on # anonymized crash reports; unset = undecided (off)
66
+ ```
67
+
68
+ `--dry-run` reports what would change without changing it. `--human` draws the
69
+ same questions as a checkbox list in your terminal, for a machine with no
70
+ browser and a person sitting at it.
71
+
72
+ **`--no-login` is how someone says "this machine only".** It is a flag on the
73
+ `--agent` path, not a step on the screen: a brain that lives in a folder here
74
+ cannot follow them to their phone or their next laptop, and that is discovered
75
+ weeks later, by which time the notes are in the wrong place. On the screen the
76
+ same choice is made in front of them, with the differences side by side.
77
+
78
+ **One sign-in covers both halves (0.17.0+).** Signing in also links the user's
79
+ registry account (same Google account, automatic), so the credentials hold a
80
+ registry session next to the brain token. `memgineering whoami` reports both —
81
+ the brain identity and a `registry:` line with the username. If the registry
82
+ line says "not linked", the link simply did not happen at sign-in time (older
83
+ server, registry briefly down); a fresh `logout` + `login` links it. Never
84
+ treat a missing registry line as a failed brain sign-in — the brain token
85
+ stands on its own. Consent is asked exactly once, when an account is first
86
+ created.
87
+
88
+ **When the setup finishes, say what is true and no more.** Commands work
89
+ immediately — `recall`, `remember`, the session hook. What waits is the
90
+ guidance files setup just wrote: an agent reads those at the start of a
91
+ conversation, so they arrive with the next one. Do not tell the user they must
92
+ restart. (Measured: a fresh agent relayed "restart required" as fact, the user
93
+ checked, and it was not one.)
94
+
95
+ **Ask before setting policy for them.** Auto-update means the tool updates
96
+ itself; `--hook on` means note summaries and their standing rules reach an agent
97
+ unasked. Recommend both, but they are theirs to decide.
98
+
99
+ **Error telemetry is theirs to decide too, and defaults to off.** With
100
+ `--error-telemetry on`, the CLI sends an anonymous report when it ITSELF
101
+ breaks: error kind, CLI/Node version, platform, and a sanitized message
102
+ excerpt — never note content, commands, or anything naming them, and the
103
+ server has no columns identity could land in. Unset leaves it `undecided`
104
+ (behaves as off) so a person can be asked later; a terminal `setup` asks
105
+ once; without a terminal it never prompts. Two off-switches at any time:
106
+ `memgineering setup --error-telemetry off`, or `MEMGINEERING_NO_TELEMETRY=1`
107
+ in the environment. Deleted server-side after 90 days; the full contract is
108
+ at api.memgineering.com/privacy.
109
+
110
+ **`--hook off` removes them**, it does not merely decline to add them, so it is
111
+ the answer when someone already has the callbacks and has decided they do not
112
+ want them. Only groups memgineering wrote are taken out; anything else in that
113
+ settings file is left alone.
114
+
115
+ **After setup the agent session has to restart** for the guidance to load. Say
116
+ so, or they will wonder why nothing changed.
117
+
118
+ ### When it reports something it could not do
119
+
120
+ The guide lives between `<!-- memgineering-start -->` and
121
+ `<!-- memgineering-end -->`, and those markers are the only way it can be found
122
+ again. Two outcomes are worth recognising:
123
+
124
+ - **`N file(s) could not be written`** — a guide setup wrote is still in that
125
+ file with its markers gone, or a settings file is not valid JSON. Everything
126
+ else in that run WAS applied; the exit code is non-zero so the one skipped
127
+ file is not mistaken for a clean install. Put the markers back around the
128
+ block, or delete the block, then run setup again. Never append a second copy
129
+ by hand: two guides means both are in the user's context every session.
130
+ - **`Appended below an unmarked guide`** — the same shape, on a file setup has
131
+ no record of writing, so it installed rather than refusing. Look at the file:
132
+ if an older unmarked copy is now sitting above the new block, delete that copy.
133
+ If those lines are the user's own writing, nothing is wrong.
134
+ - **`Replaced N file(s) you had edited`** — the bytes on disk were not the ones
135
+ setup last wrote, so someone's own words were just overwritten. setup owns
136
+ those files and an upgrade has to replace them; what belongs to the user goes
137
+ OUTSIDE the markers, where nothing touches it. Ordinary upgrades do not print
138
+ this.
139
+
140
+ The hooks go to Claude Code and Codex, and only there. Codex asks the user to
141
+ review new hooks once at the start of the next session and runs neither until
142
+ they answer — **tell them the key: `t` trusts them.** Measured on Codex
143
+ 0.149.1: both hooks show `Installed 1 / Active 0` until that panel is
144
+ answered, and the trust is recorded per hook CONTENT
145
+ (`[hooks.state."<path>:<event>:0:0"] trusted_hash`) in `~/.codex/config.toml`,
146
+ so an upgrade that changes a hook asks again. Somebody who is not told this
147
+ reads the silence as an install that did not take.
148
+
149
+ Grok is the case worth knowing, because the obvious guess is wrong: it has
150
+ hooks, more events than either of those two, and `~/.grok/hooks/` needs no
151
+ trust prompt — but a hook there cannot say anything to the model. Measured
152
+ three ways on 1.0.3, each with a value the session could not have known:
153
+ `PreToolUse` with `additionalContext`, `SessionStart` stdout, and
154
+ `UserPromptSubmit` with `additionalContext`. All three hooks ran; none of the
155
+ three arrived. Its own docs agree — `PreToolUse` reads `decision`/`deny`, and
156
+ "every other event is passive". So Grok gets the guide and the skills, which do
157
+ reach it, and nothing that would spawn a process to talk to nobody.
158
+
159
+ On Grok and Antigravity, run `memgineering resurface` yourself when you start
160
+ work in a folder, and `memgineering rules` before you change anything — that is
161
+ the same job the hooks do elsewhere, done by hand.
162
+
163
+ ### The screen, in more detail
164
+
165
+ ```
166
+ memgineering setup --web # the default: a page in their own browser
167
+ memgineering setup --web --print-url # no browser here — hand over the link
168
+ memgineering setup --human # checkbox screen in your terminal, no browser
169
+ ```
170
+
171
+ The page is on memgineering.com, not on this machine — the same site, the same
172
+ sign-in, the same design. So a person who is already signed in there is
173
+ recognised, and the sign-in they do on that screen is the ONLY one the whole
174
+ install asks for. **Do not run `login` first**; it adds an approval to a flow
175
+ that no longer needs one.
176
+
177
+ **The command returns; the screen does not.** With nobody watching a terminal
178
+ (you, a pipe, a CI job) the waiting half detaches and keeps going after your
179
+ command exits, so a slow reader cannot time your call out. `--wait` forces the
180
+ old behaviour of blocking until the screen is answered, for a script that
181
+ genuinely wants it.
182
+
183
+ It covers step 2 as well, with the same disclosure `link --dry-run` prints —
184
+ including, for someone who already keeps notes on this machine, the option to
185
+ carry that folder up to the account. Folder names are sent only after the
186
+ screen asks for them, and never their contents.
187
+
188
+ ## 2. Connect a brain
189
+
190
+ Signed in — the default — a brain belongs on the account, where every machine
191
+ and every tool they use reads the same one. Three openings; run
192
+ `memgineering brains` first to learn which one you are in:
193
+
194
+ **The account already holds brains** — list, ask which, point:
195
+
196
+ ```
197
+ memgineering brains # what it holds, with note counts
198
+ memgineering use --brain work # nothing is uploaded by switching
199
+ ```
200
+
201
+ **The account holds nothing and there are no notes here** — make one:
202
+
203
+ ```
204
+ memgineering create work --user "Rayul" --language Korean --about "one line"
205
+ ```
206
+
207
+ Agree the NAME with the user first, and ask the three base questions in their
208
+ language — what to call them, which language to answer in, one line about who
209
+ they are. Every flag except the name is optional: leave out what they do not
210
+ want to say. `create` makes the brain on the account, writes the six starter
211
+ notes, records those answers as real content, points this machine at it, and
212
+ its output says how many base files are still empty templates —
213
+ `memgineering onboard` prints what to ask for the rest, and it now reaches a
214
+ hosted brain too. Its `--json` may also report `missing`: base notes the brain
215
+ does not hold at all, with a `missing_hint` naming the way to put them there —
216
+ never a revise instruction that cannot succeed.
217
+
218
+ A name the account already holds is refused with nothing written — `use
219
+ --brain <name>` points at it instead, or agree a different name. The one
220
+ exception is a brain holding nothing but its own untouched scaffolding: that
221
+ is an interrupted `create`, and running the same command again finishes it.
222
+
223
+ ### Renaming and deleting a hosted brain
224
+
225
+ **A wrongly-named brain is a rename, not a delete.** `memgineering rename
226
+ <new name>` changes what the brain this machine reads is called, in place —
227
+ notes, ledger and id untouched; `--brain <name-or-id>` renames another one.
228
+ Other machines pick the new name up on their own next command; nothing on
229
+ them breaks, because pointers hold the id. Never create a second brain to
230
+ fix a name.
231
+
232
+ `memgineering delete-brain <name-or-id> --confirm "<exact name>"` is the
233
+ destructive one: the brain, every note in it, its ledger and its
234
+ measurements, gone from the server, not recoverable. Run it ONLY when the
235
+ person has explicitly asked for THIS brain to be deleted, and take the
236
+ confirm name from what they said — never type it for them from a listing to
237
+ tidy an account up. Without `--confirm` in a real terminal it asks the
238
+ person to retype the brain's name; with no terminal it refuses rather than
239
+ deciding. `unlink --brain` is the gentle sibling: it only stops this machine
240
+ reading a brain and deletes nothing.
241
+
242
+ **They already keep notes in a folder on this machine** — carry them up
243
+ instead of starting empty:
244
+
245
+ ```
246
+ memgineering push --brain work # folder → account; deletes nothing local
247
+ memgineering reindex # makes the moved notes searchable by meaning
248
+ ```
249
+
250
+ ### Migrating notes that were never memgineering notes
251
+
252
+ `push` carries files; it does not turn prose into memory. After a migration,
253
+ offer — do not sweep — a pass over the notes they actually care about: ask
254
+ WHICH matter, `memgineering open` each, then
255
+ `memgineering revise <path> --action reinforce --claim "<one factual line the
256
+ note itself contains>" --summary "<what recall should show>"`. Never write a
257
+ claim the note does not contain: a guessed fact recalled later is
258
+ indistinguishable from something they said. One `reindex` at the end covers
259
+ the whole batch.
260
+
261
+ ### Machine-only (they chose `--no-login`)
262
+
263
+ **They already keep notes somewhere:**
264
+
265
+ ```
266
+ memgineering link ~/notes
267
+ ```
268
+
269
+ Prints exactly what would be indexed and what would be refused — with samples of
270
+ the real lines that would be stored — then asks. **Run it and stop.** Do not
271
+ pass `--yes` for them: that screen is the one moment they decide what this tool
272
+ may read.
273
+
274
+ With no terminal attached it says so rather than assuming no. Then show them
275
+ `memgineering link <path> --dry-run` — same disclosure, writes nothing — wait
276
+ for a real yes, and only then run with `--yes`.
277
+
278
+ **Tell them one thing before they answer:** the title and first paragraph of
279
+ every listed note gets stored outside the folder, and with the session-start
280
+ hook on, a few of those summaries reach every new session unasked. Anything they
281
+ would not want in either place goes in `.memgdeny` at the top of the folder, one
282
+ path per line, no wildcards:
283
+
284
+ ```
285
+ 30_personal/medical.md
286
+ journal/ (a trailing slash covers a whole folder)
287
+ ```
288
+
289
+ A `.memgdeny` line matching no file is refused on purpose — a rule with a wrong
290
+ path protects nothing.
291
+
292
+ **They have no notes yet:**
293
+
294
+ ```
295
+ memgineering init ~/brain
296
+ ```
297
+
298
+ Creates the layout and links it. Tell them to fill in `01_BASE/USER.md` and
299
+ leave the rest; the folders are there for when they are needed, not as homework.
300
+
301
+ ### Several brains
302
+
303
+ Normal — one of their own, a shared folder, one per project. Which one answers is
304
+ decided in this order: `--vault <path>` → a `.memgineering` pointer found by
305
+ walking up → the brain the cwd is inside → the only one linked → their default.
306
+
307
+ ```
308
+ memgineering use ~/brains/work # bind this directory to one brain
309
+ memgineering use --default ~/brains/work
310
+ ```
311
+
312
+ Inside a repository `use` writes a relative path, so it can be committed and
313
+ resolves for a teammate who links the same brain.
314
+
315
+ ### Which project a folder is
316
+
317
+ ```
318
+ memgineering project # what this folder answers to, and how it was decided
319
+ memgineering project acme/site # bind a name of your own to this repository
320
+ memgineering project --unset # back to the derived name
321
+ ```
322
+
323
+ Derived without asking: the git remote's `owner/repo`, else the checkout's
324
+ folder name, else nothing — a folder outside any repository names no project
325
+ until somebody sets one. The name follows the repository, so worktrees and
326
+ subfolders of one checkout answer the same. It is what `remember` stamps as a
327
+ note's scope and what the reads send as `asked_from`, so a hosted resurface
328
+ can rank what was asked about here — as a name; the folder's path never
329
+ leaves the machine. Renaming does not move history: what was recalled under
330
+ the old name stays recorded there and the new name starts fresh, which the
331
+ command says out loud whenever it changes anything.
332
+
333
+ **An account can hold several hosted brains. `brains` lists them and
334
+ `use --brain <name>` switches.**
335
+
336
+ ```
337
+ memgineering brains # what the account holds, and which one this machine reads
338
+ memgineering use --brain work # name or id; nothing is uploaded
339
+ ```
340
+
341
+ **Run `brains` before you switch, not after a guess.** It carries a note count
342
+ and a creation date, which is what tells two brains apart when their names do
343
+ not — and it marks the one this machine currently reads. `--json` puts that id
344
+ at the top level as `current`, so you do not have to scan the array to answer
345
+ the question you most often have. An absent `note_count` is `null` and not `0`:
346
+ zero notes is an empty brain, and no count is a server too old to send one.
347
+
348
+ It moves the one hosted brain this machine reads and touches no notes — `push`
349
+ and `pull` are what move those. It does not create: an unknown name is refused
350
+ with the account's list, because pointing at a brain that does not exist would
351
+ have every recall answer from an empty one, and from the outside that looks like
352
+ the notes are gone. Making a NEW brain is `create <name>` (empty, scaffolded)
353
+ or `push --brain <name>` (filled from a folder) — both point this machine at
354
+ the result on their own.
355
+
356
+ It refuses a folder path, `--default` or `--here` in the same call. Those bind a
357
+ folder; this is one setting for the whole machine.
358
+
359
+ **Do not give up on a write because the choice is ambiguous.** A refused
360
+ `remember` means the thing they asked you to keep was not kept — ask which
361
+ brain, or pass `--vault` for the write and settle the default afterwards.
362
+
363
+ ## Checking it worked
364
+
365
+ ```
366
+ memgineering recall "anything" # should answer, even if with "nothing matched"
367
+ memgineering log # what this brain has recorded
368
+ ```
369
+
370
+ ## Asking where things stand, without changing them
371
+
372
+ There is no `status` verb. Three read-only questions cover it, and none of them
373
+ writes anything:
374
+
375
+ ```
376
+ memgineering setup --agent --dry-run # which tools are installed, what would change
377
+ memgineering whoami # which account this machine is signed in as
378
+ memgineering use # which brain answers recall and takes writes
379
+ ```
380
+
381
+ **`use` is the one to run before believing anything about where a note went.**
382
+ Signed in and pointed at a hosted brain, it names that brain — where `recall`
383
+ reads and every write lands — and then the folder on this disk, which `--local`
384
+ reaches and which the before-edit hook reads.
385
+
386
+ Pointed at one with no sign-in here (what `logout` leaves: token cleared,
387
+ pointer kept), it names the **folder** first, because that is genuinely where
388
+ the next write goes — nothing refuses, it falls through to the local brain.
389
+
390
+ The third state is a sign-in left waiting by `login --emit-only`: it names the
391
+ folder AND the waiting sign-in, because until somebody approves it the next
392
+ command's claim is refused and the write lands in the folder — and once approved
393
+ that same claim succeeds and everything goes to the hosted brain.
394
+
395
+ In `--json`, read **`destination`**: `"hosted"`, `"local"`, or `"pending"`.
396
+ `"pending"` is not a hedge — a sign-in waiting for approval lands writes in
397
+ `brain` until somebody approves it and in the hosted brain after, and this
398
+ command will not open a browser to find out which. Do not read
399
+ `hosted.signed_in` for this: it is `false` for both the logged-out and the
400
+ waiting state, and those go to different places. It reads state off the disk, so
401
+ it answers with the server down and never finishes a sign-in just for being
402
+ asked.
403
+
404
+ `setup --agent --dry-run` is the one worth naming out loud, because the answer to
405
+ "am I installed" lives behind a verb that otherwise installs. A tester who wanted
406
+ the answer either avoided `setup` and had no answer, or ran it without
407
+ `--dry-run`. It writes nothing at all — it reports.
408
+
409
+ The hook itself is `memgineering guard`, deliberately absent from `--help`: it
410
+ reads a PreToolUse payload on stdin and does nothing without one, so listing it
411
+ would put "run this" in front of an agent for a command that cannot work when
412
+ run. If a hook is misbehaving, that is the name to look for in the tool's hook
413
+ config — not a command to invoke by hand.
414
+
415
+ ## Moving a brain between this machine and their account
416
+
417
+ ```
418
+ memgineering push # this folder → their account
419
+ memgineering pull ~/my-brain # their account → a folder here
420
+ ```
421
+
422
+ Both are safe to run twice and careful in opposite directions: **`push` never
423
+ deletes anything locally, `pull` never overwrites anything locally.** Whatever
424
+ was already there is left alone and counted, so an interrupted transfer finishes
425
+ by running the same command again. `--dry-run` on either lists what would move.
426
+
427
+ Reach for `pull` when they want a backup, are moving machines, or ask where
428
+ their memory actually lives. **Say what it brings**: notes the brain excludes
429
+ from recall come down too — excluded means "stop reading this", not "this is no
430
+ longer yours" — along with `.memgignore`. Readable files in a folder is not
431
+ something to let them discover later.
432
+
433
+ **One `pull` is one brain, not one account.** If the output names other hosted
434
+ brains (`other_brains` in `--json`), this folder is not their memory — it is part
435
+ of it. Run `pull --brain <name> <folder>` for each before telling them anything
436
+ is backed up. A partial backup nobody knows is partial is worse than one that
437
+ failed.
438
+
439
+ What lands is markdown, not yet a brain here. Offer `memgineering link <folder>`
440
+ as a next step rather than running it.
441
+
442
+ ### What a hosted brain does that a folder does not
443
+
444
+ Every verb works on either kind now, consolidation included. Two things are
445
+ only true of a hosted brain.
446
+
447
+ **Meaning is searched, if a model is configured for it.** That is what lets an
448
+ English question reach a Korean note. It needs `BRAIN_EMBEDDING_URL` and
449
+ `BRAIN_EMBEDDING_MODEL` set on the server; with neither, the brain searches text
450
+ and says so. Recall reports which happened — `semantic: "used"` or `"skipped"`
451
+ with a reason — so if somebody expected meaning-based matching and did not get
452
+ it, read that field before guessing. A brain in a folder always searches text
453
+ and needs no model anywhere; that is a decision, not a gap.
454
+
455
+ **Its indexes live on the server.** Nothing to install and nothing to rebuild
456
+ by hand in the ordinary case — writes keep the index in step on their own.
457
+ `memgineering reindex` reaches either kind of brain: on a hosted one it backfills
458
+ what is missing and clears stored rows for notes the brain has since been told
459
+ not to read, reporting both; `--local` forces the folder brain. On a brain in a
460
+ FOLDER it also names what it left out — notes a deny name, a `.memgignore` rule
461
+ or a symlink kept from the index, and any folder a rule excluded whole — so "3
462
+ notes rebuilt" is never the whole answer when a fourth was dropped. A hosted
463
+ reindex cannot say that: the rules are applied on the machine that pushed, so
464
+ the server only ever saw what arrived.
465
+
466
+ Under `--json` that is `not_indexed` with `denied_by_name`, `denied_explicitly`,
467
+ `excluded_by_rule`, `skipped_symlinks` and `excluded_folders`. **Read the count
468
+ together with `excluded_folders`**: a rule that names a folder stops the walk at
469
+ the folder, so nothing inside it is ever counted — `not_indexed: 0` beside a
470
+ non-empty `excluded_folders` means the count is a floor, not the answer. `push`
471
+ reports the same set with its total under `not_sent`. `--rebuild`
472
+ exists for one situation only, where an embedding model changed the shape of its
473
+ answers without changing its name and the index has to be laid down again.
474
+
475
+ ## Turning things off
476
+
477
+ ```
478
+ memgineering setup --agent --auto-update off
479
+ memgineering unlink # stop reading a brain; notes untouched
480
+ memgineering unlink --purge # also delete the local index and undo snapshots
481
+ ```
482
+
483
+ `MEMGINEERING_NO_UPDATE=1` skips the update check for a single run without
484
+ changing the setting.