agent-procedures 0.1.0 → 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.
package/README.md CHANGED
@@ -2,21 +2,72 @@
2
2
 
3
3
  Procedural memory for coding agents.
4
4
 
5
+ Coding agents are pretty good at figuring things out. They're bad at remembering how they did it last time, so they just figure it out again. Every time.
6
+
7
+ Reflex watches the tools your agent actually runs, keeps the paths that worked, and hands them back the next time you ask for something similar. It doesn't store facts, your docs already do that. It stores how.
8
+
9
+ The npm package is `agent-procedures`. The product is Reflex.
10
+
11
+ ## How it works (hot path vs cold path)
12
+
13
+ The **hot path** runs every time you prompt the agent or the agent runs a tool. It has to be fast, so it doesn't call an LLM. It's just disk I/O. When you ask for something, Reflex checks its memory for a match and injects the steps into the agent's context. When the agent uses tools, Reflex traces what happens. If the agent gets the job done without leaving broken steps behind, Reflex saves that trace as a new procedure.
14
+
15
+ The **cold path** is a background groomer. Once 5 new procedures pile up, it kicks off a background process that asks a cheap LLM to review them. It drops the risky ones and adds aliases (like synonyms) to the good ones so they match more easily next time.
16
+
17
+ You don't run either of these manually. You just use your agent.
18
+
19
+ ## Status & Harnesses
20
+
21
+ Early. Reflex is built to plug into different agent platforms (harnesses). Right now, **Claude Code is the only one built** and is the default.
22
+
23
+ I set the engine up so Cursor and others can plug in later, but the adapters for those don't exist yet.
24
+
5
25
  ## Install
6
26
 
27
+ Run this in the repo you want Reflex in:
28
+
7
29
  ```bash
8
30
  npx agent-procedures init
9
31
  ```
10
32
 
11
- Creates a project-scoped store:
33
+ By default this installs the Claude Code harness. If you were using a different one later, you'd run `npx agent-procedures init --harness cursor`.
34
+
35
+ Installing the package on its own won't do anything. You need `init`. It creates the folders, copies the runtime in, and adds a hook so your agent knows to call it.
36
+
37
+ ## API key (for the background groomer)
38
+
39
+ Because the groomer uses an LLM to review procedures, it needs a cheap model key.
40
+
41
+ If you already have `ANTHROPIC_API_KEY`, `OPENAI_API_KEY` or `GEMINI_API_KEY` exported in your terminal, it just uses that. Otherwise:
42
+
43
+ ```bash
44
+ npx agent-procedures auth login # pick a provider, paste your key
45
+ npx agent-procedures auth status # check what it's using and the last groomer error
46
+ ```
47
+
48
+ The key gets checked before it's saved, so a typo fails right away instead of a week later in a log file. It gets stored in `~/.reflex/credentials.json` on your machine and only you can read it.
49
+
50
+ ## What ends up in your repo
12
51
 
13
52
  ```
14
53
  .reflex/
15
- config.json # settings (not memory)
16
- procedures.jsonl # remembered procedures
54
+ config.json # settings, not memory
55
+ procedures.jsonl # what it remembered
17
56
  runs.jsonl # optional run outcomes
57
+ runtime.js # the engine, one bundled file — do not edit
58
+ traces/ # scratch for the current turn
18
59
  ```
19
60
 
20
- `.reflex/` is added to `.gitignore` by default.
61
+ `traces/` gets added to `.gitignore`. **Commit everything else**, including `.claude/settings.json` (the hook wiring), so anyone who clones the repo gets the same memory. If you upgrade the package, run `init` again. That overwrites `runtime.js`.
62
+
63
+ ## Adding a harness
64
+
65
+ If you want to build an adapter for something other than Claude Code:
66
+
67
+ Only three things change between harnesses: where hooks get registered, what the event payload looks like, and how context gets passed back to the agent. The rest of the engine doesn't care who called it.
68
+
69
+ Adding one is a single file in `lib/harnesses/` plus one line in `lib/harnesses/index.js`. `claude.js` is the reference.
70
+
71
+ ## License
21
72
 
22
- npm install alone does nothing — you need `init` to seed the project.
73
+ MIT
package/bin/cli.js CHANGED
@@ -8,19 +8,48 @@ if (!command || command === "--help" || command === "-h") {
8
8
  console.log(`agent-procedures — procedural memory for coding agents (Reflex)
9
9
 
10
10
  Usage:
11
- npx agent-procedures init Create .reflex/ in the current project
11
+ npx agent-procedures init [--harness claude] Create .reflex/ and wire hooks
12
+ npx agent-procedures auth login Store an API key for the background groomer
13
+ npx agent-procedures auth status Show which provider/key the groomer will use
12
14
  `);
13
15
  process.exit(command ? 0 : 1);
14
16
  }
15
17
 
16
18
  if (command === "init") {
17
- const results = init(process.cwd());
18
- console.log("Initialized Reflex in .reflex/");
19
- console.log(` config.json ${results.config}`);
20
- console.log(` procedures.jsonl ${results.procedures}`);
21
- console.log(` runs.jsonl ${results.runs}`);
22
- console.log(` .gitignore ${results.gitignore}`);
23
- process.exit(0);
19
+ const args = process.argv.slice(3);
20
+ const i = args.indexOf("--harness");
21
+ const harness = i >= 0 ? args[i + 1] : undefined;
22
+ try {
23
+ const results = init(process.cwd(), { harness });
24
+ console.log("Initialized Reflex in the repository");
25
+ console.log(` .reflex/config.json ${results.config}`);
26
+ console.log(` .reflex/procedures.jsonl ${results.procedures}`);
27
+ console.log(` .reflex/runs.jsonl ${results.runs}`);
28
+ console.log(` .reflex/runtime.js ${results.runtime}`);
29
+ console.log(` .gitignore ${results.gitignore}`);
30
+ console.log(` hooks (${harness || "claude"}) ${results.hooks}`);
31
+ process.exit(0);
32
+ } catch (e) {
33
+ console.error(`Error: ${e.message}`);
34
+ process.exit(1);
35
+ }
36
+ }
37
+
38
+ if (command === "auth") {
39
+ const { login, status, USAGE } = await import("../lib/auth.js");
40
+ const [sub, ...rest] = process.argv.slice(3);
41
+ try {
42
+ if (sub === "login") await login(rest);
43
+ else if (sub === "status") status();
44
+ else {
45
+ console.error(USAGE);
46
+ process.exit(1);
47
+ }
48
+ process.exit(0);
49
+ } catch (e) {
50
+ console.error(`Error: ${e.message}`);
51
+ process.exit(1);
52
+ }
24
53
  }
25
54
 
26
55
  console.error(`Unknown command: ${command}`);