@canonmsg/agent-sdk 13.2.1 → 13.3.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.
- package/dist/chunks/{chunk-TJBG6NKF.js → chunk-B6AOBWNZ.js} +463 -275
- package/dist/chunks/{chunk-POBMFS2K.js → chunk-BQGXOAIW.js} +2 -2
- package/dist/chunks/{chunk-VIS5WXNH.js → chunk-CUPSYLBV.js} +2042 -2026
- package/dist/chunks/{chunk-BPSFHEAA.js → chunk-HFT75BNB.js} +1 -1
- package/dist/chunks/{chunk-2NVLVPSG.js → chunk-NIORQKUI.js} +1 -1
- package/dist/chunks/{chunk-HTLKCUQG.js → chunk-SS22I6HM.js} +291 -59
- package/dist/chunks/{mls-crypto-ZBEC26B5.js → mls-crypto-AW7TY744.js} +2 -2
- package/dist/cli.js +143 -26
- package/dist/index.js +6 -6
- package/dist/internal/agent-tools/communication-tool.d.ts +80 -0
- package/dist/internal/agent-tools/index.d.ts +1 -0
- package/dist/internal/backend-contracts/endpoint.d.ts +25 -0
- package/dist/internal/backend-contracts/mlsDevKeyPackages.d.ts +4 -0
- package/dist/internal/core/client.d.ts +0 -4
- package/dist/internal/core/endpoint-client.d.ts +8 -0
- package/dist/internal/core/index.d.ts +1 -1
- package/dist/internal/core/registration-profile.d.ts +4 -1
- package/dist/internal/core/types.d.ts +3 -1
- package/dist/internal/endpoint/engine.d.ts +32 -3
- package/dist/internal/endpoint/media.d.ts +2 -2
- package/dist/internal/endpoint/mls-dev-groups.d.ts +9 -1
- package/dist/media.js +4 -4
- package/dist/mls-wasm-host.js +3 -3
- package/dist/runner/mls.d.ts +12 -2
- package/dist/runner/runner.d.ts +5 -2
- package/package.json +1 -1
|
@@ -2,8 +2,8 @@ import {
|
|
|
2
2
|
createMlsDevCredentialVerifier,
|
|
3
3
|
mlsDevDeviceHttpConfiguration,
|
|
4
4
|
parseMlsDevClientConfiguration
|
|
5
|
-
} from "./chunk-
|
|
6
|
-
import "./chunk-
|
|
5
|
+
} from "./chunk-NIORQKUI.js";
|
|
6
|
+
import "./chunk-CUPSYLBV.js";
|
|
7
7
|
export {
|
|
8
8
|
createMlsDevCredentialVerifier,
|
|
9
9
|
mlsDevDeviceHttpConfiguration,
|
package/dist/cli.js
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
MLS_SETUP_ACTIONS,
|
|
4
|
+
RUNNER_CLIENT,
|
|
4
5
|
acpDriver,
|
|
5
6
|
awaitErrand,
|
|
6
7
|
checkAcp,
|
|
@@ -25,28 +26,30 @@ import {
|
|
|
25
26
|
runMlsDevSetup,
|
|
26
27
|
startRelayChannel,
|
|
27
28
|
writeRelayCredential
|
|
28
|
-
} from "./chunks/chunk-
|
|
29
|
+
} from "./chunks/chunk-B6AOBWNZ.js";
|
|
29
30
|
import {
|
|
30
31
|
assertPrivateHome,
|
|
31
32
|
runnerLockName
|
|
32
|
-
} from "./chunks/chunk-
|
|
33
|
+
} from "./chunks/chunk-BQGXOAIW.js";
|
|
33
34
|
import {
|
|
34
35
|
CanonApiError,
|
|
35
36
|
CanonClient,
|
|
36
37
|
acquireLock,
|
|
38
|
+
clearPendingRegistration,
|
|
39
|
+
ensureAgentProfile,
|
|
37
40
|
isProfileLocked,
|
|
41
|
+
loadPendingRegistrations,
|
|
38
42
|
loadProfiles,
|
|
39
|
-
readCliPackageVersion,
|
|
40
43
|
resolveCanonRuntimeConnection,
|
|
41
44
|
runCli,
|
|
42
45
|
verifyCanonRuntimeConnection
|
|
43
|
-
} from "./chunks/chunk-
|
|
44
|
-
import "./chunks/chunk-
|
|
45
|
-
import "./chunks/chunk-
|
|
46
|
+
} from "./chunks/chunk-SS22I6HM.js";
|
|
47
|
+
import "./chunks/chunk-HFT75BNB.js";
|
|
48
|
+
import "./chunks/chunk-NIORQKUI.js";
|
|
46
49
|
import {
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
} from "./chunks/chunk-
|
|
50
|
+
AGENT_HOME_ELSEWHERE,
|
|
51
|
+
__name
|
|
52
|
+
} from "./chunks/chunk-CUPSYLBV.js";
|
|
50
53
|
|
|
51
54
|
// src/cli.ts
|
|
52
55
|
import { realpathSync } from "node:fs";
|
|
@@ -54,8 +57,25 @@ import { homedir, tmpdir } from "node:os";
|
|
|
54
57
|
import { dirname, join, resolve } from "node:path";
|
|
55
58
|
import { pathToFileURL } from "node:url";
|
|
56
59
|
import { parseArgs } from "node:util";
|
|
57
|
-
var
|
|
58
|
-
|
|
60
|
+
var OWNER_DECLINED = "OWNER_DECLINED";
|
|
61
|
+
function exitCodeFor(error) {
|
|
62
|
+
const code = error?.code;
|
|
63
|
+
return code === AGENT_HOME_ELSEWHERE || code === OWNER_DECLINED ? 0 : 1;
|
|
64
|
+
}
|
|
65
|
+
__name(exitCodeFor, "exitCodeFor");
|
|
66
|
+
function stopThenExit(stop, code, exit = process.exit, boundMs = 15e3) {
|
|
67
|
+
let done = false;
|
|
68
|
+
const finish = /* @__PURE__ */ __name(() => {
|
|
69
|
+
if (!done) {
|
|
70
|
+
done = true;
|
|
71
|
+
clearTimeout(bound);
|
|
72
|
+
exit(code);
|
|
73
|
+
}
|
|
74
|
+
}, "finish");
|
|
75
|
+
const bound = setTimeout(finish, boundMs);
|
|
76
|
+
void Promise.resolve().then(stop).catch(() => void 0).finally(finish);
|
|
77
|
+
}
|
|
78
|
+
__name(stopThenExit, "stopThenExit");
|
|
59
79
|
function once(handler) {
|
|
60
80
|
let called = false;
|
|
61
81
|
return (...args) => {
|
|
@@ -69,6 +89,8 @@ __name(once, "once");
|
|
|
69
89
|
var HELP = `canon-agent: run a Canon agent on the unified runner
|
|
70
90
|
|
|
71
91
|
Usage:
|
|
92
|
+
canon-agent run --driver <driver> --name <name> --owner-phone <+E.164> [--description <text>]
|
|
93
|
+
[--environment <id>] ... (the first run: registers the agent, then runs)
|
|
72
94
|
canon-agent run --driver code --module <path> [--profile <name>] [--environment <id>]
|
|
73
95
|
canon-agent run --driver claude [--cwd <dir>] [--model <id>] [--permission-mode <mode>]
|
|
74
96
|
[--claude-path <path>] [--profile <name>] [--environment <id>]
|
|
@@ -99,6 +121,19 @@ command also takes --mls-dev-config <path>, an operator's own custody instead. W
|
|
|
99
121
|
of these, the agent refuses every room, and where Canon encrypts every new conversation
|
|
100
122
|
it does not start.
|
|
101
123
|
|
|
124
|
+
First run: with --name and --owner-phone, a run whose profile (--profile, default the
|
|
125
|
+
name) has no key asks the owner to approve the agent in Canon, waits up to 30 minutes,
|
|
126
|
+
saves the profile and runs. A run whose saved key Canon refuses asks the owner for a
|
|
127
|
+
new key for the same agent the same way; the agent keeps its conversations, devices and
|
|
128
|
+
connections. The request stays open while nobody answers: run the command again to keep
|
|
129
|
+
waiting. A declined request ends the run.
|
|
130
|
+
|
|
131
|
+
One home: an agent answers from one place at a time. A run on a new machine, or with an
|
|
132
|
+
empty $CANON_HOME, takes it over at start, and the run it replaced stops and exits 0, so
|
|
133
|
+
a supervisor that restarts only on failure leaves it stopped. That run does not take the
|
|
134
|
+
home back by itself; start it with --take-over to move the agent back there. While the
|
|
135
|
+
agent's owner has Canon's relay on for its MCP connection, no run starts (exit 0).
|
|
136
|
+
|
|
102
137
|
Waking and sleeping: code, claude, codex and acp also take [--wake-config <path> |
|
|
103
138
|
--wake-off] [--idle-timeout <duration>]. With --wake-config the agent registers, at
|
|
104
139
|
each start, a public HTTPS callback for up to 32 rooms; Canon POSTs it a signed,
|
|
@@ -191,6 +226,8 @@ Flags:
|
|
|
191
226
|
with a signed challenge first; the agent does not start if
|
|
192
227
|
that fails. Without the flag a registration is left as it is.
|
|
193
228
|
--wake-off Remove the agent's wake callback at start.
|
|
229
|
+
--take-over Move the agent's home back to this machine after a run
|
|
230
|
+
elsewhere took it over.
|
|
194
231
|
--idle-timeout <d> Stop and exit 0 after this long with nothing to do: whole
|
|
195
232
|
seconds, or 90s, 10m, 1h. Typing in a room does not reach the
|
|
196
233
|
agent: a host that also receives typing hints decides itself
|
|
@@ -221,6 +258,9 @@ Flags:
|
|
|
221
258
|
1 unless it was accepted (a note kept, a post sent, an errand's
|
|
222
259
|
turn ended and any report it sent to --origin accepted).
|
|
223
260
|
--profile <name> A profile in $CANON_HOME/agents.json (key and endpoints).
|
|
261
|
+
--name <name> run: the agent's name, to register it (with --owner-phone).
|
|
262
|
+
--owner-phone <phone> run: the owner's phone number in Canon, international format.
|
|
263
|
+
--description <text> run: what the agent does, shown to its owner (default: the name).
|
|
224
264
|
--environment <id> canon-prod-v1 or canon-dev-v1 (default: CANON_ENVIRONMENT_ID).
|
|
225
265
|
--help, -h Show this help.
|
|
226
266
|
--version, -V Show the package version.
|
|
@@ -310,10 +350,11 @@ async function main() {
|
|
|
310
350
|
if (trustedAgents.some((id) => !/^[\w.:-]{1,200}$/.test(id))) throw new UsageError("--trust-agent takes an agent id.");
|
|
311
351
|
const instructions = values.instructions !== void 0 ? await loadInstructions(resolve(values.instructions)) : void 0;
|
|
312
352
|
const wake = values["wake-off"] ? null : values["wake-config"] !== void 0 ? await loadWakeConfiguration(resolve(values["wake-config"])) : void 0;
|
|
353
|
+
const registered = await ensureRegistered(values, values.driver);
|
|
354
|
+
if (registered) values.profile = registered;
|
|
313
355
|
const { environmentId, home, profile, apiKey } = await settings(values);
|
|
314
356
|
const mls = await mlsDevice(values, environmentId, home);
|
|
315
|
-
const baseUrl =
|
|
316
|
-
const streamUrl = process.env.CANON_STREAM_URL || profile?.streamUrl;
|
|
357
|
+
const { apiBaseUrl: baseUrl, streamUrl } = connectionFor(environmentId, profile);
|
|
317
358
|
let driver;
|
|
318
359
|
if (values.driver === "claude") {
|
|
319
360
|
driver = claudeDriver({
|
|
@@ -366,8 +407,8 @@ async function main() {
|
|
|
366
407
|
...team,
|
|
367
408
|
...trustedAgents.length ? { trustedAgents } : {},
|
|
368
409
|
...values["allow-session-for-destructive"] ? { sessionApprovalForDestructive: true } : {},
|
|
369
|
-
...RUNNER_CLIENT ? { client: RUNNER_CLIENT } : {},
|
|
370
410
|
...wake !== void 0 ? { wake } : {},
|
|
411
|
+
...values["take-over"] ? { takeOver: true } : {},
|
|
371
412
|
// Idle: a clean stop and exit 0, so a supervisor that restarts only on failure leaves the agent stopped until it is woken.
|
|
372
413
|
...idleTimeoutMs !== void 0 ? { idleTimeoutMs, onIdle: once(() => {
|
|
373
414
|
console.error(`canon-agent: nothing to do for ${values["idle-timeout"]}; stopping.`);
|
|
@@ -378,7 +419,7 @@ async function main() {
|
|
|
378
419
|
}) } : {},
|
|
379
420
|
onFatal: once((error) => {
|
|
380
421
|
console.error(`canon-agent: ${error.message}`);
|
|
381
|
-
|
|
422
|
+
stopThenExit(() => runner.stop(), exitCodeFor(error));
|
|
382
423
|
})
|
|
383
424
|
});
|
|
384
425
|
stopOnSignals(() => runner.stop());
|
|
@@ -394,8 +435,7 @@ __name(main, "main");
|
|
|
394
435
|
async function runRelay(values, team) {
|
|
395
436
|
const { environmentId, home, profile } = await settings(values, { key: false });
|
|
396
437
|
const relay = await loadRelayConfiguration(values["relay-config"], { environmentId });
|
|
397
|
-
const baseUrl =
|
|
398
|
-
const streamUrl = process.env.CANON_STREAM_URL || profile?.streamUrl;
|
|
438
|
+
const { apiBaseUrl: baseUrl, streamUrl } = connectionFor(environmentId, profile);
|
|
399
439
|
let current;
|
|
400
440
|
let latest;
|
|
401
441
|
let switching = Promise.resolve();
|
|
@@ -446,10 +486,12 @@ async function runRelay(values, team) {
|
|
|
446
486
|
relay: true,
|
|
447
487
|
installationId: stored2.installationId,
|
|
448
488
|
...team,
|
|
449
|
-
...RUNNER_CLIENT ? { client: RUNNER_CLIENT } : {},
|
|
450
489
|
onFatal: once((error) => {
|
|
451
490
|
console.error(`canon-agent: ${error.message}`);
|
|
452
|
-
|
|
491
|
+
stopThenExit(async () => {
|
|
492
|
+
await channel.close();
|
|
493
|
+
await runner.stop();
|
|
494
|
+
}, 1);
|
|
453
495
|
})
|
|
454
496
|
});
|
|
455
497
|
try {
|
|
@@ -522,11 +564,85 @@ function parse() {
|
|
|
522
564
|
cancel: { type: "string" },
|
|
523
565
|
"wake-config": { type: "string" },
|
|
524
566
|
"wake-off": { type: "boolean" },
|
|
525
|
-
"idle-timeout": { type: "string" }
|
|
567
|
+
"idle-timeout": { type: "string" },
|
|
568
|
+
"take-over": { type: "boolean" },
|
|
569
|
+
name: { type: "string" },
|
|
570
|
+
"owner-phone": { type: "string" },
|
|
571
|
+
description: { type: "string" }
|
|
526
572
|
}
|
|
527
573
|
});
|
|
528
574
|
}
|
|
529
575
|
__name(parse, "parse");
|
|
576
|
+
var REGISTRATION_WAIT_MS = 30 * 6e4;
|
|
577
|
+
var REGISTRATION_CLIENT_TYPES = { claude: "claude-code", codex: "codex" };
|
|
578
|
+
async function ensureRegistered(values, driver) {
|
|
579
|
+
const name = values.name?.trim(), ownerPhone = values["owner-phone"]?.trim();
|
|
580
|
+
if (!name && !ownerPhone && values.description === void 0) return void 0;
|
|
581
|
+
if (!name || !ownerPhone) throw new UsageError("--name and --owner-phone go together (and --description with them).");
|
|
582
|
+
if (process.env.CANON_API_KEY) throw new UsageError("--name and --owner-phone keep the agent's key in a profile: unset CANON_API_KEY.");
|
|
583
|
+
const environmentId = values.environment || process.env.CANON_ENVIRONMENT_ID;
|
|
584
|
+
if (!environmentId) throw new Error("CANON_ENVIRONMENT_ID (or --environment) is required.");
|
|
585
|
+
const home = resolve(process.env.CANON_HOME || join(homedir(), ".canon"));
|
|
586
|
+
await assertPrivateHome(home);
|
|
587
|
+
const profile = values.profile || name;
|
|
588
|
+
const saved = loadProfiles(home)[profile];
|
|
589
|
+
if (saved && saved.environmentId !== environmentId) throw new Error(`Profile "${profile}" belongs to ${saved.environmentId}, not ${environmentId}.`);
|
|
590
|
+
const connection = connectionFor(environmentId, saved);
|
|
591
|
+
const agentName = saved?.agentName ?? name;
|
|
592
|
+
const register = /* @__PURE__ */ __name(async (reconnect) => {
|
|
593
|
+
const pending = loadPendingRegistrations()[profile];
|
|
594
|
+
const ask = reconnect || pending?.requestedAgentId ? `a new key for ${agentName}` : agentName;
|
|
595
|
+
const waiting = /* @__PURE__ */ __name(() => console.error(`canon-agent: ask the owner of ${ownerPhone} to approve ${ask} in Canon. Waiting up to 30 minutes; the request stays open until they answer, and running this command again keeps waiting.`), "waiting");
|
|
596
|
+
if (pending && !pending.credentialAgentId) waiting();
|
|
597
|
+
const asked = reconnect || !!pending || !saved;
|
|
598
|
+
const progress = await ensureAgentProfile({
|
|
599
|
+
profile,
|
|
600
|
+
reconnect,
|
|
601
|
+
waitMs: REGISTRATION_WAIT_MS,
|
|
602
|
+
onSubmitted: waiting,
|
|
603
|
+
connection,
|
|
604
|
+
input: {
|
|
605
|
+
name,
|
|
606
|
+
description: values.description?.trim() || name,
|
|
607
|
+
ownerPhone,
|
|
608
|
+
clientType: REGISTRATION_CLIENT_TYPES[driver] ?? "generic",
|
|
609
|
+
developerInfo: `canon-agent run --driver ${driver}`
|
|
610
|
+
}
|
|
611
|
+
});
|
|
612
|
+
switch (progress.status) {
|
|
613
|
+
case "approved":
|
|
614
|
+
if (asked) console.error(`canon-agent: ${progress.agentName} is approved; its key is saved in profile "${profile}".`);
|
|
615
|
+
return progress.apiKey;
|
|
616
|
+
case "pending":
|
|
617
|
+
throw new Error(`Nobody has answered the request for ${ask} yet. It stays open: run this command again to keep waiting.`);
|
|
618
|
+
case "rejected":
|
|
619
|
+
clearPendingRegistration(profile);
|
|
620
|
+
throw Object.assign(new Error(`The owner declined ${ask}. Nothing was saved; run this command again to ask again.`), { code: OWNER_DECLINED });
|
|
621
|
+
case "credential-expired":
|
|
622
|
+
clearPendingRegistration(profile);
|
|
623
|
+
throw new Error(`The owner approved ${ask}, but its key was not collected within 48 hours and Canon removed it. Run this command again to ask again.`);
|
|
624
|
+
case "credential-delivered":
|
|
625
|
+
clearPendingRegistration(profile);
|
|
626
|
+
throw new Error(`The key for ${ask} was already collected elsewhere, so this run cannot have it. Run this command again to ask again.`);
|
|
627
|
+
}
|
|
628
|
+
}, "register");
|
|
629
|
+
const apiKey = await register(false);
|
|
630
|
+
try {
|
|
631
|
+
await new CanonClient(apiKey, resolveCanonRuntimeConnection(connection).apiBaseUrl).getAgentMe();
|
|
632
|
+
return profile;
|
|
633
|
+
} catch (error) {
|
|
634
|
+
if (!(error instanceof CanonApiError) || error.status !== 401) throw error;
|
|
635
|
+
}
|
|
636
|
+
console.error(`canon-agent: Canon no longer accepts ${agentName}'s saved key.`);
|
|
637
|
+
await register(true);
|
|
638
|
+
return profile;
|
|
639
|
+
}
|
|
640
|
+
__name(ensureRegistered, "ensureRegistered");
|
|
641
|
+
function connectionFor(environmentId, profile) {
|
|
642
|
+
const apiBaseUrl = process.env.CANON_BASE_URL || profile?.baseUrl, streamUrl = process.env.CANON_STREAM_URL || profile?.streamUrl;
|
|
643
|
+
return { environmentId, ...apiBaseUrl ? { apiBaseUrl } : {}, ...streamUrl ? { streamUrl } : {} };
|
|
644
|
+
}
|
|
645
|
+
__name(connectionFor, "connectionFor");
|
|
530
646
|
async function settings(values, { key = true } = {}) {
|
|
531
647
|
const environmentId = values.environment || process.env.CANON_ENVIRONMENT_ID;
|
|
532
648
|
if (!environmentId) throw new Error("CANON_ENVIRONMENT_ID (or --environment) is required.");
|
|
@@ -564,11 +680,7 @@ async function mlsSetup(values) {
|
|
|
564
680
|
let client;
|
|
565
681
|
let lock;
|
|
566
682
|
try {
|
|
567
|
-
const connection = resolveCanonRuntimeConnection(
|
|
568
|
-
environmentId,
|
|
569
|
-
apiBaseUrl: process.env.CANON_BASE_URL || profile?.baseUrl,
|
|
570
|
-
streamUrl: process.env.CANON_STREAM_URL || profile?.streamUrl
|
|
571
|
-
});
|
|
683
|
+
const connection = resolveCanonRuntimeConnection(connectionFor(environmentId, profile));
|
|
572
684
|
await verifyCanonRuntimeConnection(connection);
|
|
573
685
|
client = new CanonClient(apiKey, connection.apiBaseUrl, {
|
|
574
686
|
environmentId,
|
|
@@ -660,5 +772,10 @@ __name(stopOnSignals, "stopOnSignals");
|
|
|
660
772
|
runCli(import.meta.url, main, (error) => {
|
|
661
773
|
console.error(`canon-agent: ${error instanceof Error ? error.message : String(error)}`);
|
|
662
774
|
if (error instanceof UsageError) console.error(HELP.split("\n\nFlags:")[0]);
|
|
663
|
-
process.exit(1);
|
|
775
|
+
process.exit(error instanceof UsageError ? 1 : exitCodeFor(error));
|
|
664
776
|
}, { name: "canon-agent", help: HELP });
|
|
777
|
+
export {
|
|
778
|
+
ensureRegistered,
|
|
779
|
+
exitCodeFor,
|
|
780
|
+
stopThenExit
|
|
781
|
+
};
|
package/dist/index.js
CHANGED
|
@@ -26,8 +26,8 @@ import {
|
|
|
26
26
|
runMlsDevSetup,
|
|
27
27
|
runtimeDescriptor,
|
|
28
28
|
startRelayChannel
|
|
29
|
-
} from "./chunks/chunk-
|
|
30
|
-
import "./chunks/chunk-
|
|
29
|
+
} from "./chunks/chunk-B6AOBWNZ.js";
|
|
30
|
+
import "./chunks/chunk-BQGXOAIW.js";
|
|
31
31
|
import {
|
|
32
32
|
CanonApiError,
|
|
33
33
|
DEFAULT_ANTHROPIC_REQUEST_HEADROOM_BYTES,
|
|
@@ -52,10 +52,10 @@ import {
|
|
|
52
52
|
toAnthropicImageBlock,
|
|
53
53
|
toAnthropicImageBlocksWithinBudget,
|
|
54
54
|
uploadMediaFile
|
|
55
|
-
} from "./chunks/chunk-
|
|
56
|
-
import "./chunks/chunk-
|
|
57
|
-
import "./chunks/chunk-
|
|
58
|
-
import "./chunks/chunk-
|
|
55
|
+
} from "./chunks/chunk-SS22I6HM.js";
|
|
56
|
+
import "./chunks/chunk-HFT75BNB.js";
|
|
57
|
+
import "./chunks/chunk-NIORQKUI.js";
|
|
58
|
+
import "./chunks/chunk-CUPSYLBV.js";
|
|
59
59
|
export {
|
|
60
60
|
CanonApiError,
|
|
61
61
|
ConnectorRelayError,
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import { type CanonClient, type CommunicateInput } from '../core/index.js';
|
|
2
|
+
export interface VerbToolDefinition {
|
|
3
|
+
name: string;
|
|
4
|
+
description: string;
|
|
5
|
+
inputSchema: Record<string, unknown>;
|
|
6
|
+
}
|
|
7
|
+
export interface VerbToolResult {
|
|
8
|
+
content: Array<{
|
|
9
|
+
type: 'text';
|
|
10
|
+
text: string;
|
|
11
|
+
}>;
|
|
12
|
+
isError?: boolean;
|
|
13
|
+
}
|
|
14
|
+
export declare const CANON_COMMUNICATE_TOOL_NAME = "communicate";
|
|
15
|
+
export declare const CANON_COMMUNICATE_DISCOVERY_MAX_RESULTS = 10;
|
|
16
|
+
/**
|
|
17
|
+
* What each action takes: the fields it needs, then those it may have. The legacy aliases (start_direct,
|
|
18
|
+
* create_group, manage_group_members) take their action's fields; the parser still accepts them, and no schema offers them.
|
|
19
|
+
*/
|
|
20
|
+
declare const ACTION_FIELDS: {
|
|
21
|
+
readonly list_conversations: {
|
|
22
|
+
readonly required: readonly [];
|
|
23
|
+
readonly optional: readonly ["limit"];
|
|
24
|
+
};
|
|
25
|
+
readonly discover_agents: {
|
|
26
|
+
readonly required: readonly [];
|
|
27
|
+
readonly optional: readonly ["query", "limit", "cursor"];
|
|
28
|
+
};
|
|
29
|
+
readonly message_existing: {
|
|
30
|
+
readonly required: readonly ["conversationId", "text"];
|
|
31
|
+
readonly optional: readonly ["messageId"];
|
|
32
|
+
};
|
|
33
|
+
readonly start_conversation: {
|
|
34
|
+
readonly required: readonly ["principalId", "text"];
|
|
35
|
+
readonly optional: readonly ["selection", "messageId"];
|
|
36
|
+
};
|
|
37
|
+
readonly create_conversation: {
|
|
38
|
+
readonly required: readonly ["memberIds"];
|
|
39
|
+
readonly optional: readonly ["name"];
|
|
40
|
+
};
|
|
41
|
+
readonly manage_participants: {
|
|
42
|
+
readonly required: readonly ["conversationId", "userId", "operation"];
|
|
43
|
+
readonly optional: readonly [];
|
|
44
|
+
};
|
|
45
|
+
readonly leave_conversation: {
|
|
46
|
+
readonly required: readonly ["conversationId"];
|
|
47
|
+
readonly optional: readonly [];
|
|
48
|
+
};
|
|
49
|
+
readonly forward_message: {
|
|
50
|
+
readonly required: readonly ["sourceConversationId", "targetConversationId", "messageId"];
|
|
51
|
+
readonly optional: readonly ["text"];
|
|
52
|
+
};
|
|
53
|
+
readonly share_contact: {
|
|
54
|
+
readonly required: readonly ["conversationId", "contactUserId"];
|
|
55
|
+
readonly optional: readonly ["text", "messageId"];
|
|
56
|
+
};
|
|
57
|
+
};
|
|
58
|
+
export type CanonCommunicateAction = keyof typeof ACTION_FIELDS;
|
|
59
|
+
/** The actions a binding offers, each with the fields it shows for it (an action's required fields always). */
|
|
60
|
+
export type CommunicateShape = Readonly<Partial<Record<CanonCommunicateAction, readonly string[]>>>;
|
|
61
|
+
/** Every action with every field: the complete communication surface. */
|
|
62
|
+
export declare const CANON_COMMUNICATE_SHAPE: CommunicateShape;
|
|
63
|
+
/**
|
|
64
|
+
* One flat object schema for `communicate`: `action` names the action, and every other field is optional and says which
|
|
65
|
+
* actions take it. Claude reads a tool's schema as one object, so a top-level `oneOf` showed it only its first
|
|
66
|
+
* alternative (the driver trial on Dev, 2026-11-09); the parser checks each combination instead.
|
|
67
|
+
*/
|
|
68
|
+
export declare function communicateInputSchema(shape: CommunicateShape, textMaxLength?: number | null): Record<string, unknown>;
|
|
69
|
+
/**
|
|
70
|
+
* The complete model-facing communication surface. It is exported separately
|
|
71
|
+
* from the in-conversation verb list so each runtime can opt into it.
|
|
72
|
+
*/
|
|
73
|
+
export declare function canonCommunicateToolDefinition(name?: string): VerbToolDefinition;
|
|
74
|
+
/**
|
|
75
|
+
* Runtime validation for bindings that dispatch directly. The schema is flat, so this is where a combination is checked:
|
|
76
|
+
* an action the binding does not offer, a field the action needs, or one it does not take, is refused by name.
|
|
77
|
+
*/
|
|
78
|
+
export declare function parseCommunicateToolInput(value: unknown, shape?: CommunicateShape): CommunicateInput;
|
|
79
|
+
export declare function executeCanonCommunicateTool(client: CanonClient, args: unknown, shape?: CommunicateShape): Promise<VerbToolResult>;
|
|
80
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { CANON_COMMUNICATE_DISCOVERY_MAX_RESULTS, CANON_COMMUNICATE_SHAPE, CANON_COMMUNICATE_TOOL_NAME, canonCommunicateToolDefinition, communicateInputSchema, executeCanonCommunicateTool, parseCommunicateToolInput, type CanonCommunicateAction, type CommunicateShape, type VerbToolDefinition, type VerbToolResult, } from './communication-tool.js';
|
|
@@ -118,3 +118,28 @@ export declare const ENDPOINT_ID_PATTERN: RegExp;
|
|
|
118
118
|
export declare const ENDPOINT_ACTION_PATTERN: RegExp;
|
|
119
119
|
export declare function isEndpointOperationRequest(value: unknown): value is EndpointOperationRequest;
|
|
120
120
|
export declare function isEndpointOperationReceipt(value: unknown): value is EndpointOperationReceipt;
|
|
121
|
+
/**
|
|
122
|
+
* An agent answers from one home at a time: Canon's relay for its MCP connection while the owner has the relay on,
|
|
123
|
+
* otherwise its runner, the installation that started most recently (`initialize_endpoint` moves it there). Everything
|
|
124
|
+
* the other home sends is refused with `AGENT_HOME_ELSEWHERE`, so no message gets two answers. It is read from the
|
|
125
|
+
* agent's own document alone (`users/{agentId}`), so every hot path can check it without another read.
|
|
126
|
+
*
|
|
127
|
+
* `since` (ms, Canon's clock): this home answers for work from here, for its work floor and in the refusal's text. Nothing
|
|
128
|
+
* Canon accepted before it is that home's work, since the home before may have answered it. For the relay, its approval.
|
|
129
|
+
* For a runner, the later of `installedAt` and the relay's turn-off, after which the runner it replaced is the home again
|
|
130
|
+
* by itself. Despite its name, `installedAt` holds where its installation answers for work from (its baseline's cutover):
|
|
131
|
+
* a first installation's approval, a later one's take-over. Older markers hold a first installation's first start, and
|
|
132
|
+
* are read as they are.
|
|
133
|
+
*/
|
|
134
|
+
export declare const AGENT_HOME_ELSEWHERE = "AGENT_HOME_ELSEWHERE";
|
|
135
|
+
export type AgentHome = {
|
|
136
|
+
kind: 'connector';
|
|
137
|
+
since?: number;
|
|
138
|
+
} | {
|
|
139
|
+
kind: 'runner';
|
|
140
|
+
installationId?: string;
|
|
141
|
+
since?: number;
|
|
142
|
+
};
|
|
143
|
+
export declare function readAgentHome(agentConfig: unknown): AgentHome;
|
|
144
|
+
/** The one refusal both homes give the other: what is true now, and what the owner or operator can do. */
|
|
145
|
+
export declare function agentHomeElsewhereMessage(agentName: string | undefined, home: AgentHome): string;
|
|
@@ -1,5 +1,9 @@
|
|
|
1
1
|
export declare const MLS_DEV_KEY_PACKAGES_MAX_BYTES = 32768;
|
|
2
2
|
export declare const MLS_DEV_KEY_PACKAGE_TLS_MAX_BYTES = 16384;
|
|
3
|
+
/** How long a claim holds its recipient's slot before another member's device may take it over (mls-rooms-by-default.md
|
|
4
|
+
* §2.4). On Dev from 2026-10-20 to 11-08, 113 Adds were accepted a median 2.4 s after their claim, 99% within 9.4 s, and
|
|
5
|
+
* the slowest in 61.5 s: two minutes is about twice the slowest, and a dead claimant holds a device off no longer. */
|
|
6
|
+
export declare const MLS_DEV_KEY_PACKAGE_CLAIM_LEASE_MS: number;
|
|
3
7
|
export interface MlsDevKeyPackagePublishRequest {
|
|
4
8
|
readonly version: 1;
|
|
5
9
|
readonly requestId: string;
|
|
@@ -8,10 +8,6 @@ export interface ResumableMediaUploadResult {
|
|
|
8
8
|
status?: 'processing' | 'ready' | 'failed';
|
|
9
9
|
attachment: MediaAttachment;
|
|
10
10
|
}
|
|
11
|
-
/**
|
|
12
|
-
* Agent-facing ergonomics over the shared endpoint engine. Authentication and
|
|
13
|
-
* operator registration remain outside the conversation protocol.
|
|
14
|
-
*/
|
|
15
11
|
export declare class CanonClient {
|
|
16
12
|
private baseUrl;
|
|
17
13
|
private apiKey;
|
|
@@ -30,6 +30,14 @@ export interface CanonClientEndpointOptions {
|
|
|
30
30
|
mediaDirectory?: string;
|
|
31
31
|
/** Operator inspection/import does not automatically publish queued operations. */
|
|
32
32
|
autoDrain?: boolean;
|
|
33
|
+
/**
|
|
34
|
+
* This client is the agent's runner, and its installation is the agent's home: a new installation takes the home at
|
|
35
|
+
* start; one that lost it to another refuses to start (`AGENT_HOME_ELSEWHERE`) unless `takeOver` moves it back, so two
|
|
36
|
+
* supervised machines never take it from each other in turn. Other clients (a script, a CLI step) never move the home.
|
|
37
|
+
*/
|
|
38
|
+
claimHome?: boolean;
|
|
39
|
+
/** With `claimHome`: move the home back to this installation after another one took it. */
|
|
40
|
+
takeOver?: boolean;
|
|
33
41
|
/** Replicated cloud hosts supply operator-owned durable byte storage. */
|
|
34
42
|
mediaBytes?: EndpointMediaBytes<string>;
|
|
35
43
|
/** Test seam for the client's out-of-protocol HTTP (identity, profile); production leaves it unset. */
|
|
@@ -55,5 +55,5 @@ export { handleCliMetadataRequest, isDirectExecution, readCliPackageVersion, run
|
|
|
55
55
|
export type { CliMetadata, RunCliMetadataOptions, } from './cli-metadata.js';
|
|
56
56
|
export { CANON_VERB_NAMES, CANON_VERB_NAMESPACE, CANON_VERBS_SCHEMA_ID, CANON_VERBS_SCHEMA_VERSION, CANON_VERB_WIRE_SCHEMA_ID, CANON_VERB_WIRE_SCHEMA_VERSION, CANON_CARD_SCHEMA_ID, VERB_LIMITS, VERB_RATE_LIMITS, VERB_WIRE_ENVELOPE_FIELDS, canonVerbToolName, findVerbByteLimitViolations, findVerbWireEnvelopeViolations, getVerbResultSchema, mergeVerbWireToIntent, normalizeVerbNativeMetadata, projectVerbIntentToWire, type CanonVerbName, type CanonVerbWireEnvelope, type CanonVerbWireRequest, type CanonVerbWireResponse, type CanonVerbJsonSchema, type SendToInput, type SendToResult, type VerbMessageOptions, type VerbNativeMetadata, type VerbWireAccepted, type VerbWireBody, } from '../backend-contracts/index.js';
|
|
57
57
|
export { DEFAULT_DISCOVER_AGENTS_LIMIT, MAX_DISCOVER_AGENTS_LIMIT, MAX_DISCOVER_AGENTS_QUERY_LENGTH, type CanonAgentDirectoryEntry, type DiscoverAgentsInput, type DiscoverAgentsResult, } from '../backend-contracts/index.js';
|
|
58
|
-
export { parseDirectConversationSelection, readCommunicationRule, type CommunicateInput, type CommunicateResult, type CommunicationRule, type DirectConversationSelection, type StartDirectInput, type StartDirectResult, } from '../backend-contracts/index.js';
|
|
58
|
+
export { MLS_DEV_TEXT_MAX_BYTES, parseDirectConversationSelection, readCommunicationRule, type CommunicateInput, type CommunicateResult, type CommunicationRule, type DirectConversationSelection, type StartDirectInput, type StartDirectResult, } from '../backend-contracts/index.js';
|
|
59
59
|
export { canonMediaDownloadUrl, sanitizeDownloadFileName, buildMediaContentDisposition, getStoredFileExtension } from '../backend-contracts/index.js';
|
|
@@ -3,7 +3,10 @@ export interface EnsureAgentProfileOptions extends Omit<ResumeRegistrationOption
|
|
|
3
3
|
/** The local profile store owns its stable localRegistrationId. */
|
|
4
4
|
input: Omit<ResumeRegistrationOptions['input'], 'localRegistrationId'>;
|
|
5
5
|
profile: string;
|
|
6
|
-
/**
|
|
6
|
+
/**
|
|
7
|
+
* Ask the owner for a new key for this profile's agent (its saved agent ID, or `input.requestedAgentId`), even if a
|
|
8
|
+
* usable local credential exists. Approval only replaces the key: the agent keeps its rooms, devices and connections.
|
|
9
|
+
*/
|
|
7
10
|
reconnect?: boolean;
|
|
8
11
|
}
|
|
9
12
|
/** Reuse an environment-bound local profile, or resume its owner-approved registration. */
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { AgentOrigin, AgentOriginDeclaration, ArtifactContext } from '../backend-contracts/index.js';
|
|
1
|
+
import type { AgentHome, AgentOrigin, AgentOriginDeclaration, ArtifactContext } from '../backend-contracts/index.js';
|
|
2
2
|
import type { CanonControlValue, CanonRuntimeStreamingMode, CanonRuntimeDetailTier, CanonRuntimeVisibility, CanonRuntimeCommandDescriptor } from '../backend-contracts/index.js';
|
|
3
3
|
export type { AgentOrigin, AgentOriginDeclaration, CanonControlValue, CanonRuntimeStreamingMode, CanonRuntimeDetailTier, CanonRuntimeVisibility, CanonRuntimeActionAvailability, CanonRuntimeActionPlacement, CanonRuntimeActionCategory, CanonRuntimePrimitiveId, CanonRuntimeCommandArgumentKind, CanonRuntimeCommandArgumentChoice, CanonRuntimeCommandArgumentDescriptor, CanonRuntimeActionDispatch, CanonRuntimeActionDescriptor, CanonRuntimeCommandDescriptor, } from '../backend-contracts/index.js';
|
|
4
4
|
import type { ExecutionEnvironmentMode } from './execution-environment-mode.js';
|
|
@@ -479,6 +479,8 @@ export interface AgentContext {
|
|
|
479
479
|
ownershipVersion: number;
|
|
480
480
|
/** Server-created new-principal marker; initialization still binds the installation atomically. */
|
|
481
481
|
endpointBootstrapEligible?: boolean;
|
|
482
|
+
/** Where the agent answers from: Canon's relay, or the runner installation that started last (absent from older Canon). */
|
|
483
|
+
home?: AgentHome;
|
|
482
484
|
canonContactId?: string;
|
|
483
485
|
displayName?: string;
|
|
484
486
|
avatarUrl?: string | null;
|
|
@@ -72,6 +72,11 @@ export interface EndpointOperation {
|
|
|
72
72
|
/** Local-only binding of a withheld start's text; retained after the opener is sent or its payload is erased. */
|
|
73
73
|
openerFingerprint?: string;
|
|
74
74
|
receipt?: EndpointOperationReceipt;
|
|
75
|
+
/** A refused encrypted send this device encrypted again: the operation that replaced it, which retries and waits
|
|
76
|
+
* follow (mls-dev-groups.ts, resendText). */
|
|
77
|
+
resentAs?: string;
|
|
78
|
+
/** Local successor made after Canon refused an encrypted send, with readers and sender admission rechecked. */
|
|
79
|
+
automaticResend?: boolean;
|
|
75
80
|
attempts: number;
|
|
76
81
|
attempted: boolean;
|
|
77
82
|
nextAttemptAt?: number;
|
|
@@ -148,10 +153,15 @@ export interface Endpoint {
|
|
|
148
153
|
submit(intent: EndpointIntent, options?: EndpointExecuteOptions): Promise<EndpointOperation>;
|
|
149
154
|
execute<T = unknown>(intent: EndpointIntent, options?: EndpointExecuteOptions): Promise<EndpointOperationReceipt<T>>;
|
|
150
155
|
executeResult<T = unknown>(intent: EndpointIntent, options?: EndpointExecuteOptions): Promise<T>;
|
|
151
|
-
/** reconcileOnly reads the server receipt; it never dispatches
|
|
156
|
+
/** reconcileOnly reads and records the server receipt; it never dispatches or encrypts again. An operation encrypted
|
|
157
|
+
* again (`resentAs`) answers with the one that replaced it. An ordinary retry of a send Canon refused one change behind
|
|
158
|
+
* encrypts it again, by the rule its first refusal had, when a reconcile only recorded the refusal. */
|
|
152
159
|
retry<T = unknown>(operationId: string, options?: {
|
|
153
160
|
reconcileOnly?: boolean;
|
|
154
161
|
}): Promise<EndpointOperationReceipt<T>>;
|
|
162
|
+
/** A person's Retry of an encrypted message Canon refused: encrypts it again, from this device's copy, for its room as
|
|
163
|
+
* it is now, under a new operation that replaces the refused one. Returns the operation to retry. */
|
|
164
|
+
resend(operationId: string): Promise<EndpointOperation>;
|
|
155
165
|
drain(options?: {
|
|
156
166
|
limit?: number;
|
|
157
167
|
}): Promise<void>;
|
|
@@ -192,8 +202,9 @@ export interface Endpoint {
|
|
|
192
202
|
cancelMessageGroup(id: string): Promise<void>;
|
|
193
203
|
/** Runtime-specific publication policy; closures are never serialized.
|
|
194
204
|
* Return false to defer, or throw a nonretryable EndpointError to retire an
|
|
195
|
-
* unsent operation. An attempted operation still needs its server receipt.
|
|
196
|
-
|
|
205
|
+
* unsent operation. An attempted operation still needs its server receipt.
|
|
206
|
+
* Automatic resends retain the policy; only an audience-specific check may use the revalidated resend context. */
|
|
207
|
+
registerDeliveryGuard(id: string, allow: EndpointDeliveryGuard): () => void;
|
|
197
208
|
/** Keep a start's opening line that Canon did not store, and send it once the room and the request allow (§2a.13). */
|
|
198
209
|
deferOpener(input: {
|
|
199
210
|
conversationId: string;
|
|
@@ -216,6 +227,21 @@ export interface Endpoint {
|
|
|
216
227
|
/** Immutable operator-reviewed or server-proven cutover for new rooms/admissions. */
|
|
217
228
|
configureRecoveryBaseline(config: EndpointRecoveryBaseline): Promise<void>;
|
|
218
229
|
getRecoveryBaseline(): Promise<EndpointRecoveryBaseline | undefined>;
|
|
230
|
+
/**
|
|
231
|
+
* Work here starts at `cutoverAt` (Canon's clock), where this installation's turn as its agent's home began: a
|
|
232
|
+
* take-over, or Canon's relay turned off. Every input Canon accepted before it is history, never work, whether it is
|
|
233
|
+
* already in the inbox or still to come off a room's feed, since the home before may have answered it. Only an input a
|
|
234
|
+
* journaled output answers keeps it. The floor only ever moves later.
|
|
235
|
+
*/
|
|
236
|
+
startWorkAt(cutoverAt: string): Promise<void>;
|
|
237
|
+
/**
|
|
238
|
+
* A runner moving its agent's home here, under a new `initialize_endpoint` operation each time, starts work from
|
|
239
|
+
* Canon's answer (`startWorkAt`). Only this call sends it. One that fails, or that a process left unanswered when it
|
|
240
|
+
* died, is never sent again (the latter is settled when the store next opens, before anything drains), so no later
|
|
241
|
+
* start makes a take-over without its operator. If Canon took the home all the same, the next start reads that from the
|
|
242
|
+
* agent's home and starts work from there.
|
|
243
|
+
*/
|
|
244
|
+
takeOverHome(): Promise<void>;
|
|
219
245
|
refreshRecovery(): Promise<void>;
|
|
220
246
|
planRecoveryMigration(baseline: EndpointRecoveryBaseline, conversationIds?: string[]): Promise<EndpointRecoveryMigration>;
|
|
221
247
|
importRecoveryMigration(manifest: EndpointRecoveryMigration, reviewedSha256: string): Promise<EndpointMigrationReceipt>;
|
|
@@ -266,5 +292,8 @@ export interface Endpoint {
|
|
|
266
292
|
logout(): Promise<void>;
|
|
267
293
|
close(): Promise<void>;
|
|
268
294
|
}
|
|
295
|
+
export type EndpointDeliveryGuard = (context: {
|
|
296
|
+
automaticResend: boolean;
|
|
297
|
+
}) => Promise<boolean>;
|
|
269
298
|
export declare function mergeConversationSnapshot<T extends EndpointConversation>(current: T | undefined, incoming: T): T;
|
|
270
299
|
export declare function createEndpoint(options: EndpointOptions): Endpoint;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { Endpoint } from './engine.js';
|
|
1
|
+
import type { Endpoint, EndpointDeliveryGuard } from './engine.js';
|
|
2
2
|
import { type EndpointStore } from './store.js';
|
|
3
3
|
export interface EndpointMediaDescriptor {
|
|
4
4
|
mimeType: string;
|
|
@@ -64,7 +64,7 @@ export interface EndpointMediaProgress {
|
|
|
64
64
|
export interface EndpointMediaSendOptions {
|
|
65
65
|
signal?: AbortSignal;
|
|
66
66
|
onProgress?: (progress: EndpointMediaProgress) => void;
|
|
67
|
-
beforePublish?:
|
|
67
|
+
beforePublish?: EndpointDeliveryGuard;
|
|
68
68
|
}
|
|
69
69
|
export interface EndpointMediaInput<Source> {
|
|
70
70
|
conversationId: string;
|
|
@@ -48,6 +48,8 @@ export interface MlsDevAdmissionHold {
|
|
|
48
48
|
readonly waitingPrincipalIds: readonly string[];
|
|
49
49
|
/** This device joined after the room's first message, so its history starts later (mls-rooms-by-default.md §2.7). */
|
|
50
50
|
readonly missedEarlier?: true;
|
|
51
|
+
/** The room's group exists and this device is not in it: only a device already there can add it (§2.4). */
|
|
52
|
+
readonly outside?: true;
|
|
51
53
|
}
|
|
52
54
|
export interface MlsDevCurrentAudience {
|
|
53
55
|
readonly version: 1;
|
|
@@ -166,6 +168,8 @@ export interface MlsDevGroupBridge {
|
|
|
166
168
|
/** Reads and applies the room's conversation snapshot from Canon, for openings of members admitted since. */
|
|
167
169
|
readRoom?(conversationId: string): Promise<unknown>;
|
|
168
170
|
}
|
|
171
|
+
/** How many times a refused send is encrypted again by itself before it shows as not sent. */
|
|
172
|
+
export declare const MLS_DEV_RESEND_MAX = 3;
|
|
169
173
|
/** Internal attachment: the engine supplies its existing queue, receipt reducer,
|
|
170
174
|
* event/recovery intake, store and lifetime. Native work never runs inside tx. */
|
|
171
175
|
export declare function createMlsDevGroups(options: MlsDevDeviceClientOptions, context: MlsDevDeviceClientContext, keyPackages: MlsDevKeyPackageClient | undefined, bridge: MlsDevGroupBridge): {
|
|
@@ -175,6 +179,8 @@ export declare function createMlsDevGroups(options: MlsDevDeviceClientOptions, c
|
|
|
175
179
|
* encrypted room (mls-payload-v3.md §4). Items and cards are not forwarded yet. */
|
|
176
180
|
forwardText(value: unknown, operationId: string, guardId?: string): Promise<EndpointOperation>;
|
|
177
181
|
sendText(value: unknown, operationId: string, guardId?: string): Promise<EndpointOperation>;
|
|
182
|
+
/** A person's Retry of a text or item Canon refused: encrypted again for the room as it is now (`resendText`). */
|
|
183
|
+
resendText(operation: EndpointOperation): Promise<EndpointOperation | undefined>;
|
|
178
184
|
/** `sendText` for a person's composer: in a held room the text is kept, not refused (undefined), until `sendHeldTexts`. */
|
|
179
185
|
holdText(value: unknown, operationId: string): Promise<EndpointOperation | undefined>;
|
|
180
186
|
sendHeldTexts(conversationId: string): Promise<{
|
|
@@ -196,6 +202,8 @@ export declare function createMlsDevGroups(options: MlsDevDeviceClientOptions, c
|
|
|
196
202
|
syncText(conversationId: string, options?: EndpointSyncOptions): Promise<EndpointSyncPage>;
|
|
197
203
|
isTextReady: (conversationId: string) => Promise<boolean>;
|
|
198
204
|
readAcceptedReceipt(operation: EndpointOperation): Promise<EndpointOperationReceipt | undefined>;
|
|
199
|
-
settleReceipt(operation: EndpointOperation, receipt: EndpointOperationReceipt
|
|
205
|
+
settleReceipt(operation: EndpointOperation, receipt: EndpointOperationReceipt, options?: {
|
|
206
|
+
reconcileOnly?: boolean;
|
|
207
|
+
}): Promise<boolean>;
|
|
200
208
|
};
|
|
201
209
|
export {};
|