@mysten-incubation/memwal-mcp 0.0.14-dev.1 → 0.0.14-dev.11
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 +238 -1
- package/dist/auth-required.d.ts +105 -0
- package/dist/auth-required.d.ts.map +1 -1
- package/dist/auth-required.js +48 -14
- package/dist/auth-required.js.map +1 -1
- package/dist/auth.d.ts +179 -18
- package/dist/auth.d.ts.map +1 -1
- package/dist/auth.js +458 -35
- package/dist/auth.js.map +1 -1
- package/dist/auto-save.d.ts +100 -0
- package/dist/auto-save.d.ts.map +1 -0
- package/dist/auto-save.js +290 -0
- package/dist/auto-save.js.map +1 -0
- package/dist/bridge.d.ts +10 -2
- package/dist/bridge.d.ts.map +1 -1
- package/dist/bridge.js +155 -25
- package/dist/bridge.js.map +1 -1
- package/dist/compatibility.d.ts.map +1 -1
- package/dist/compatibility.js +17 -2
- package/dist/compatibility.js.map +1 -1
- package/dist/consent.d.ts +36 -0
- package/dist/consent.d.ts.map +1 -0
- package/dist/consent.js +129 -0
- package/dist/consent.js.map +1 -0
- package/dist/crypto.d.ts.map +1 -1
- package/dist/crypto.js +13 -1
- package/dist/crypto.js.map +1 -1
- package/dist/health-probe.d.ts +35 -0
- package/dist/health-probe.d.ts.map +1 -0
- package/dist/health-probe.js +87 -0
- package/dist/health-probe.js.map +1 -0
- package/dist/index.d.ts +11 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +266 -5
- package/dist/index.js.map +1 -1
- package/dist/instructions.d.ts +17 -21
- package/dist/instructions.d.ts.map +1 -1
- package/dist/instructions.js +74 -12
- package/dist/instructions.js.map +1 -1
- package/dist/login.d.ts +15 -1
- package/dist/login.d.ts.map +1 -1
- package/dist/login.js +109 -9
- package/dist/login.js.map +1 -1
- package/dist/memory-policy.d.ts +38 -0
- package/dist/memory-policy.d.ts.map +1 -0
- package/dist/memory-policy.js +80 -0
- package/dist/memory-policy.js.map +1 -0
- package/dist/messages.d.ts +10 -3
- package/dist/messages.d.ts.map +1 -1
- package/dist/messages.js +16 -5
- package/dist/messages.js.map +1 -1
- package/dist/recovery.d.ts +1 -0
- package/dist/recovery.d.ts.map +1 -1
- package/dist/recovery.js +15 -13
- package/dist/recovery.js.map +1 -1
- package/package.json +1 -1
package/dist/compatibility.js
CHANGED
|
@@ -28,6 +28,21 @@ export function resolveConnectTimeoutMs() {
|
|
|
28
28
|
let compatibilityCache = null;
|
|
29
29
|
let compatibilityCacheUrl = null;
|
|
30
30
|
let compatibilityPromise = null;
|
|
31
|
+
async function readSuccessJson(res) {
|
|
32
|
+
const raw = await res.text();
|
|
33
|
+
if (raw.trim() === "") {
|
|
34
|
+
throw new Error(`MemWal: HTTP ${res.status} response had an empty body; expected JSON`);
|
|
35
|
+
}
|
|
36
|
+
try {
|
|
37
|
+
return JSON.parse(raw);
|
|
38
|
+
}
|
|
39
|
+
catch (err) {
|
|
40
|
+
if (err instanceof SyntaxError) {
|
|
41
|
+
throw new Error(`MemWal: HTTP ${res.status} response was not JSON`);
|
|
42
|
+
}
|
|
43
|
+
throw err;
|
|
44
|
+
}
|
|
45
|
+
}
|
|
31
46
|
/**
|
|
32
47
|
* @param signal Optional abort signal bounding the whole check. The caller
|
|
33
48
|
* passes ONE signal shared with the subsequent SSE connect so a single
|
|
@@ -57,7 +72,7 @@ async function fetchAndValidate(relayerUrl, signal) {
|
|
|
57
72
|
});
|
|
58
73
|
let metadata;
|
|
59
74
|
if (versionResp.ok) {
|
|
60
|
-
metadata =
|
|
75
|
+
metadata = await readSuccessJson(versionResp);
|
|
61
76
|
}
|
|
62
77
|
else if (versionResp.status === 404 || versionResp.status === 405) {
|
|
63
78
|
const healthResp = await fetch(`${base}/health`, {
|
|
@@ -68,7 +83,7 @@ async function fetchAndValidate(relayerUrl, signal) {
|
|
|
68
83
|
throw new Error(`Walrus Memory MCP compatibility check failed: GET /version returned ` +
|
|
69
84
|
`${versionResp.status}, and GET /health returned ${healthResp.status}`);
|
|
70
85
|
}
|
|
71
|
-
metadata =
|
|
86
|
+
metadata = await readSuccessJson(healthResp);
|
|
72
87
|
}
|
|
73
88
|
else {
|
|
74
89
|
throw new Error(`Walrus Memory MCP compatibility check failed: GET /version returned ${versionResp.status}`);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"compatibility.js","sourceRoot":"","sources":["../src/compatibility.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,MAAM,gCAAgC,GAAG,OAAO,CAAC;AACxD,MAAM,CAAC,MAAM,2BAA2B,GAAG,CAAC,CAAC;AAE7C;;;;;;;sCAOsC;AACtC,MAAM,0BAA0B,GAAG,MAAM,CAAC;AAE1C;;;;;;GAMG;AACH,MAAM,UAAU,uBAAuB;IACnC,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC,6BAA6B,CAAC;IACtD,IAAI,CAAC,GAAG;QAAE,OAAO,0BAA0B,CAAC;IAC5C,MAAM,CAAC,GAAG,MAAM,CAAC,GAAG,CAAC,CAAC;IACtB,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC;QAAE,OAAO,0BAA0B,CAAC;IACrE,OAAO,CAAC,CAAC;AACb,CAAC;AAUD,IAAI,kBAAkB,GAAkC,IAAI,CAAC;AAC7D,IAAI,qBAAqB,GAAkB,IAAI,CAAC;AAChD,IAAI,oBAAoB,GAAyB,IAAI,CAAC;AAEtD;;;;;GAKG;AACH,MAAM,CAAC,KAAK,UAAU,uBAAuB,CACzC,UAAkB,EAClB,MAAoB;IAEpB,MAAM,IAAI,GAAG,UAAU,CAAC,OAAO,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC;IAC5C,IAAI,kBAAkB,IAAI,qBAAqB,KAAK,IAAI;QAAE,OAAO;IACjE,IAAI,oBAAoB;QAAE,OAAO,oBAAoB,CAAC;IAEtD,oBAAoB,GAAG,gBAAgB,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC,OAAO,CAAC,GAAG,EAAE;QAC/D,oBAAoB,GAAG,IAAI,CAAC;IAChC,CAAC,CAAC,CAAC;IACH,OAAO,oBAAoB,CAAC;AAChC,CAAC;AAED,KAAK,UAAU,gBAAgB,CAAC,UAAkB,EAAE,MAAoB;IACpE,MAAM,IAAI,GAAG,UAAU,CAAC;IACxB,6EAA6E;IAC7E,4EAA4E;IAC5E,4EAA4E;IAC5E,MAAM,KAAK,GAAG,MAAM,IAAI,WAAW,CAAC,OAAO,CAAC,uBAAuB,EAAE,CAAC,CAAC;IACvE,MAAM,WAAW,GAAG,MAAM,KAAK,CAAC,GAAG,IAAI,UAAU,EAAE;QAC/C,MAAM,EAAE,KAAK;QACb,MAAM,EAAE,KAAK;KAChB,CAAC,CAAC;IACH,IAAI,QAAgC,CAAC;IAErC,IAAI,WAAW,CAAC,EAAE,EAAE,CAAC;QACjB,QAAQ,GAAG,
|
|
1
|
+
{"version":3,"file":"compatibility.js","sourceRoot":"","sources":["../src/compatibility.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import type { Readable, Writable } from "node:stream";
|
|
2
|
+
/** The prompt body, everything above the input line. */
|
|
3
|
+
export declare const CONSENT_PROMPT: string;
|
|
4
|
+
/** The input line. Enter alone takes the recommended option. */
|
|
5
|
+
export declare const CONSENT_QUESTION = "Your choice [1/2]: ";
|
|
6
|
+
/** What to say when the answer is neither 1 nor 2. */
|
|
7
|
+
export declare const CONSENT_REPROMPT = "Please answer 1 or 2 (or press Enter for 1).";
|
|
8
|
+
/**
|
|
9
|
+
* Map one line of input to an answer.
|
|
10
|
+
*
|
|
11
|
+
* Empty (a bare Enter) accepts option 1. Anything that is not 1 or 2 returns
|
|
12
|
+
* `null`, which means re-ask — never "assume the recommended one", because a
|
|
13
|
+
* typo is not an answer to a question about permanent storage.
|
|
14
|
+
*/
|
|
15
|
+
export declare function interpretConsentAnswer(raw: string): boolean | null;
|
|
16
|
+
/**
|
|
17
|
+
* Ask the question on a terminal and resolve to the answer.
|
|
18
|
+
*
|
|
19
|
+
* Resolves `null` — meaning "no answer given" — if the input stream ends first
|
|
20
|
+
* (Ctrl-D, a closed pipe, a killed terminal). The caller leaves the state unset
|
|
21
|
+
* in that case and asks again next time rather than recording a choice the user
|
|
22
|
+
* never made.
|
|
23
|
+
*
|
|
24
|
+
* Streams are injected so this is testable without a pty; `main()` passes the
|
|
25
|
+
* real stdin and stderr. Output goes to stderr because stdout belongs to the
|
|
26
|
+
* MCP protocol on every other path in this package.
|
|
27
|
+
*/
|
|
28
|
+
export declare function askAutoSaveConsent(opts: {
|
|
29
|
+
input: Readable;
|
|
30
|
+
output: Writable;
|
|
31
|
+
/** Guard against an accidental headless call. Defaults to requiring a TTY. */
|
|
32
|
+
isTTY?: boolean;
|
|
33
|
+
}): Promise<boolean | null>;
|
|
34
|
+
/** What is printed once the answer is in. */
|
|
35
|
+
export declare function consentOutcomeNotice(enabled: boolean, path: string): string;
|
|
36
|
+
//# sourceMappingURL=consent.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"consent.d.ts","sourceRoot":"","sources":["../src/consent.ts"],"names":[],"mappings":"AA6BA,OAAO,KAAK,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAEtD,wDAAwD;AACxD,eAAO,MAAM,cAAc,QAyBf,CAAC;AAEb,gEAAgE;AAChE,eAAO,MAAM,gBAAgB,wBAAwB,CAAC;AAEtD,sDAAsD;AACtD,eAAO,MAAM,gBAAgB,iDACqB,CAAC;AAEnD;;;;;;GAMG;AACH,wBAAgB,sBAAsB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,GAAG,IAAI,CAMlE;AAED;;;;;;;;;;;GAWG;AACH,wBAAsB,kBAAkB,CAAC,IAAI,EAAE;IAC3C,KAAK,EAAE,QAAQ,CAAC;IAChB,MAAM,EAAE,QAAQ,CAAC;IACjB,8EAA8E;IAC9E,KAAK,CAAC,EAAE,OAAO,CAAC;CACnB,GAAG,OAAO,CAAC,OAAO,GAAG,IAAI,CAAC,CA4B1B;AAED,6CAA6C;AAC7C,wBAAgB,oBAAoB,CAAC,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,CAO3E"}
|
package/dist/consent.js
ADDED
|
@@ -0,0 +1,129 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The automatic-memory consent question (WALM-642).
|
|
3
|
+
*
|
|
4
|
+
* Asked at interactive login and NOWHERE else. Deliberately not an MCP tool,
|
|
5
|
+
* not a tool description, not an instruction, and not anything a model can
|
|
6
|
+
* reach: a model answering on the user's behalf is not consent, and an
|
|
7
|
+
* agent-shaped surface for this question would be exactly that. The only caller
|
|
8
|
+
* is `main()` in index.ts, behind `process.stdin.isTTY`.
|
|
9
|
+
*
|
|
10
|
+
* Login is the gate because MemWal is unusable without it, so every real user
|
|
11
|
+
* passes through it once, and it is already a moment that requires a terminal.
|
|
12
|
+
*
|
|
13
|
+
* On the wording — it is the substance of this change, not decoration:
|
|
14
|
+
*
|
|
15
|
+
* - It names the consequence ("writes it to your memory without asking each
|
|
16
|
+
* time"), not the feature. Someone should be able to picture what happens
|
|
17
|
+
* to them, in their own session, from reading it.
|
|
18
|
+
* - Permanence leads, because it is the fact that changes the answer. Walrus
|
|
19
|
+
* is immutable: you can stop saving new memories but you cannot take back
|
|
20
|
+
* one already saved. Burying that under "we value your privacy" would make
|
|
21
|
+
* this a cookie banner, which it is not.
|
|
22
|
+
* - The redaction claim is deliberately hedged. `redaction.ts` documents real
|
|
23
|
+
* residual gaps — an unlabelled hex secret, a bare BIP-39 word run — so
|
|
24
|
+
* "safety net, not a guarantee" is the accurate claim and must stay. Saying
|
|
25
|
+
* more would be selling a promise the code does not make.
|
|
26
|
+
* - Declining is free and is stated as a normal choice, not a warning. A "no"
|
|
27
|
+
* is recorded once and never asked again.
|
|
28
|
+
*/
|
|
29
|
+
import { createInterface } from "node:readline";
|
|
30
|
+
/** The prompt body, everything above the input line. */
|
|
31
|
+
export const CONSENT_PROMPT = [
|
|
32
|
+
"",
|
|
33
|
+
"MemWal can save things about you automatically.",
|
|
34
|
+
"",
|
|
35
|
+
"What that means: when you state a preference, a decision, or a setting in",
|
|
36
|
+
'chat — "I prefer pnpm", "we deploy from dev", "the relayer is at X" —',
|
|
37
|
+
"MemWal writes it to your memory without asking each time, so it is there",
|
|
38
|
+
"in your next session and in every other client you use.",
|
|
39
|
+
"",
|
|
40
|
+
"Before you choose:",
|
|
41
|
+
"",
|
|
42
|
+
" - Saved memories are permanent. They go to Walrus, which is immutable",
|
|
43
|
+
" storage. You can stop saving new ones at any time, but you cannot",
|
|
44
|
+
" delete one that is already saved.",
|
|
45
|
+
" - They are encrypted to your account. Only your delegate key reads them.",
|
|
46
|
+
" - MemWal strips obvious credentials — API keys, tokens, passwords,",
|
|
47
|
+
" private keys — before saving. Treat that as a safety net, not a",
|
|
48
|
+
" guarantee: do not paste secrets into a session with this on.",
|
|
49
|
+
"",
|
|
50
|
+
" [1] Save automatically recommended, this is what MemWal is for",
|
|
51
|
+
' [2] Only save when I ask nothing is saved unless you say "remember this"',
|
|
52
|
+
"",
|
|
53
|
+
"Change this any time with `memwal-mcp auto-save on|off`.",
|
|
54
|
+
"See what is stored with `memwal_recall`.",
|
|
55
|
+
"",
|
|
56
|
+
].join("\n");
|
|
57
|
+
/** The input line. Enter alone takes the recommended option. */
|
|
58
|
+
export const CONSENT_QUESTION = "Your choice [1/2]: ";
|
|
59
|
+
/** What to say when the answer is neither 1 nor 2. */
|
|
60
|
+
export const CONSENT_REPROMPT = "Please answer 1 or 2 (or press Enter for 1).";
|
|
61
|
+
/**
|
|
62
|
+
* Map one line of input to an answer.
|
|
63
|
+
*
|
|
64
|
+
* Empty (a bare Enter) accepts option 1. Anything that is not 1 or 2 returns
|
|
65
|
+
* `null`, which means re-ask — never "assume the recommended one", because a
|
|
66
|
+
* typo is not an answer to a question about permanent storage.
|
|
67
|
+
*/
|
|
68
|
+
export function interpretConsentAnswer(raw) {
|
|
69
|
+
const v = raw.trim().toLowerCase();
|
|
70
|
+
if (v === "")
|
|
71
|
+
return true;
|
|
72
|
+
if (v === "1")
|
|
73
|
+
return true;
|
|
74
|
+
if (v === "2")
|
|
75
|
+
return false;
|
|
76
|
+
return null;
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Ask the question on a terminal and resolve to the answer.
|
|
80
|
+
*
|
|
81
|
+
* Resolves `null` — meaning "no answer given" — if the input stream ends first
|
|
82
|
+
* (Ctrl-D, a closed pipe, a killed terminal). The caller leaves the state unset
|
|
83
|
+
* in that case and asks again next time rather than recording a choice the user
|
|
84
|
+
* never made.
|
|
85
|
+
*
|
|
86
|
+
* Streams are injected so this is testable without a pty; `main()` passes the
|
|
87
|
+
* real stdin and stderr. Output goes to stderr because stdout belongs to the
|
|
88
|
+
* MCP protocol on every other path in this package.
|
|
89
|
+
*/
|
|
90
|
+
export async function askAutoSaveConsent(opts) {
|
|
91
|
+
// A prompt with nobody in front of it is a hang, not a question. The
|
|
92
|
+
// caller already checks this; the second check is here because the cost of
|
|
93
|
+
// getting it wrong is an MCP server that never finishes starting.
|
|
94
|
+
if (opts.isTTY === false)
|
|
95
|
+
return null;
|
|
96
|
+
opts.output.write(`${CONSENT_PROMPT}\n`);
|
|
97
|
+
const rl = createInterface({ input: opts.input, terminal: false });
|
|
98
|
+
try {
|
|
99
|
+
opts.output.write(CONSENT_QUESTION);
|
|
100
|
+
// The interface's async iterator, rather than a promise per `line`
|
|
101
|
+
// event: attaching a fresh listener after each answer drops any line
|
|
102
|
+
// that arrived while nothing was listening, which deadlocks the re-ask
|
|
103
|
+
// path the moment input is buffered rather than typed.
|
|
104
|
+
for await (const line of rl) {
|
|
105
|
+
const answer = interpretConsentAnswer(line);
|
|
106
|
+
if (answer !== null)
|
|
107
|
+
return answer;
|
|
108
|
+
opts.output.write(`${CONSENT_REPROMPT}\n`);
|
|
109
|
+
opts.output.write(CONSENT_QUESTION);
|
|
110
|
+
}
|
|
111
|
+
// Exhausted without an answer: Ctrl-D, a closed pipe, a killed
|
|
112
|
+
// terminal. Not a choice, and not recorded as one.
|
|
113
|
+
opts.output.write("\n");
|
|
114
|
+
return null;
|
|
115
|
+
}
|
|
116
|
+
finally {
|
|
117
|
+
rl.close();
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
/** What is printed once the answer is in. */
|
|
121
|
+
export function consentOutcomeNotice(enabled, path) {
|
|
122
|
+
return enabled
|
|
123
|
+
? "Automatic memory is ON. MemWal will save durable facts as you state them. " +
|
|
124
|
+
`Turn it off any time with \`memwal-mcp auto-save off\`. (${path})`
|
|
125
|
+
: "Automatic memory is OFF. Nothing is saved unless you ask for it — " +
|
|
126
|
+
'"remember this" still works, and so does recall. ' +
|
|
127
|
+
`Turn it on any time with \`memwal-mcp auto-save on\`. (${path})`;
|
|
128
|
+
}
|
|
129
|
+
//# sourceMappingURL=consent.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"consent.js","sourceRoot":"","sources":["../src/consent.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,OAAO,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AAGhD,wDAAwD;AACxD,MAAM,CAAC,MAAM,cAAc,GAAG;IAC1B,EAAE;IACF,iDAAiD;IACjD,EAAE;IACF,2EAA2E;IAC3E,uEAAuE;IACvE,0EAA0E;IAC1E,yDAAyD;IACzD,EAAE;IACF,oBAAoB;IACpB,EAAE;IACF,yEAAyE;IACzE,uEAAuE;IACvE,uCAAuC;IACvC,4EAA4E;IAC5E,sEAAsE;IACtE,qEAAqE;IACrE,kEAAkE;IAClE,EAAE;IACF,uEAAuE;IACvE,+EAA+E;IAC/E,EAAE;IACF,0DAA0D;IAC1D,0CAA0C;IAC1C,EAAE;CACL,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AAEb,gEAAgE;AAChE,MAAM,CAAC,MAAM,gBAAgB,GAAG,qBAAqB,CAAC;AAEtD,sDAAsD;AACtD,MAAM,CAAC,MAAM,gBAAgB,GACzB,8CAA8C,CAAC;AAEnD;;;;;;GAMG;AACH,MAAM,UAAU,sBAAsB,CAAC,GAAW;IAC9C,MAAM,CAAC,GAAG,GAAG,CAAC,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC;IACnC,IAAI,CAAC,KAAK,EAAE;QAAE,OAAO,IAAI,CAAC;IAC1B,IAAI,CAAC,KAAK,GAAG;QAAE,OAAO,IAAI,CAAC;IAC3B,IAAI,CAAC,KAAK,GAAG;QAAE,OAAO,KAAK,CAAC;IAC5B,OAAO,IAAI,CAAC;AAChB,CAAC;AAED;;;;;;;;;;;GAWG;AACH,MAAM,CAAC,KAAK,UAAU,kBAAkB,CAAC,IAKxC;IACG,qEAAqE;IACrE,2EAA2E;IAC3E,kEAAkE;IAClE,IAAI,IAAI,CAAC,KAAK,KAAK,KAAK;QAAE,OAAO,IAAI,CAAC;IAEtC,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,cAAc,IAAI,CAAC,CAAC;IAEzC,MAAM,EAAE,GAAG,eAAe,CAAC,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,QAAQ,EAAE,KAAK,EAAE,CAAC,CAAC;IACnE,IAAI,CAAC;QACD,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,gBAAgB,CAAC,CAAC;QACpC,mEAAmE;QACnE,qEAAqE;QACrE,uEAAuE;QACvE,uDAAuD;QACvD,IAAI,KAAK,EAAE,MAAM,IAAI,IAAI,EAAE,EAAE,CAAC;YAC1B,MAAM,MAAM,GAAG,sBAAsB,CAAC,IAAI,CAAC,CAAC;YAC5C,IAAI,MAAM,KAAK,IAAI;gBAAE,OAAO,MAAM,CAAC;YACnC,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,gBAAgB,IAAI,CAAC,CAAC;YAC3C,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,gBAAgB,CAAC,CAAC;QACxC,CAAC;QACD,+DAA+D;QAC/D,mDAAmD;QACnD,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;QACxB,OAAO,IAAI,CAAC;IAChB,CAAC;YAAS,CAAC;QACP,EAAE,CAAC,KAAK,EAAE,CAAC;IACf,CAAC;AACL,CAAC;AAED,6CAA6C;AAC7C,MAAM,UAAU,oBAAoB,CAAC,OAAgB,EAAE,IAAY;IAC/D,OAAO,OAAO;QACV,CAAC,CAAC,4EAA4E;YACxE,4DAA4D,IAAI,GAAG;QACzE,CAAC,CAAC,oEAAoE;YAChE,mDAAmD;YACnD,0DAA0D,IAAI,GAAG,CAAC;AAChF,CAAC"}
|
package/dist/crypto.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"crypto.d.ts","sourceRoot":"","sources":["../src/crypto.ts"],"names":[],"mappings":"AAMA,iBAAS,GAAG,CAAC,KAAK,EAAE,UAAU,GAAG,MAAM,CAItC;AAED,iBAAS,OAAO,CAAC,CAAC,EAAE,MAAM,GAAG,UAAU,
|
|
1
|
+
{"version":3,"file":"crypto.d.ts","sourceRoot":"","sources":["../src/crypto.ts"],"names":[],"mappings":"AAMA,iBAAS,GAAG,CAAC,KAAK,EAAE,UAAU,GAAG,MAAM,CAItC;AAED,iBAAS,OAAO,CAAC,CAAC,EAAE,MAAM,GAAG,UAAU,CAqBtC;AAED,MAAM,WAAW,OAAO;IACpB,aAAa,EAAE,MAAM,CAAC;IACtB,YAAY,EAAE,MAAM,CAAC;IACrB,UAAU,EAAE,MAAM,CAAC;CACtB;AAED,mEAAmE;AACnE,wBAAsB,eAAe,IAAI,OAAO,CAAC,OAAO,CAAC,CAQxD;AAED;;;GAGG;AACH,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,UAAU,GAAG,MAAM,CAM3D;AAED;;;;;;;GAOG;AACH,wBAAsB,WAAW,CAAC,aAAa,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAGzF;AAED,OAAO,EAAE,GAAG,IAAI,UAAU,EAAE,OAAO,IAAI,UAAU,EAAE,CAAC"}
|
package/dist/crypto.js
CHANGED
|
@@ -9,7 +9,19 @@ function hex(bytes) {
|
|
|
9
9
|
.join("");
|
|
10
10
|
}
|
|
11
11
|
function fromHex(s) {
|
|
12
|
-
|
|
12
|
+
if (typeof s !== "string") {
|
|
13
|
+
throw new TypeError("hexToBytes: expected string input");
|
|
14
|
+
}
|
|
15
|
+
const clean = s.startsWith("0x") || s.startsWith("0X") ? s.slice(2) : s;
|
|
16
|
+
if (clean.length === 0) {
|
|
17
|
+
throw new Error("hexToBytes: empty hex string");
|
|
18
|
+
}
|
|
19
|
+
if (clean.length % 2 !== 0) {
|
|
20
|
+
throw new Error(`hexToBytes: odd-length hex string (length=${clean.length}); hex must have an even number of digits`);
|
|
21
|
+
}
|
|
22
|
+
if (!/^[0-9a-fA-F]+$/.test(clean)) {
|
|
23
|
+
throw new Error("hexToBytes: input contains non-hex characters");
|
|
24
|
+
}
|
|
13
25
|
const out = new Uint8Array(clean.length / 2);
|
|
14
26
|
for (let i = 0; i < out.length; i++) {
|
|
15
27
|
out[i] = parseInt(clean.slice(i * 2, i * 2 + 2), 16);
|
package/dist/crypto.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"crypto.js","sourceRoot":"","sources":["../src/crypto.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,OAAO,EAAE,iBAAiB,EAAE,SAAS,EAAE,KAAK,EAAE,MAAM,gBAAgB,CAAC;AACrE,OAAO,EAAE,OAAO,EAAE,MAAM,yBAAyB,CAAC;AAElD,SAAS,GAAG,CAAC,KAAiB;IAC1B,OAAO,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC;SACnB,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC;SAC3C,IAAI,CAAC,EAAE,CAAC,CAAC;AAClB,CAAC;AAED,SAAS,OAAO,CAAC,CAAS;IACtB,MAAM,KAAK,GAAG,CAAC,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"crypto.js","sourceRoot":"","sources":["../src/crypto.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Ask the relayer's public `/health` why a call went unanswered: down,
|
|
3
|
+
* unreachable from this machine, configured wrong, or up with one call stuck.
|
|
4
|
+
* Each wants a different next step, so the bridge probes before it answers.
|
|
5
|
+
*/
|
|
6
|
+
export type HealthProbe = {
|
|
7
|
+
kind: "ok";
|
|
8
|
+
ms: number;
|
|
9
|
+
version?: string;
|
|
10
|
+
writesUnavailable?: boolean;
|
|
11
|
+
} | {
|
|
12
|
+
kind: "http";
|
|
13
|
+
ms: number;
|
|
14
|
+
status: number;
|
|
15
|
+
} | {
|
|
16
|
+
kind: "unreachable";
|
|
17
|
+
ms: number;
|
|
18
|
+
code: string;
|
|
19
|
+
} | {
|
|
20
|
+
kind: "timeout";
|
|
21
|
+
ms: number;
|
|
22
|
+
};
|
|
23
|
+
/** Override via `MEMWAL_MCP_HEALTH_PROBE_MS`, mostly for tests. */
|
|
24
|
+
export declare function resolveHealthProbeMs(): number;
|
|
25
|
+
/** `GET {baseUrl}/health`, bounded by `timeoutMs`. Never rejects: a probe
|
|
26
|
+
* that fails is itself the answer. */
|
|
27
|
+
export declare function probeRelayerHealth(baseUrl: string, timeoutMs: number): Promise<HealthProbe>;
|
|
28
|
+
/** `health` is the value for a `Relayer health:` line; `verdict` says what
|
|
29
|
+
* it means for the call; `reachable` is whether a plain retry can help. */
|
|
30
|
+
export declare function describeHealthProbe(probe: HealthProbe, relayerUrl: string): {
|
|
31
|
+
health: string;
|
|
32
|
+
verdict: string;
|
|
33
|
+
reachable: boolean;
|
|
34
|
+
};
|
|
35
|
+
//# sourceMappingURL=health-probe.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"health-probe.d.ts","sourceRoot":"","sources":["../src/health-probe.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,MAAM,MAAM,WAAW,GACjB;IAAE,IAAI,EAAE,IAAI,CAAC;IAAC,EAAE,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAC;IAAC,iBAAiB,CAAC,EAAE,OAAO,CAAA;CAAE,GACzE;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,EAAE,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,GAC5C;IAAE,IAAI,EAAE,aAAa,CAAC;IAAC,EAAE,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,GACjD;IAAE,IAAI,EAAE,SAAS,CAAC;IAAC,EAAE,EAAE,MAAM,CAAA;CAAE,CAAC;AAQtC,mEAAmE;AACnE,wBAAgB,oBAAoB,IAAI,MAAM,CAM7C;AAED;sCACsC;AACtC,wBAAsB,kBAAkB,CACpC,OAAO,EAAE,MAAM,EACf,SAAS,EAAE,MAAM,GAClB,OAAO,CAAC,WAAW,CAAC,CA6BtB;AAKD;2EAC2E;AAC3E,wBAAgB,mBAAmB,CAC/B,KAAK,EAAE,WAAW,EAClB,UAAU,EAAE,MAAM,GACnB;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,OAAO,CAAA;CAAE,CAiCzD"}
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Ask the relayer's public `/health` why a call went unanswered: down,
|
|
3
|
+
* unreachable from this machine, configured wrong, or up with one call stuck.
|
|
4
|
+
* Each wants a different next step, so the bridge probes before it answers.
|
|
5
|
+
*/
|
|
6
|
+
const DEFAULT_HEALTH_PROBE_MS = 3_000;
|
|
7
|
+
const MIN_HEALTH_PROBE_MS = 100;
|
|
8
|
+
/** A diagnosis nobody waits a minute for. Also keeps the value inside what
|
|
9
|
+
* `AbortSignal.timeout` accepts. */
|
|
10
|
+
const MAX_HEALTH_PROBE_MS = 60_000;
|
|
11
|
+
/** Override via `MEMWAL_MCP_HEALTH_PROBE_MS`, mostly for tests. */
|
|
12
|
+
export function resolveHealthProbeMs() {
|
|
13
|
+
const raw = process.env.MEMWAL_MCP_HEALTH_PROBE_MS;
|
|
14
|
+
if (!raw)
|
|
15
|
+
return DEFAULT_HEALTH_PROBE_MS;
|
|
16
|
+
const n = Math.floor(Number(raw));
|
|
17
|
+
if (!Number.isFinite(n) || n < MIN_HEALTH_PROBE_MS)
|
|
18
|
+
return DEFAULT_HEALTH_PROBE_MS;
|
|
19
|
+
return Math.min(n, MAX_HEALTH_PROBE_MS);
|
|
20
|
+
}
|
|
21
|
+
/** `GET {baseUrl}/health`, bounded by `timeoutMs`. Never rejects: a probe
|
|
22
|
+
* that fails is itself the answer. */
|
|
23
|
+
export async function probeRelayerHealth(baseUrl, timeoutMs) {
|
|
24
|
+
const started = Date.now();
|
|
25
|
+
let signal;
|
|
26
|
+
try {
|
|
27
|
+
// Inside the `try`: `AbortSignal.timeout` throws on a value it
|
|
28
|
+
// cannot take, and this function must not reject.
|
|
29
|
+
signal = AbortSignal.timeout(timeoutMs);
|
|
30
|
+
const res = await fetch(`${baseUrl.replace(/\/+$/, "")}/health`, { signal });
|
|
31
|
+
const ms = Date.now() - started;
|
|
32
|
+
if (!res.ok) {
|
|
33
|
+
await res.body?.cancel();
|
|
34
|
+
return { kind: "http", ms, status: res.status };
|
|
35
|
+
}
|
|
36
|
+
const body = (await res.json().catch(() => null));
|
|
37
|
+
const version = typeof body?.version === "string" ? body.version : undefined;
|
|
38
|
+
// `/health` answers 200 while writes are paused or Postgres is
|
|
39
|
+
// full; "ok" alone would hide the cause of a failed write.
|
|
40
|
+
const writesUnavailable = body?.write_ready === false || body?.writes === "paused";
|
|
41
|
+
return { kind: "ok", ms, version, ...(writesUnavailable ? { writesUnavailable } : {}) };
|
|
42
|
+
}
|
|
43
|
+
catch (err) {
|
|
44
|
+
const ms = Date.now() - started;
|
|
45
|
+
if (signal?.aborted)
|
|
46
|
+
return { kind: "timeout", ms };
|
|
47
|
+
const code = err?.cause?.code;
|
|
48
|
+
return { kind: "unreachable", ms, code: typeof code === "string" ? code : "unknown" };
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
/** DNS could not find the host: the one cause a user fixes on their side. */
|
|
52
|
+
const UNRESOLVED_CODES = new Set(["ENOTFOUND", "EAI_AGAIN"]);
|
|
53
|
+
/** `health` is the value for a `Relayer health:` line; `verdict` says what
|
|
54
|
+
* it means for the call; `reachable` is whether a plain retry can help. */
|
|
55
|
+
export function describeHealthProbe(probe, relayerUrl) {
|
|
56
|
+
switch (probe.kind) {
|
|
57
|
+
case "ok":
|
|
58
|
+
return {
|
|
59
|
+
health: `ok (${probe.ms}ms${probe.version ? `, v${probe.version}` : ""}` +
|
|
60
|
+
`${probe.writesUnavailable ? ", writes unavailable" : ""})`,
|
|
61
|
+
verdict: "The relayer is up, so this call stalled inside it or its reply was lost on the way back.",
|
|
62
|
+
reachable: true,
|
|
63
|
+
};
|
|
64
|
+
case "http":
|
|
65
|
+
return {
|
|
66
|
+
health: `HTTP ${probe.status} (${probe.ms}ms)`,
|
|
67
|
+
verdict: "The relayer answered but is not healthy.",
|
|
68
|
+
reachable: false,
|
|
69
|
+
};
|
|
70
|
+
case "timeout":
|
|
71
|
+
return {
|
|
72
|
+
health: `no answer within ${(probe.ms / 1000).toFixed(1)}s`,
|
|
73
|
+
verdict: `The relayer at ${relayerUrl} is down, overloaded, or not reachable from this machine.`,
|
|
74
|
+
reachable: false,
|
|
75
|
+
};
|
|
76
|
+
case "unreachable":
|
|
77
|
+
return {
|
|
78
|
+
health: `unreachable (${probe.code})`,
|
|
79
|
+
verdict: UNRESOLVED_CODES.has(probe.code)
|
|
80
|
+
? `The relayer host in ${relayerUrl} could not be resolved. Check the relayer URL ` +
|
|
81
|
+
"(MEMWAL_SERVER_URL or --relayer) and this machine's network."
|
|
82
|
+
: `The relayer at ${relayerUrl} is down or not reachable from this machine.`,
|
|
83
|
+
reachable: false,
|
|
84
|
+
};
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
//# sourceMappingURL=health-probe.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"health-probe.js","sourceRoot":"","sources":["../src/health-probe.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
CHANGED
|
@@ -7,10 +7,17 @@ interface ParsedArgs {
|
|
|
7
7
|
help: boolean;
|
|
8
8
|
logout: boolean;
|
|
9
9
|
forceLogin: boolean;
|
|
10
|
+
/** Approve the project-local credentials found from the working directory
|
|
11
|
+
* (WALM-639). A repo file is inert until this has been run for it. */
|
|
12
|
+
approveProject: boolean;
|
|
13
|
+
/** Withdraw that approval again. */
|
|
14
|
+
revokeProject: boolean;
|
|
10
15
|
relayerUrl?: string;
|
|
11
16
|
webUrl?: string;
|
|
12
17
|
label?: string;
|
|
13
18
|
namespace?: string;
|
|
19
|
+
/** `auto-save on|off|status` — the automatic-memory opt-in (WALM-642). */
|
|
20
|
+
autoSave?: "on" | "off" | "status";
|
|
14
21
|
/** Args parseArgs did not recognise, in the order seen. For a flag
|
|
15
22
|
* written `--key=value`, only `--key` is recorded — see parseArgs. */
|
|
16
23
|
unknown: string[];
|
|
@@ -20,8 +27,10 @@ export declare function main(argv?: string[]): Promise<void>;
|
|
|
20
27
|
/** The `--help` body. Exported so tests can assert it stays in step with the
|
|
21
28
|
* flags parseArgs actually accepts. */
|
|
22
29
|
export declare function helpText(): string;
|
|
23
|
-
export { loadCreds, saveCreds, clearCreds, credsPath } from "./auth.js";
|
|
30
|
+
export { loadCreds, saveCreds, clearCreds, credsPath, resolveCreds, approveProjectCreds, revokeProjectCredsApproval, formatProjectCredsNotice, formatProjectCredsStorageWarning, } from "./auth.js";
|
|
31
|
+
export { isAutoSaveEnabled, isConsentPending, autoSaveStatus, setAutoSave, markConsentPending, publishHookState, settingsPath, hookStatePath, } from "./auto-save.js";
|
|
32
|
+
export { askAutoSaveConsent, interpretConsentAnswer, CONSENT_PROMPT } from "./consent.js";
|
|
24
33
|
export { loginFlow } from "./login.js";
|
|
25
34
|
export { runBridge } from "./bridge.js";
|
|
26
|
-
export type { MemWalCredentials } from "./auth.js";
|
|
35
|
+
export type { MemWalCredentials, CredsResolution, ProjectCredsDecision } from "./auth.js";
|
|
27
36
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAsCA;;;;GAIG;AACH,UAAU,UAAU;IAChB,IAAI,EAAE,OAAO,CAAC;IACd,MAAM,EAAE,OAAO,CAAC;IAChB,UAAU,EAAE,OAAO,CAAC;IACpB;0EACsE;IACtE,cAAc,EAAE,OAAO,CAAC;IACxB,oCAAoC;IACpC,aAAa,EAAE,OAAO,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,0EAA0E;IAC1E,QAAQ,CAAC,EAAE,IAAI,GAAG,KAAK,GAAG,QAAQ,CAAC;IACnC;2EACuE;IACvE,OAAO,EAAE,MAAM,EAAE,CAAC;CACrB;AAeD,wBAAgB,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,UAAU,CA8GpD;AAED,wBAAsB,IAAI,CAAC,IAAI,GAAE,MAAM,EAA0B,GAAG,OAAO,CAAC,IAAI,CAAC,CA0YhF;AAkCD;wCACwC;AACxC,wBAAgB,QAAQ,IAAI,MAAM,CAgIjC;AAGD,OAAO,EACH,SAAS,EACT,SAAS,EACT,UAAU,EACV,SAAS,EACT,YAAY,EACZ,mBAAmB,EACnB,0BAA0B,EAC1B,wBAAwB,EACxB,gCAAgC,GACnC,MAAM,WAAW,CAAC;AACnB,OAAO,EACH,iBAAiB,EACjB,gBAAgB,EAChB,cAAc,EACd,WAAW,EACX,kBAAkB,EAClB,gBAAgB,EAChB,YAAY,EACZ,aAAa,GAChB,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,kBAAkB,EAAE,sBAAsB,EAAE,cAAc,EAAE,MAAM,cAAc,CAAC;AAC1F,OAAO,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AACvC,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,YAAY,EAAE,iBAAiB,EAAE,eAAe,EAAE,oBAAoB,EAAE,MAAM,WAAW,CAAC"}
|