myagentmemory 0.4.15 → 0.4.17

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.
@@ -18,29 +18,27 @@ const MISSING_ENTITLEMENT = {
18
18
  state: "missing",
19
19
  features: [],
20
20
  capabilities: {},
21
- reason: "Enter an email address to activate the free daily session allowance",
21
+ reason: "Install the no-account Pro preview to activate local recall and learning",
22
22
  };
23
23
  function cloneEntitlement(value) {
24
24
  return structuredClone(value);
25
25
  }
26
- function freeEntitlement(dailySessionLimit) {
26
+ function freeEntitlement() {
27
27
  return {
28
28
  plan: "free",
29
29
  state: "active",
30
30
  features: ["session-intelligence", "web-console"],
31
31
  capabilities: {
32
32
  "session-index": { enabled: true },
33
- "session-worker": {
34
- enabled: true,
35
- quota: { limit: dailySessionLimit, window: "day", scope: "account" },
36
- },
37
- learning: { enabled: true },
33
+ recall: { enabled: true, quota: { limit: 10, window: "day", scope: "device" } },
34
+ "session-worker": { enabled: false },
35
+ learning: { enabled: true, quota: { limit: 1, window: "day", scope: "device" } },
38
36
  "retrieval-evaluation": { enabled: true },
39
37
  "operational-metrics": { enabled: true },
40
38
  "web-console": { enabled: true },
41
39
  "memory-explorer": { enabled: true },
42
40
  },
43
- reason: `${dailySessionLimit} free agent sessions per UTC day`,
41
+ reason: "Free preview: 10 recalls and 1 learning scan per local day; indexing and dashboard access remain available",
44
42
  };
45
43
  }
46
44
  function isEmail(value) {
@@ -57,12 +55,102 @@ function securityHeaders(contentType) {
57
55
  "X-Content-Type-Options": "nosniff",
58
56
  };
59
57
  }
58
+ const ACTIVATION_PAGE_STYLES = `
59
+ :root{color-scheme:light;font-family:Inter,ui-sans-serif,-apple-system,BlinkMacSystemFont,"Segoe UI",sans-serif;color:#172033;background:#f4f7fb;font-synthesis:none}
60
+ *{box-sizing:border-box}
61
+ body{min-height:100vh;margin:0;padding:2rem 1.25rem;display:grid;place-items:center;background:radial-gradient(circle at 12% 0%,#e8f0ff 0,transparent 38rem),radial-gradient(circle at 100% 100%,#eef2ff 0,transparent 32rem),#f7f9fc}
62
+ main{width:min(100%,34rem)}
63
+ .skip-link{position:fixed;z-index:1;top:1rem;left:1rem;padding:.65rem .8rem;border-radius:.55rem;background:#172033;color:#fff;font-weight:700;transform:translateY(-200%)}
64
+ .skip-link:focus{transform:translateY(0)}
65
+ .brand{display:flex;align-items:center;gap:.75rem;margin:0 0 1.25rem .25rem;color:#33415c;font-size:.875rem;font-weight:700;letter-spacing:.01em}
66
+ .mark{width:2.25rem;height:2.25rem;display:grid;place-items:center;border-radius:.7rem;background:linear-gradient(145deg,#172033,#3159b8);color:#fff;box-shadow:0 .5rem 1.25rem rgba(35,65,130,.2);font-size:1.05rem;letter-spacing:-.08em}
67
+ .card{padding:clamp(1.5rem,5vw,2.5rem);border:1px solid rgba(205,216,231,.9);border-radius:1.5rem;background:rgba(255,255,255,.94);box-shadow:0 1.5rem 4rem rgba(32,51,84,.12),0 .125rem .375rem rgba(32,51,84,.06);backdrop-filter:blur(1rem)}
68
+ .eyebrow{display:inline-flex;align-items:center;gap:.45rem;margin:0 0 1rem;padding:.42rem .7rem;border:1px solid #d9e4f7;border-radius:999px;background:#f3f7ff;color:#315798;font-size:.78rem;font-weight:750;letter-spacing:.03em;text-transform:uppercase}
69
+ .eyebrow::before{content:"";width:.45rem;height:.45rem;border-radius:50%;background:#2b67d1;box-shadow:0 0 0 .22rem #dbe8ff}
70
+ h1{margin:0;color:#141d2c;font-size:clamp(2rem,7vw,2.75rem);line-height:1.06;letter-spacing:-.045em;text-wrap:balance}
71
+ .intro{margin:.9rem 0 1.75rem;color:#526176;font-size:1.05rem;line-height:1.55}
72
+ form{display:grid;gap:.75rem}
73
+ label{color:#29364a;font-size:.9rem;font-weight:700}
74
+ input{width:100%;min-height:3.25rem;padding:.8rem 3.5rem .8rem 1rem;border:1px solid #bcc8d8;border-radius:.8rem;background:#fff;color:#172033;font:inherit;box-shadow:inset 0 1px 2px rgba(24,39,65,.04)}
75
+ input::placeholder{color:#8a96a7}
76
+ input:hover{border-color:#92a2b8}
77
+ input:focus-visible{outline:0;border-color:#2b67d1;box-shadow:0 0 0 .25rem rgba(43,103,209,.15)}
78
+ button{min-height:3.35rem;margin-top:.25rem;padding:.85rem 1rem;border:1px solid #172033;border-radius:.8rem;background:linear-gradient(180deg,#24334a,#172033);color:#fff;font:inherit;font-weight:750;cursor:pointer;box-shadow:0 .55rem 1.2rem rgba(23,32,51,.18);touch-action:manipulation;transition:transform .15s}
79
+ button:hover{background:linear-gradient(180deg,#2d405c,#1d2a40);box-shadow:0 .7rem 1.4rem rgba(23,32,51,.23);transform:translateY(-1px)}
80
+ button:active{transform:translateY(0)}
81
+ button:focus-visible,summary:focus-visible{outline:.2rem solid rgba(43,103,209,.32);outline-offset:.18rem}
82
+ .terminal-note{margin:.8rem 0 0;color:#6a7789;font-size:.85rem;text-align:center}
83
+ .error{margin:0 0 1rem;padding:.8rem 1rem;border:1px solid #efb8bd;border-radius:.75rem;background:#fff3f4;color:#982631;font-size:.9rem;line-height:1.45}
84
+ details{margin-top:1.5rem;padding-top:1.25rem;border-top:1px solid #e2e8f0;color:#5b687a;font-size:.85rem;line-height:1.55}
85
+ summary{color:#46566d;font-weight:700;cursor:pointer;list-style-position:outside;touch-action:manipulation}
86
+ details p{margin:.8rem 0 0}
87
+ .never-sent{padding:.75rem .85rem;border-radius:.65rem;background:#f5f7fa;color:#536176}
88
+ .success{display:grid;place-items:center;width:3.5rem;height:3.5rem;margin-bottom:1.4rem;border-radius:1rem;background:#eaf7ef;color:#197542;font-size:1.65rem;font-weight:800;box-shadow:inset 0 0 0 1px #c9ead6}
89
+ .completion .intro{margin-bottom:0}
90
+ @media (max-width:30rem){body{padding:1rem}.brand{margin-left:.1rem}.card{border-radius:1.15rem}h1{font-size:2rem}}
91
+ @media (prefers-reduced-motion:reduce){input,button{transition:none}}
92
+ `;
60
93
  function activationPage(action, error) {
61
- const errorHtml = error ? `<p class="error">${error}</p>` : "";
62
- return `<!doctype html><html lang="en"><head><meta charset="utf-8"><meta name="viewport" content="width=device-width"><title>Activate AgentMemory</title><style>body{font:16px system-ui;max-width:34rem;margin:10vh auto;padding:0 1.5rem;color:#18212b}form{display:grid;gap:1rem}input,button{font:inherit;padding:.8rem;border-radius:.5rem;border:1px solid #aab4bf}button{background:#18212b;color:#fff;cursor:pointer}.muted{color:#586574}.error{color:#a21d24}</style></head><body><h1>Activate AgentMemory</h1><p>Enter an email address to enable the free daily agent-session allowance on this device.</p>${errorHtml}<form method="post" action="${action}"><label>Email <input type="email" name="email" autocomplete="email" maxlength="254" required autofocus></label><button type="submit">Activate and return to terminal</button></form><p class="muted">The AgentMemory CLI sends your email plus core, bundle, platform, architecture, and release-channel metadata to the private activation service. D1 stores a daily count of opaque SessionStart operations for your normalized email. The request never includes memory, session content, queries, repository paths, raw agent session identifiers, IP addresses, or user-agent strings. Activation records expire after 365 days without use.</p></body></html>`;
94
+ const errorHtml = error ? `<p class="error" id="activation-error" role="alert">${error}</p>` : "";
95
+ const describedBy = error ? "activation-error terminal-note" : "terminal-note";
96
+ const autofocus = error ? " autofocus" : "";
97
+ return `<!doctype html>
98
+ <html lang="en">
99
+ <head>
100
+ <meta charset="utf-8">
101
+ <meta name="viewport" content="width=device-width, initial-scale=1">
102
+ <meta name="theme-color" content="#f4f7fb">
103
+ <title>Activate AgentMemory</title>
104
+ <style>${ACTIVATION_PAGE_STYLES}</style>
105
+ </head>
106
+ <body>
107
+ <a class="skip-link" href="#activation">Skip to Activation</a>
108
+ <main id="activation">
109
+ <div class="brand" translate="no"><span class="mark" aria-hidden="true">AM</span><span>AgentMemory</span></div>
110
+ <section class="card" aria-labelledby="activation-title">
111
+ <p class="eyebrow">Free daily allowance</p>
112
+ <h1 id="activation-title">Activate This Device</h1>
113
+ <p class="intro">Use your email to enable AgentMemory Pro for your local agent sessions.</p>
114
+ <form method="post" action="${action}">
115
+ <label for="email">Email address</label>
116
+ ${errorHtml}
117
+ <input id="email" type="email" name="email" autocomplete="email" inputmode="email" spellcheck="false" placeholder="you@example.com…" maxlength="254" required${autofocus} aria-describedby="${describedBy}">
118
+ <button type="submit">Activate AgentMemory</button>
119
+ </form>
120
+ <p class="terminal-note" id="terminal-note">Your terminal will finish setup after activation.</p>
121
+ <details>
122
+ <summary>What’s shared during activation</summary>
123
+ <p>Your email identifies your free daily allowance. The CLI also sends core and bundle versions, platform, architecture, and release channel. The service stores a daily count of opaque session-start operations. Activation records expire after 365 days without use.</p>
124
+ <p class="never-sent"><strong>Never sent:</strong> The request never includes memory, session content, queries, repository paths, raw agent session identifiers, IP addresses, or user-agent strings.</p>
125
+ </details>
126
+ </section>
127
+ </main>
128
+ </body>
129
+ </html>`;
63
130
  }
64
131
  function completionPage() {
65
- return '<!doctype html><html lang="en"><head><meta charset="utf-8"><meta name="viewport" content="width=device-width"><title>AgentMemory activated</title></head><body><h1>Activation complete</h1><p>You can close this tab and return to the terminal.</p></body></html>';
132
+ return `<!doctype html>
133
+ <html lang="en">
134
+ <head>
135
+ <meta charset="utf-8">
136
+ <meta name="viewport" content="width=device-width, initial-scale=1">
137
+ <meta name="theme-color" content="#f4f7fb">
138
+ <title>AgentMemory activated</title>
139
+ <style>${ACTIVATION_PAGE_STYLES}</style>
140
+ </head>
141
+ <body>
142
+ <a class="skip-link" href="#completion">Skip to Activation Status</a>
143
+ <main id="completion">
144
+ <div class="brand" translate="no"><span class="mark" aria-hidden="true">AM</span><span>AgentMemory</span></div>
145
+ <section class="card completion" aria-labelledby="completion-title">
146
+ <div class="success" aria-hidden="true">✓</div>
147
+ <p class="eyebrow">Device activated</p>
148
+ <h1 id="completion-title">You’re All Set</h1>
149
+ <p class="intro">Return to your terminal to finish installing AgentMemory Pro. You can close this tab.</p>
150
+ </section>
151
+ </main>
152
+ </body>
153
+ </html>`;
66
154
  }
67
155
  function send(response, status, body, contentType = "text/html; charset=utf-8") {
68
156
  response.writeHead(status, securityHeaders(contentType));
@@ -256,41 +344,27 @@ export class TemporaryPluginBackend {
256
344
  this.artifactOrigin = options.artifactOrigin ?? ARTIFACT_ORIGIN;
257
345
  this.fetchImplementation = options.fetch ?? globalThis.fetch;
258
346
  this.openUrl = options.openUrl ?? openLoopbackUrl;
259
- this.activate = options.activate ?? (() => collectTemporaryActivation(this.openUrl));
347
+ this.activate = options.activate ?? (async () => `am_install_${randomBytes(24).toString("base64url")}`);
260
348
  }
261
349
  async getLocalEntitlement() {
262
350
  const activation = this.readActivation();
263
- return activation ? freeEntitlement(activation.dailySessionLimit) : cloneEntitlement(MISSING_ENTITLEMENT);
351
+ return activation ? freeEntitlement() : cloneEntitlement(MISSING_ENTITLEMENT);
264
352
  }
265
353
  async resolveAccess(request) {
266
354
  const activation = this.readActivation();
267
- let email = activation?.email;
268
- if (!email) {
269
- if (!request.allowAuthentication)
270
- return {
271
- kind: "auth_required",
272
- entitlement: cloneEntitlement(MISSING_ENTITLEMENT),
273
- nextAction: {
274
- kind: "authenticate",
275
- url: "https://jayzeng.github.io/agentmemory/",
276
- message: "Run plugin install in an interactive terminal to enter an email address",
277
- },
278
- };
279
- email = await this.activate();
280
- }
355
+ const installationId = activation?.installationId ?? (await this.activate());
281
356
  const response = await this.request(`${this.apiOrigin}/v1/plugin/access`, {
282
357
  method: "POST",
283
358
  headers: { "Content-Type": "application/json" },
284
359
  body: JSON.stringify({
285
- schemaVersion: 1,
286
- email,
360
+ schemaVersion: 2,
361
+ installationId,
287
362
  bundleId: request.bundleId,
288
363
  installedVersion: request.installedVersion ?? null,
289
364
  coreVersion: this.coreVersion,
290
365
  channel: request.channel,
291
366
  platform: process.platform,
292
367
  architecture: process.arch,
293
- consentVersion: "activation-v2",
294
368
  }),
295
369
  });
296
370
  const value = (await readJson(response));
@@ -299,14 +373,20 @@ export class TemporaryPluginBackend {
299
373
  throw new PluginBootstrapFailure("service_response_invalid", "The access response omitted its artifact grant");
300
374
  if (typeof value.usageCredential !== "string" || !ACTIVATION_CREDENTIAL.test(value.usageCredential))
301
375
  throw new PluginBootstrapFailure("service_response_invalid", "The access response omitted its usage credential");
302
- const freeQuota = value.entitlement.capabilities["session-worker"]?.quota;
376
+ const recallQuota = value.entitlement.capabilities.recall?.quota;
377
+ const learningQuota = value.entitlement.capabilities.learning?.quota;
303
378
  if (value.entitlement.plan !== "free" ||
304
379
  value.entitlement.state !== "active" ||
305
- !freeQuota ||
306
- freeQuota.scope !== "account" ||
307
- freeQuota.window !== "day")
308
- throw new PluginBootstrapFailure("service_response_invalid", "The free session policy is invalid");
309
- this.writeActivation(email, value.usageCredential, freeQuota.limit);
380
+ !recallQuota ||
381
+ recallQuota.scope !== "device" ||
382
+ recallQuota.window !== "day" ||
383
+ !learningQuota ||
384
+ learningQuota.scope !== "device" ||
385
+ learningQuota.window !== "day" ||
386
+ value.entitlement.capabilities["session-index"]?.enabled !== true ||
387
+ value.entitlement.capabilities["web-console"]?.enabled !== true)
388
+ throw new PluginBootstrapFailure("service_response_invalid", "The free preview policy is invalid");
389
+ this.writeActivation(installationId, value.usageCredential, 1);
310
390
  return { kind: "granted", entitlement: value.entitlement, artifactGrant: value.artifactGrant };
311
391
  }
312
392
  async reserveSession(operationId) {
@@ -361,8 +441,9 @@ export class TemporaryPluginBackend {
361
441
  if (!stat.isFile() || stat.isSymbolicLink() || (process.platform !== "win32" && (stat.mode & 0o077) !== 0))
362
442
  return null;
363
443
  const value = JSON.parse(fs.readFileSync(activationPath, "utf-8"));
364
- if (value.schemaVersion !== 2 ||
365
- !isEmail(value.email) ||
444
+ if (value.schemaVersion !== 3 ||
445
+ typeof value.installationId !== "string" ||
446
+ !/^am_install_[A-Za-z0-9_-]{32}$/.test(value.installationId) ||
366
447
  !Number.isFinite(Date.parse(value.activatedAt)) ||
367
448
  !ACTIVATION_CREDENTIAL.test(value.usageCredential) ||
368
449
  !Number.isSafeInteger(value.dailySessionLimit) ||
@@ -375,9 +456,9 @@ export class TemporaryPluginBackend {
375
456
  return null;
376
457
  }
377
458
  }
378
- writeActivation(email, usageCredential, dailySessionLimit) {
379
- if (!isEmail(email))
380
- throw new PluginBootstrapFailure("email_invalid", "Enter a valid email address");
459
+ writeActivation(installationId, usageCredential, dailySessionLimit) {
460
+ if (!/^am_install_[A-Za-z0-9_-]{32}$/.test(installationId))
461
+ throw new PluginBootstrapFailure("activation_failed", "The installation identifier is invalid");
381
462
  if (!ACTIVATION_CREDENTIAL.test(usageCredential))
382
463
  throw new PluginBootstrapFailure("activation_failed", "The activation credential is invalid");
383
464
  if (!Number.isSafeInteger(dailySessionLimit) || dailySessionLimit <= 0 || dailySessionLimit > 10_000)
@@ -394,7 +475,13 @@ export class TemporaryPluginBackend {
394
475
  if (!directoryStat.isDirectory() || directoryStat.isSymbolicLink())
395
476
  throw new PluginBootstrapFailure("activation_path_invalid", "The plugin activation directory is unsafe");
396
477
  const temporary = `${target}.tmp-${process.pid}-${randomUUID()}`;
397
- fs.writeFileSync(temporary, `${JSON.stringify({ schemaVersion: 2, email, activatedAt: new Date().toISOString(), usageCredential, dailySessionLimit }, null, 2)}\n`, { mode: 0o600, flag: "wx" });
478
+ fs.writeFileSync(temporary, `${JSON.stringify({
479
+ schemaVersion: 3,
480
+ installationId,
481
+ activatedAt: new Date().toISOString(),
482
+ usageCredential,
483
+ dailySessionLimit,
484
+ }, null, 2)}\n`, { mode: 0o600, flag: "wx" });
398
485
  fs.renameSync(temporary, target);
399
486
  }
400
487
  async sessionUsage(action, operationId) {
@@ -2,7 +2,7 @@
2
2
 
3
3
  ## Status
4
4
 
5
- Accepted design on 2026-08-16 and revised on 2026-08-17. The public core implements host types, loopback email activation, live catalog and artifact retrieval, Ed25519 release verification, bounded package validation, transactional install, bundle health checks, paid-command dispatch, and SessionStart hook dispatch. The free plan grants a configurable number of agent sessions per normalized email and UTC day; durable account authentication, payment, renewal, and account management remain deferred.
5
+ Accepted design on 2026-08-16 and revised on 2026-08-17. The public core implements host types, anonymous preview activation, live catalog and artifact retrieval, Ed25519 release verification, bounded package validation, transactional install, bundle health checks, paid-command dispatch, and SessionStart hook dispatch. The free preview grants 10 device-local recalls and one device-local learning scan per local day while keeping indexing and Memory Dashboard visibility available. Account authentication, payment, renewal, and account management remain deferred.
6
6
 
7
7
  The public `agentmemory` repository and `myagentmemory` npm package remain the free, MIT-licensed core. The public bootstrap client and host contracts are also MIT-licensed. Official commercial implementations and browser assets are built and distributed separately from the private `agent-memory-plugin` workspace under their own terms. Pricing, the billing provider, device limits, offline-grace duration, and Enterprise contract terms are intentionally not decided here. The temporary beta currently uses allowlisted `*.agentmemory.paperpilot.me` service origins; changing those origins is a public-client release change.
8
8
 
@@ -10,10 +10,10 @@ The public `agentmemory` repository and `myagentmemory` npm package remain the f
10
10
 
11
11
  The public core will provide a small bootstrap and host surface for signed first-party plugins. It will not contain paid implementations, browser assets, commercial entitlement logic, or a general third-party marketplace.
12
12
 
13
- The primary user command is:
13
+ The primary product-facing command is:
14
14
 
15
15
  ```bash
16
- agent-memory plugin install
16
+ agent-memory pro install
17
17
  ```
18
18
 
19
19
  `plugin install` is an idempotent reconcile operation:
@@ -23,11 +23,11 @@ agent-memory plugin install
23
23
  | Plugin absent | Active or grace | Install the compatible signed bundle |
24
24
  | Plugin older than the selected release | Active or grace | Upgrade atomically |
25
25
  | Plugin current | Active or grace | Report that it is current |
26
- | Any | Missing | Start loopback email activation in an interactive terminal |
26
+ | Any | Missing | Request an anonymous free-preview entitlement and signed artifact grant |
27
27
  | Any | Expired | Direct the user to renewal; leave core available |
28
28
  | Incompatible bundle | Any | Leave the current version untouched and explain the required core version |
29
29
 
30
- An absent plugin cannot activate itself. The public bootstrap collects an email locally, obtains a server-issued usage credential and short-lived artifact grant, and verifies the release and artifact. The credential is persisted only after the service accepts activation. After installation, the public host reconstructs the free account-metered capability policy in core code and checks required capabilities before commands and hooks. Signed long-lived entitlements can extend this credential when authentication and payment ship.
30
+ An absent plugin cannot activate itself. The public bootstrap creates a random installation identifier, obtains a server-issued free-preview policy and short-lived artifact grant, and verifies the release and artifact. A mode-0600 activation record is persisted only after the service accepts the request. After installation, the public host reconstructs the free capability policy in core code and checks required capabilities before commands and hooks. Signed long-lived paid entitlements can extend this record when authentication and payment ship.
31
31
 
32
32
  ## Ownership boundary
33
33
 
@@ -67,6 +67,12 @@ Core memory operations must continue to work when the service is unreachable, a
67
67
  ### Bootstrap commands
68
68
 
69
69
  ```text
70
+ agent-memory pro
71
+ agent-memory pro install
72
+ agent-memory pro status
73
+ agent-memory pro upgrade
74
+ agent-memory pro manage
75
+
70
76
  agent-memory plugin
71
77
  agent-memory plugin list
72
78
  agent-memory plugin status
@@ -76,6 +82,8 @@ agent-memory plugin uninstall [--yes]
76
82
  agent-memory plugin manage [--no-browser]
77
83
  ```
78
84
 
85
+ The `pro` namespace is the user-facing surface. The `plugin` namespace remains supported for low-level administration and compatibility.
86
+
79
87
  - `plugin` with no subcommand prints a discovery summary and the next relevant command.
80
88
  - `list` reports known official plugins and whether each is installed and available. It does not download artifacts or inspect memory.
81
89
  - `status` is read-only. It reports the installed bundle, selected channel, compatibility, entitlement state, and update availability.
@@ -84,7 +92,7 @@ agent-memory plugin manage [--no-browser]
84
92
  - `uninstall` removes executable plugin material and the active receipt. It preserves core memory, plugin state, and the permission-restricted activation credential.
85
93
  - `manage` remains unavailable until authenticated account and billing management exists.
86
94
 
87
- Installed plugins contribute top-level commands such as `recall`, `learn`, `worker`, and `web`. Bootstrap command names are reserved by the core and cannot be replaced by a plugin.
95
+ Installed plugins contribute top-level commands including `recall` and `learn`; `dashboard` is a product-facing alias for the lower-level `web` command. Bootstrap command names are reserved by the core and cannot be replaced by a plugin.
88
96
 
89
97
  The current private compatibility CLI uses `plugin install` and `plugin uninstall` for skill files only. During migration, those meanings move to `install-skills --plugin-only` and `uninstall-skills --plugin-only`; the bootstrap command names above become authoritative.
90
98
 
@@ -93,13 +101,13 @@ The current private compatibility CLI uses `plugin install` and `plugin uninstal
93
101
  After a successful interactive `agent-memory init`, the core may print one informational line:
94
102
 
95
103
  ```text
96
- Optional: AgentMemory Pro adds session recall and a local Web Console.
97
- Run: agent-memory plugin install
104
+ Core remembers what you save. Pro learns from what you do.
105
+ Run: agent-memory pro install
98
106
  ```
99
107
 
100
- Top-level help includes an `Optional official plugins` section. Human-readable `status` may include the same recommendation while no official plugin is installed. Routine `context`, `read`, `write`, `search`, and scratchpad commands never show commercial prompts.
108
+ Top-level help includes a Pro section. Human-readable `status` may include the same recommendation while Pro is not installed. Routine `context`, `read`, `write`, `search`, and scratchpad commands never show commercial prompts.
101
109
 
102
- The core must not open a browser during package installation, `init`, `help`, `status`, or any normal memory operation. A browser may open only after an explicit interactive `plugin install`. `--no-browser`, non-interactive execution, and `--json` fail closed with `auth_required` when no activation record exists.
110
+ The free preview does not open a browser or request identity. Browsers remain restricted to explicit `dashboard`, future `pro manage`, and future paid upgrade/authentication flows. Non-interactive and `--json` installs use the same anonymous access request and still fail closed when the commercial service is unavailable.
103
111
 
104
112
  ### Machine-readable output
105
113
 
@@ -133,17 +141,17 @@ Every bootstrap command supports `--json` and emits one JSON document with a ver
133
141
 
134
142
  `result` is one of `not_installed`, `installed`, `upgraded`, `current`, `update_available`, `uninstalled`, `auth_required`, `renewal_required`, or `unavailable`. Failures use `ok: false` plus a stable `error.code` and redacted `error.message`. Output must never contain access tokens, download credentials, signed entitlement contents, local memory paths, or URLs containing bearer credentials.
135
143
 
136
- ## Free activation flow
144
+ ## Anonymous free-preview flow
137
145
 
138
- 1. `agent-memory plugin install` starts an HTTP server bound to `127.0.0.1` on an ephemeral port.
139
- 2. The CLI prints and opens a nonce-bearing local URL. The page accepts one email address with bounded input, an exact Host and nonce path, same-origin browser request validation, restrictive response headers, and a five-minute deadline.
140
- 3. Submission returns a completion page but does not create a local credential yet.
141
- 4. The waiting CLI sends the email plus core, installed-bundle, platform, architecture, release-channel, and consent-version fields to the private control plane. Its activation database stores none of the user's memory, session content, queries, repository paths, raw agent session identifiers, IP address, or user-agent string.
142
- 5. The service normalizes the email, stores only a hash of a random usage credential, and returns the credential, a free account-metered entitlement, and a short-lived object-bound artifact grant. Only then does the CLI atomically write a mode-0600 activation record.
146
+ 1. `agent-memory pro install` creates a random installation identifier locally when no activation record exists.
147
+ 2. The CLI sends that identifier plus core, installed-bundle, platform, architecture, and release-channel fields to the private control plane. It sends no email, memory, session content, query, repository path, raw agent session identifier, IP address, or user-agent string.
148
+ 3. The service stores the pseudonymous identifier and only the hash of a random compatibility credential, then returns a free-preview capability policy and short-lived object-bound artifact grant.
149
+ 4. The CLI validates the explicit free policy: local indexing and Memory Dashboard access, 10 device-local recalls per day, one device-local learning scan per day, and no free automatic background worker.
150
+ 5. Only then does the CLI atomically write a mode-0600 activation record.
143
151
  6. The CLI verifies the Ed25519-signed release plus package digest and limits, imports it for health checks, and atomically activates the receipt.
144
- 7. Each paid SessionStart hook reserves one opaque operation against the email's UTC-day allowance, commits after useful hook work, and releases on failure. Exhaustion skips paid hook work without affecting public-core context.
152
+ 7. Device-local quota operations reserve before work, commit after useful work, and release on abstention or failure. A zero-result recall does not consume allowance.
145
153
 
146
- Email ownership is not verified in this free flow. Authentication, payment, renewal, account management, and signed paid entitlements are not implemented yet.
154
+ Authentication, payment, renewal, account management, and signed paid entitlements are not implemented yet.
147
155
 
148
156
  ## Future authentication and purchase flow
149
157
 
@@ -163,12 +171,12 @@ An Enterprise administrator may pre-provision an organization entitlement or man
163
171
 
164
172
  The service exposes:
165
173
 
166
- - `POST /v1/plugin/access` for a free account-metered entitlement, a usage credential, and a short-lived artifact grant;
167
- - `POST /v1/plugin/sessions/reserve|commit|release` for atomic daily allowance enforcement;
174
+ - `POST /v1/plugin/access` for an anonymous free-preview policy, compatibility credential, and short-lived artifact grant;
175
+ - `POST /v1/plugin/sessions/reserve|commit|release` for migration compatibility with activation-v2 clients;
168
176
  - `GET /v1/plugin/releases` for an Ed25519-signed release selected from the private R2 catalog;
169
177
  - `GET|HEAD /v1/artifacts/download` for the exact content-addressed object authorized by the bearer grant.
170
178
 
171
- The access request contains the submitted email plus the bounded core, bundle, platform, architecture, release-channel, and consent-version fields described above. Session metering sends only a random operation ID and bearer credential; D1 associates those values with a normalized email and UTC-day counter. Application payloads contain no memory content, search query, session content, path, repository name, raw agent session identifier, qmd data, IP address, or user-agent string. The activation database stores neither IP addresses nor user-agent strings. Future authenticated service responsibilities include:
179
+ The access request contains a random installation identifier plus the bounded core, bundle, platform, architecture, and release-channel fields described above. Application payloads contain no email, memory content, search query, session content, path, repository name, raw agent session identifier, qmd data, IP address, or user-agent string. The activation database stores neither IP addresses nor user-agent strings. Future authenticated service responsibilities include:
172
180
 
173
181
  - create and poll a device authorization;
174
182
  - read the authenticated principal's effective entitlement;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "myagentmemory",
3
- "version": "0.4.15",
3
+ "version": "0.4.17",
4
4
  "description": "agentmemory (agent-memory) is persistent memory for coding agents (Claude Code, OpenAI Codex, Cursor, Agent) with qmd-powered semantic search across daily logs, long-term memory, and scratchpad",
5
5
  "main": "./dist/core.js",
6
6
  "types": "./dist/core.d.ts",
package/src/cli-spec.ts CHANGED
@@ -23,6 +23,10 @@ export const COMMANDS = [
23
23
  "install-hooks",
24
24
  "uninstall-hooks",
25
25
  "completion",
26
+ "pro",
27
+ "recall",
28
+ "learn",
29
+ "dashboard",
26
30
  "plugin",
27
31
  "version",
28
32
  "help",
@@ -48,9 +52,13 @@ export const COMMAND_DESCRIPTIONS: Record<(typeof COMMANDS)[number], string> = {
48
52
  "install-hooks": "install automatic SessionStart indexing and context hooks",
49
53
  "uninstall-hooks": "remove only SessionStart hooks managed by agent-memory",
50
54
  completion: "install or print Bash, Zsh, Fish, or PowerShell completion",
51
- plugin: "index, recall, learn from, and evaluate prior agent sessions",
55
+ pro: "install, inspect, or upgrade AgentMemory Pro",
56
+ recall: "recall decisions and context from prior coding sessions with Pro",
57
+ learn: "find repeated corrections worth remembering with Pro",
58
+ dashboard: "open the private local Memory Dashboard",
59
+ plugin: "discover, install, update, or remove optional official plugins",
52
60
  version: "print the installed agent-memory version",
53
- help: "show top-level, command, or nested plugin help",
61
+ help: "show this command overview",
54
62
  };
55
63
 
56
64
  export const PLUGIN_COMMAND_DESCRIPTIONS: Record<(typeof PLUGIN_COMMANDS)[number], string> = {
@@ -89,6 +97,10 @@ export const COMMAND_OPTIONS: Record<string, readonly string[]> = {
89
97
  "install-hooks": ["--yes", "--all", "--only"],
90
98
  "uninstall-hooks": ["--only"],
91
99
  completion: ["--stdout"],
100
+ pro: [],
101
+ recall: ["--scope", "--cwd", "--limit", "--context"],
102
+ learn: [],
103
+ dashboard: ["--no-browser"],
92
104
  version: [],
93
105
  help: [],
94
106
  };