@rubytech/create-maxy-code 0.1.612 → 0.1.614
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/package.json +1 -1
- package/payload/platform/lib/agent-dispatch-rule/dist/index.d.ts +34 -0
- package/payload/platform/lib/agent-dispatch-rule/dist/index.d.ts.map +1 -1
- package/payload/platform/lib/agent-dispatch-rule/dist/index.js +39 -0
- package/payload/platform/lib/agent-dispatch-rule/dist/index.js.map +1 -1
- package/payload/platform/lib/agent-dispatch-rule/src/__tests__/carrier-verdict.test.ts +92 -0
- package/payload/platform/lib/agent-dispatch-rule/src/index.ts +59 -0
- package/payload/platform/plugins/admin/skills/platform-architecture/SKILL.md +67 -10
- package/payload/platform/plugins/admin/skills/whats-new/SKILL.md +11 -0
- package/payload/platform/plugins/docs/references/telegram-guide.md +66 -9
- package/payload/platform/plugins/scheduling/mcp/dist/index.js +2 -0
- package/payload/platform/plugins/scheduling/mcp/dist/index.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/agent-dispatch-carrier.test.d.ts +2 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/agent-dispatch-carrier.test.d.ts.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/agent-dispatch-carrier.test.js +72 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/agent-dispatch-carrier.test.js.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-delivery-reconcile.test.d.ts +2 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-delivery-reconcile.test.d.ts.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-delivery-reconcile.test.js +327 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-delivery-reconcile.test.js.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-delivery.test.d.ts +2 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-delivery.test.d.ts.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-delivery.test.js +130 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-delivery.test.js.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-run.test.js +27 -58
- package/payload/platform/plugins/scheduling/mcp/dist/lib/__tests__/routine-run.test.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/lib/agent-dispatch.d.ts +8 -3
- package/payload/platform/plugins/scheduling/mcp/dist/lib/agent-dispatch.d.ts.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/lib/agent-dispatch.js +37 -3
- package/payload/platform/plugins/scheduling/mcp/dist/lib/agent-dispatch.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/lib/routine-delivery.d.ts +67 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/routine-delivery.d.ts.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/routine-delivery.js +133 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/routine-delivery.js.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/lib/routine-run.d.ts +67 -12
- package/payload/platform/plugins/scheduling/mcp/dist/lib/routine-run.d.ts.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/lib/routine-run.js +226 -72
- package/payload/platform/plugins/scheduling/mcp/dist/lib/routine-run.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/__tests__/agent-turn-dispatch.test.js +66 -4
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/__tests__/agent-turn-dispatch.test.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/__tests__/reconcile-run-controls.test.d.ts +2 -0
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/__tests__/reconcile-run-controls.test.d.ts.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/__tests__/reconcile-run-controls.test.js +45 -0
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/__tests__/reconcile-run-controls.test.js.map +1 -0
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/agent-turn-dispatch.d.ts +3 -1
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/agent-turn-dispatch.d.ts.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/agent-turn-dispatch.js +32 -7
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/agent-turn-dispatch.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/check-due-events.js +12 -1
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/check-due-events.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/reconcile-bookings.js +15 -2
- package/payload/platform/plugins/scheduling/mcp/dist/scripts/reconcile-bookings.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-event.d.ts +14 -0
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-event.d.ts.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-event.js +4 -0
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-event.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-get.d.ts +3 -0
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-get.d.ts.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-get.js +2 -0
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-get.js.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-update.d.ts.map +1 -1
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-update.js +14 -0
- package/payload/platform/plugins/scheduling/mcp/dist/tools/schedule-update.js.map +1 -1
- package/payload/platform/plugins/telegram/mcp/dist/__tests__/card-row.test.d.ts +2 -0
- package/payload/platform/plugins/telegram/mcp/dist/__tests__/card-row.test.d.ts.map +1 -0
- package/payload/platform/plugins/telegram/mcp/dist/__tests__/card-row.test.js +237 -0
- package/payload/platform/plugins/telegram/mcp/dist/__tests__/card-row.test.js.map +1 -0
- package/payload/platform/plugins/telegram/mcp/dist/index.js +6 -4
- package/payload/platform/plugins/telegram/mcp/dist/index.js.map +1 -1
- package/payload/platform/plugins/telegram/mcp/dist/lib/card-row.d.ts +96 -0
- package/payload/platform/plugins/telegram/mcp/dist/lib/card-row.d.ts.map +1 -0
- package/payload/platform/plugins/telegram/mcp/dist/lib/card-row.js +156 -0
- package/payload/platform/plugins/telegram/mcp/dist/lib/card-row.js.map +1 -0
- package/payload/platform/plugins/telegram/mcp/dist/tools/card.d.ts.map +1 -1
- package/payload/platform/plugins/telegram/mcp/dist/tools/card.js +53 -0
- package/payload/platform/plugins/telegram/mcp/dist/tools/card.js.map +1 -1
- package/payload/platform/plugins/telegram/mcp/dist/tools/instruct.d.ts +7 -5
- package/payload/platform/plugins/telegram/mcp/dist/tools/instruct.d.ts.map +1 -1
- package/payload/platform/plugins/telegram/mcp/dist/tools/instruct.js +14 -12
- package/payload/platform/plugins/telegram/mcp/dist/tools/instruct.js.map +1 -1
- package/payload/server/public/operator.html +1 -1
- package/payload/server/server.js +804 -724
package/package.json
CHANGED
|
@@ -155,5 +155,39 @@ export declare function isDispatchable(fields: DispatchFields): boolean;
|
|
|
155
155
|
* (Task 2393), which re-exports it so its fire-site callers are unchanged.
|
|
156
156
|
*/
|
|
157
157
|
export declare function dispatchGapReason(fields: DispatchFields): string;
|
|
158
|
+
/**
|
|
159
|
+
* Task 2776 — why a named carrier bot may not carry a destination.
|
|
160
|
+
*
|
|
161
|
+
* Three reasons, kept apart because they call for different operator actions: a
|
|
162
|
+
* bot id that names nothing (`absent`), a bot that exists on another role
|
|
163
|
+
* (`not-admin`), and an admin bot that does not admit this chat (`not-listed`).
|
|
164
|
+
*
|
|
165
|
+
* `not-admin` is the measured case. A routine authored against one bot silently
|
|
166
|
+
* changed carrier when that bot's `role` changed elsewhere, and every report
|
|
167
|
+
* landed in that bot's conversation rather than the operator's, with no event
|
|
168
|
+
* and no refusal naming the switch.
|
|
169
|
+
*/
|
|
170
|
+
export type CarrierReason = "absent" | "not-admin" | "not-listed";
|
|
171
|
+
export type CarrierVerdict = {
|
|
172
|
+
ok: true;
|
|
173
|
+
} | {
|
|
174
|
+
ok: false;
|
|
175
|
+
reason: CarrierReason;
|
|
176
|
+
};
|
|
177
|
+
/**
|
|
178
|
+
* May `botId` carry `destination` for the account at `accountDir`?
|
|
179
|
+
*
|
|
180
|
+
* Reads the RAW `telegram.bots` array rather than `readChannelAdmins().byBot`,
|
|
181
|
+
* because that projection drops every entry whose role is not `admin` and so
|
|
182
|
+
* cannot tell a missing bot from a demoted one — the distinction the three
|
|
183
|
+
* reasons exist for. Fail-closed: unreadable or malformed config yields
|
|
184
|
+
* `absent`, matching the empty-list default `readChannelAdmins` already applies.
|
|
185
|
+
*
|
|
186
|
+
* The ONE authority for a named carrier. `validateAgentDispatch` calls it at
|
|
187
|
+
* write time and `schedule-inject` calls it at fire time, so the picker, the
|
|
188
|
+
* save and the dispatch cannot disagree — the guarantee Task 2368 states for
|
|
189
|
+
* the resolver path, extended to the named one.
|
|
190
|
+
*/
|
|
191
|
+
export declare function carrierVerdict(accountDir: string, botId: string, destination: string): CarrierVerdict;
|
|
158
192
|
export {};
|
|
159
193
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -9,6 +9,7 @@ exports.validateAgentDestination = validateAgentDestination;
|
|
|
9
9
|
exports.listDispatchDestinations = listDispatchDestinations;
|
|
10
10
|
exports.isDispatchable = isDispatchable;
|
|
11
11
|
exports.dispatchGapReason = dispatchGapReason;
|
|
12
|
+
exports.carrierVerdict = carrierVerdict;
|
|
12
13
|
/**
|
|
13
14
|
* The dispatch-destination rule, shared by the scheduling plugin and the admin
|
|
14
15
|
* UI so create-time, fire-time and dashboard-time cannot diverge on the rule or
|
|
@@ -301,4 +302,42 @@ function dispatchGapReason(fields) {
|
|
|
301
302
|
}
|
|
302
303
|
return "no-dispatch-configured";
|
|
303
304
|
}
|
|
305
|
+
/**
|
|
306
|
+
* May `botId` carry `destination` for the account at `accountDir`?
|
|
307
|
+
*
|
|
308
|
+
* Reads the RAW `telegram.bots` array rather than `readChannelAdmins().byBot`,
|
|
309
|
+
* because that projection drops every entry whose role is not `admin` and so
|
|
310
|
+
* cannot tell a missing bot from a demoted one — the distinction the three
|
|
311
|
+
* reasons exist for. Fail-closed: unreadable or malformed config yields
|
|
312
|
+
* `absent`, matching the empty-list default `readChannelAdmins` already applies.
|
|
313
|
+
*
|
|
314
|
+
* The ONE authority for a named carrier. `validateAgentDispatch` calls it at
|
|
315
|
+
* write time and `schedule-inject` calls it at fire time, so the picker, the
|
|
316
|
+
* save and the dispatch cannot disagree — the guarantee Task 2368 states for
|
|
317
|
+
* the resolver path, extended to the named one.
|
|
318
|
+
*/
|
|
319
|
+
function carrierVerdict(accountDir, botId, destination) {
|
|
320
|
+
let config = {};
|
|
321
|
+
try {
|
|
322
|
+
config = JSON.parse((0, node_fs_1.readFileSync)((0, node_path_1.resolve)(accountDir, "account.json"), "utf-8"));
|
|
323
|
+
}
|
|
324
|
+
catch {
|
|
325
|
+
return { ok: false, reason: "absent" };
|
|
326
|
+
}
|
|
327
|
+
const bots = Array.isArray(config.telegram?.bots) ? config.telegram.bots : [];
|
|
328
|
+
const entry = bots.find((raw) => raw && typeof raw === "object" && raw.id === botId);
|
|
329
|
+
if (!entry)
|
|
330
|
+
return { ok: false, reason: "absent" };
|
|
331
|
+
if (entry.role !== "admin")
|
|
332
|
+
return { ok: false, reason: "not-admin" };
|
|
333
|
+
const users = Array.isArray(entry.adminUsers)
|
|
334
|
+
? entry.adminUsers.filter((u) => typeof u === "number")
|
|
335
|
+
: [];
|
|
336
|
+
// The destination is a string everywhere on the dispatch path; the stored list
|
|
337
|
+
// is numeric. A non-numeric destination yields NaN, which is in no list, so it
|
|
338
|
+
// lands on not-listed rather than throwing.
|
|
339
|
+
return users.includes(Number(destination))
|
|
340
|
+
? { ok: true }
|
|
341
|
+
: { ok: false, reason: "not-listed" };
|
|
342
|
+
}
|
|
304
343
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;AA4CA,sCAOC;AAGD,kCAIC;AAuBD,8CA0EC;AASD,0EAWC;AAOD,gDAMC;AAsBD,4DAwBC;AAgCD,4DAmDC;AA4BD,wCAGC;AAgBD,8CAYC;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Task 2776 — the named-carrier rule.
|
|
3
|
+
*
|
|
4
|
+
* The three refusal reasons are kept apart because they call for different
|
|
5
|
+
* operator actions, and because `readChannelAdmins().byBot` cannot tell them
|
|
6
|
+
* apart: it drops every non-admin entry, so a demoted bot and a missing one
|
|
7
|
+
* look identical there. Demoted is the measured case.
|
|
8
|
+
*/
|
|
9
|
+
import { describe, it, expect, afterEach } from "vitest";
|
|
10
|
+
import { mkdtempSync, rmSync, writeFileSync } from "node:fs";
|
|
11
|
+
import { tmpdir } from "node:os";
|
|
12
|
+
import { join } from "node:path";
|
|
13
|
+
import { carrierVerdict } from "../index.js";
|
|
14
|
+
|
|
15
|
+
const dirs: string[] = [];
|
|
16
|
+
|
|
17
|
+
function accountDir(bots?: unknown): string {
|
|
18
|
+
const dir = mkdtempSync(join(tmpdir(), "carrier-"));
|
|
19
|
+
dirs.push(dir);
|
|
20
|
+
if (bots !== undefined) {
|
|
21
|
+
writeFileSync(join(dir, "account.json"), JSON.stringify({ telegram: { bots } }));
|
|
22
|
+
}
|
|
23
|
+
return dir;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
afterEach(() => {
|
|
27
|
+
while (dirs.length > 0) rmSync(dirs.pop() as string, { recursive: true, force: true });
|
|
28
|
+
});
|
|
29
|
+
|
|
30
|
+
const ADMIN = { id: "8711566959", role: "admin", adminUsers: [8992591236] };
|
|
31
|
+
const SPECIALIST = { id: "8804050655", role: "specialist", adminUsers: [1311221864] };
|
|
32
|
+
|
|
33
|
+
describe("carrierVerdict", () => {
|
|
34
|
+
it("accepts an admin bot that lists the destination", () => {
|
|
35
|
+
expect(carrierVerdict(accountDir([ADMIN]), "8711566959", "8992591236")).toEqual({ ok: true });
|
|
36
|
+
});
|
|
37
|
+
|
|
38
|
+
it("refuses reason=absent when no bot carries that id", () => {
|
|
39
|
+
expect(carrierVerdict(accountDir([ADMIN]), "1234567890", "8992591236")).toEqual({
|
|
40
|
+
ok: false,
|
|
41
|
+
reason: "absent",
|
|
42
|
+
});
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
it("refuses reason=not-admin when the bot exists on another role", () => {
|
|
46
|
+
// The measured case: a routine's carrier demoted to role:'specialist'
|
|
47
|
+
// elsewhere, which moved the carrier with no event and no refusal.
|
|
48
|
+
expect(carrierVerdict(accountDir([SPECIALIST]), "8804050655", "1311221864")).toEqual({
|
|
49
|
+
ok: false,
|
|
50
|
+
reason: "not-admin",
|
|
51
|
+
});
|
|
52
|
+
});
|
|
53
|
+
|
|
54
|
+
it("refuses reason=not-listed when an admin bot does not list the destination", () => {
|
|
55
|
+
expect(carrierVerdict(accountDir([ADMIN]), "8711566959", "1311221864")).toEqual({
|
|
56
|
+
ok: false,
|
|
57
|
+
reason: "not-listed",
|
|
58
|
+
});
|
|
59
|
+
});
|
|
60
|
+
|
|
61
|
+
it("refuses reason=absent on missing config (fail closed)", () => {
|
|
62
|
+
expect(carrierVerdict(accountDir(), "8711566959", "8992591236")).toEqual({
|
|
63
|
+
ok: false,
|
|
64
|
+
reason: "absent",
|
|
65
|
+
});
|
|
66
|
+
});
|
|
67
|
+
|
|
68
|
+
it("refuses reason=absent when the bots array is malformed", () => {
|
|
69
|
+
expect(carrierVerdict(accountDir("not-an-array"), "8711566959", "8992591236")).toEqual({
|
|
70
|
+
ok: false,
|
|
71
|
+
reason: "absent",
|
|
72
|
+
});
|
|
73
|
+
});
|
|
74
|
+
|
|
75
|
+
it("refuses reason=not-listed on a non-numeric destination", () => {
|
|
76
|
+
// Number("not-a-number") is NaN, which is in no list, so this lands on
|
|
77
|
+
// not-listed rather than throwing.
|
|
78
|
+
expect(carrierVerdict(accountDir([ADMIN]), "8711566959", "not-a-number")).toEqual({
|
|
79
|
+
ok: false,
|
|
80
|
+
reason: "not-listed",
|
|
81
|
+
});
|
|
82
|
+
});
|
|
83
|
+
|
|
84
|
+
it("picks the named bot out of several, not merely the first", () => {
|
|
85
|
+
const dir = accountDir([SPECIALIST, ADMIN]);
|
|
86
|
+
expect(carrierVerdict(dir, "8711566959", "8992591236")).toEqual({ ok: true });
|
|
87
|
+
expect(carrierVerdict(dir, "8804050655", "1311221864")).toEqual({
|
|
88
|
+
ok: false,
|
|
89
|
+
reason: "not-admin",
|
|
90
|
+
});
|
|
91
|
+
});
|
|
92
|
+
});
|
|
@@ -375,3 +375,62 @@ export function dispatchGapReason(fields: DispatchFields): string {
|
|
|
375
375
|
}
|
|
376
376
|
return "no-dispatch-configured";
|
|
377
377
|
}
|
|
378
|
+
|
|
379
|
+
/**
|
|
380
|
+
* Task 2776 — why a named carrier bot may not carry a destination.
|
|
381
|
+
*
|
|
382
|
+
* Three reasons, kept apart because they call for different operator actions: a
|
|
383
|
+
* bot id that names nothing (`absent`), a bot that exists on another role
|
|
384
|
+
* (`not-admin`), and an admin bot that does not admit this chat (`not-listed`).
|
|
385
|
+
*
|
|
386
|
+
* `not-admin` is the measured case. A routine authored against one bot silently
|
|
387
|
+
* changed carrier when that bot's `role` changed elsewhere, and every report
|
|
388
|
+
* landed in that bot's conversation rather than the operator's, with no event
|
|
389
|
+
* and no refusal naming the switch.
|
|
390
|
+
*/
|
|
391
|
+
export type CarrierReason = "absent" | "not-admin" | "not-listed";
|
|
392
|
+
export type CarrierVerdict = { ok: true } | { ok: false; reason: CarrierReason };
|
|
393
|
+
|
|
394
|
+
/**
|
|
395
|
+
* May `botId` carry `destination` for the account at `accountDir`?
|
|
396
|
+
*
|
|
397
|
+
* Reads the RAW `telegram.bots` array rather than `readChannelAdmins().byBot`,
|
|
398
|
+
* because that projection drops every entry whose role is not `admin` and so
|
|
399
|
+
* cannot tell a missing bot from a demoted one — the distinction the three
|
|
400
|
+
* reasons exist for. Fail-closed: unreadable or malformed config yields
|
|
401
|
+
* `absent`, matching the empty-list default `readChannelAdmins` already applies.
|
|
402
|
+
*
|
|
403
|
+
* The ONE authority for a named carrier. `validateAgentDispatch` calls it at
|
|
404
|
+
* write time and `schedule-inject` calls it at fire time, so the picker, the
|
|
405
|
+
* save and the dispatch cannot disagree — the guarantee Task 2368 states for
|
|
406
|
+
* the resolver path, extended to the named one.
|
|
407
|
+
*/
|
|
408
|
+
export function carrierVerdict(
|
|
409
|
+
accountDir: string,
|
|
410
|
+
botId: string,
|
|
411
|
+
destination: string,
|
|
412
|
+
): CarrierVerdict {
|
|
413
|
+
let config: { telegram?: { bots?: unknown } } = {};
|
|
414
|
+
try {
|
|
415
|
+
config = JSON.parse(readFileSync(resolve(accountDir, "account.json"), "utf-8")) as {
|
|
416
|
+
telegram?: { bots?: unknown };
|
|
417
|
+
};
|
|
418
|
+
} catch {
|
|
419
|
+
return { ok: false, reason: "absent" };
|
|
420
|
+
}
|
|
421
|
+
const bots = Array.isArray(config.telegram?.bots) ? config.telegram.bots : [];
|
|
422
|
+
const entry = bots.find(
|
|
423
|
+
(raw) => raw && typeof raw === "object" && (raw as { id?: unknown }).id === botId,
|
|
424
|
+
) as { role?: unknown; adminUsers?: unknown } | undefined;
|
|
425
|
+
if (!entry) return { ok: false, reason: "absent" };
|
|
426
|
+
if (entry.role !== "admin") return { ok: false, reason: "not-admin" };
|
|
427
|
+
const users = Array.isArray(entry.adminUsers)
|
|
428
|
+
? entry.adminUsers.filter((u): u is number => typeof u === "number")
|
|
429
|
+
: [];
|
|
430
|
+
// The destination is a string everywhere on the dispatch path; the stored list
|
|
431
|
+
// is numeric. A non-numeric destination yields NaN, which is in no list, so it
|
|
432
|
+
// lands on not-listed rather than throwing.
|
|
433
|
+
return users.includes(Number(destination))
|
|
434
|
+
? { ok: true }
|
|
435
|
+
: { ok: false, reason: "not-listed" };
|
|
436
|
+
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: platform-architecture
|
|
3
3
|
description: Use when grounding any documented-surface claim about what Maxy ships — plugins, skills, specialists, install/deploy flows, internals. This is the install catalogue, not evidence of what is enabled on the current account. For install state on this account, call `capabilities-here`; for documented surface, cite the `Source:` URL inline.
|
|
4
|
-
content-hash: sha256:
|
|
4
|
+
content-hash: sha256:c337b2771a5698c981624654e274f14e1a0eef067649c442204de785f84dfb03
|
|
5
5
|
brand: maxy-code
|
|
6
6
|
product-name: Maxy
|
|
7
7
|
---
|
|
@@ -2961,10 +2961,48 @@ Telegram profile name and will tell you plainly that it cannot put a name to the
|
|
|
2961
2961
|
Ask Maxy to save the Telegram ID against the contact. It is one change to one contact, and
|
|
2962
2962
|
it takes effect on the very next message.
|
|
2963
2963
|
|
|
2964
|
-
##
|
|
2964
|
+
## Which bot a routine sends from
|
|
2965
2965
|
|
|
2966
|
-
|
|
2967
|
-
|
|
2966
|
+
A routine that reports to you on Telegram has to go out through one of your bots. If the routine does
|
|
2967
|
+
not say which, Maxy picks whichever of your admin bots has your chat on its list at the
|
|
2968
|
+
moment the routine runs.
|
|
2969
|
+
|
|
2970
|
+
That is the right answer when you have one admin bot, which is the usual case. It goes wrong when you
|
|
2971
|
+
have several. If the bot that was carrying a routine is later changed to a specialist role, it stops
|
|
2972
|
+
counting as an admin bot, and the routine moves to a different one. Your reports keep being written
|
|
2973
|
+
and keep being delivered, but into a different conversation, and nothing announces the move.
|
|
2974
|
+
|
|
2975
|
+
So you can name the bot when you set the routine up. Tell Maxy which bot a routine should
|
|
2976
|
+
report through and it stays on that bot until you change the routine yourself. Ask "which bot does
|
|
2977
|
+
this routine report through?" at any time and it will tell you.
|
|
2978
|
+
|
|
2979
|
+
If you name a bot that Maxy cannot use, the routine does not run and you are told why,
|
|
2980
|
+
rather than being quietly moved to another bot. There are three reasons it can give: there is no such
|
|
2981
|
+
bot on your account, the bot exists but is no longer an admin bot, or the bot is an admin bot but
|
|
2982
|
+
your chat is not on its list. Each one points at a different fix.
|
|
2983
|
+
|
|
2984
|
+
## Knowing whether a routine actually reported
|
|
2985
|
+
|
|
2986
|
+
A routine that wakes up and a routine that sends you something are two different things, and
|
|
2987
|
+
Maxy now records them separately.
|
|
2988
|
+
|
|
2989
|
+
Waking up means the routine started and had its say. Whether it then sent you a message depends on
|
|
2990
|
+
what it found. A routine told to report only when something has changed is meant to stay quiet most
|
|
2991
|
+
of the time, and that silence is it working correctly.
|
|
2992
|
+
|
|
2993
|
+
Every message a routine sends you is recorded against the run that sent it, so a routine's history
|
|
2994
|
+
shows which runs reported and which did not. Ask "has this routine actually been messaging me?" and
|
|
2995
|
+
you will get the answer from that record rather than from the fact it has been running.
|
|
2996
|
+
|
|
2997
|
+
Maxy also checks this on its own, once a sweep, per account: how many routine wakes were
|
|
2998
|
+
accepted, how many produced a message, and which routines account for the difference. A routine that
|
|
2999
|
+
has been waking without ever reporting shows up there, named, without you having to notice the
|
|
3000
|
+
absence of messages first.
|
|
3001
|
+
|
|
3002
|
+
## Correcting what an agent told someone
|
|
3003
|
+
|
|
3004
|
+
When one of your bots tells someone something wrong, the fix is to instruct the agent that is talking
|
|
3005
|
+
to them, not to message that person yourself.
|
|
2968
3006
|
|
|
2969
3007
|
The reason is worth understanding, because the obvious approach quietly fails. Every conversation is
|
|
2970
3008
|
its own separate agent with its own memory. If you send the visitor a correction from your chat, they
|
|
@@ -2979,16 +3017,28 @@ own conversation. The agent writes the message itself, in the same voice it has
|
|
|
2979
3017
|
own memory now holds what it said, so it will not contradict it a moment later. The visitor sees a
|
|
2980
3018
|
normal message from the assistant they have been talking to, with no sign that anybody stepped in.
|
|
2981
3019
|
|
|
3020
|
+
The same is true of your specialist bots. If a specialist relays for a driver, a supplier or a
|
|
3021
|
+
colleague, and you card that person yourself, the specialist never learns you did. It answers their
|
|
3022
|
+
next message with no idea what they are replying to. That happened on a live conversation: a driver
|
|
3023
|
+
was sent a job by card, and when he came back twelve minutes later with his prices, the bot filed
|
|
3024
|
+
them as a passing remark and thanked him. Instruct it the same way, naming its bot and their chat,
|
|
3025
|
+
and it writes the message and remembers writing it.
|
|
3026
|
+
|
|
2982
3027
|
Write the intent rather than the exact sentence. This is an instruction to the agent, not text
|
|
2983
3028
|
delivered word for word, so "tell them we can do Thursday morning but not the afternoon" works better
|
|
2984
3029
|
than a script.
|
|
2985
3030
|
|
|
2986
|
-
|
|
2987
|
-
|
|
2988
|
-
- The bot is
|
|
2989
|
-
|
|
2990
|
-
- The
|
|
2991
|
-
|
|
3031
|
+
Six situations are refused, and each one says why rather than failing quietly:
|
|
3032
|
+
|
|
3033
|
+
- The bot is your own admin bot. That chat is your conversation with the agent, so instructing it
|
|
3034
|
+
there is the agent talking to itself.
|
|
3035
|
+
- The bot is bound to nothing. It answers nobody, so there is no agent to instruct.
|
|
3036
|
+
- The agent has been switched off, or a specialist's card has been renamed or deleted. Nothing is
|
|
3037
|
+
resurrected behind your back; turn it back on, or message the person yourself.
|
|
3038
|
+
- The bot is not allowed to talk to that person. Every bot has its own rule about who it answers, and
|
|
3039
|
+
a specialist answers a named list and nobody else. Starting a conversation the bot would refuse to
|
|
3040
|
+
continue leaves the person holding a message nobody can follow up, so it is refused instead. Most
|
|
3041
|
+
often this is a mistyped chat ID.
|
|
2992
3042
|
- The chat belongs to a connected business account. Those conversations are held separately and this
|
|
2993
3043
|
route cannot reach them.
|
|
2994
3044
|
- The chat is a broadcast channel the bot does not allow. A channel post reaches every subscriber and
|
|
@@ -3152,6 +3202,13 @@ your conversation view shows the button's own wording — "1 passenger", "One wa
|
|
|
3152
3202
|
chat appears in that chat's conversation, where the person who received it is,
|
|
3153
3203
|
and not in the conversation you asked for it from.
|
|
3154
3204
|
|
|
3205
|
+
Every card is recorded, whoever sent it. When Maxy hands a job to one
|
|
3206
|
+
of your specialists and that specialist cards someone, the card now shows up in
|
|
3207
|
+
that person's conversation exactly as one you asked for yourself would. Before,
|
|
3208
|
+
it did not: the card reached Telegram, the person read it, and your side held no
|
|
3209
|
+
record of it at all, so asking Maxy what it had sent got an answer
|
|
3210
|
+
drawn from Telegram rather than from your own history.
|
|
3211
|
+
|
|
3155
3212
|
The same is now true of most of what Telegram sends. Reply to one of
|
|
3156
3213
|
Maxy's messages and it sees the message you replied to, so "yes, do
|
|
3157
3214
|
that one" means something. React to a message with an emoji and it hears the
|
|
@@ -9,6 +9,17 @@ Invoked by the admin agent directly.
|
|
|
9
9
|
|
|
10
10
|
This is the platform's release timeline, newest first. Each entry shows the date it shipped and the version it shipped in, so you can tell the operator how current their install is. To compare, read the installed version from `capabilities-here` and match it against the versions below. Keep answers high level and in plain English; this is a summary, not a full commit log.
|
|
11
11
|
|
|
12
|
+
## 2026-08-16 (0.1.614)
|
|
13
|
+
|
|
14
|
+
- A routine that woke the assistant is no longer counted as having reached you. A wake is now recorded as a wake, and a run records the message that actually arrived in the chat, checked against what was really sent.
|
|
15
|
+
- A Telegram routine can name the bot that carries it. A named bot is used exactly as given, or refused with the reason.
|
|
16
|
+
- A card sent by a specialist is recorded in the conversation. It reached Telegram and was written down nowhere.
|
|
17
|
+
|
|
18
|
+
## 2026-08-16 (0.1.613)
|
|
19
|
+
|
|
20
|
+
- You can now tell the assistant what to say to someone one of your specialist bots is handling, the same way you already could for a public bot. Until now that was refused, so the only way through was to message the person yourself, and the specialist never learned you had. It would answer their next message with no idea what they were replying to.
|
|
21
|
+
- A bot will no longer start a conversation with someone it is set up never to answer. A mistyped chat ID used to send one message and then go silent, because every reply came back to a bot that refused it.
|
|
22
|
+
|
|
12
23
|
## 2026-08-15 (0.1.612)
|
|
13
24
|
|
|
14
25
|
- A conversation opened from the dashboard could show as completely empty even though the agent had answered in it. The reader was discarding the agent's replies instead of drawing them, so the thread looked like nothing had ever been said. Those replies now appear.
|
|
@@ -138,10 +138,48 @@ Telegram profile name and will tell you plainly that it cannot put a name to the
|
|
|
138
138
|
Ask {{productName}} to save the Telegram ID against the contact. It is one change to one contact, and
|
|
139
139
|
it takes effect on the very next message.
|
|
140
140
|
|
|
141
|
-
##
|
|
141
|
+
## Which bot a routine sends from
|
|
142
142
|
|
|
143
|
-
|
|
144
|
-
|
|
143
|
+
A routine that reports to you on Telegram has to go out through one of your bots. If the routine does
|
|
144
|
+
not say which, {{productName}} picks whichever of your admin bots has your chat on its list at the
|
|
145
|
+
moment the routine runs.
|
|
146
|
+
|
|
147
|
+
That is the right answer when you have one admin bot, which is the usual case. It goes wrong when you
|
|
148
|
+
have several. If the bot that was carrying a routine is later changed to a specialist role, it stops
|
|
149
|
+
counting as an admin bot, and the routine moves to a different one. Your reports keep being written
|
|
150
|
+
and keep being delivered, but into a different conversation, and nothing announces the move.
|
|
151
|
+
|
|
152
|
+
So you can name the bot when you set the routine up. Tell {{productName}} which bot a routine should
|
|
153
|
+
report through and it stays on that bot until you change the routine yourself. Ask "which bot does
|
|
154
|
+
this routine report through?" at any time and it will tell you.
|
|
155
|
+
|
|
156
|
+
If you name a bot that {{productName}} cannot use, the routine does not run and you are told why,
|
|
157
|
+
rather than being quietly moved to another bot. There are three reasons it can give: there is no such
|
|
158
|
+
bot on your account, the bot exists but is no longer an admin bot, or the bot is an admin bot but
|
|
159
|
+
your chat is not on its list. Each one points at a different fix.
|
|
160
|
+
|
|
161
|
+
## Knowing whether a routine actually reported
|
|
162
|
+
|
|
163
|
+
A routine that wakes up and a routine that sends you something are two different things, and
|
|
164
|
+
{{productName}} now records them separately.
|
|
165
|
+
|
|
166
|
+
Waking up means the routine started and had its say. Whether it then sent you a message depends on
|
|
167
|
+
what it found. A routine told to report only when something has changed is meant to stay quiet most
|
|
168
|
+
of the time, and that silence is it working correctly.
|
|
169
|
+
|
|
170
|
+
Every message a routine sends you is recorded against the run that sent it, so a routine's history
|
|
171
|
+
shows which runs reported and which did not. Ask "has this routine actually been messaging me?" and
|
|
172
|
+
you will get the answer from that record rather than from the fact it has been running.
|
|
173
|
+
|
|
174
|
+
{{productName}} also checks this on its own, once a sweep, per account: how many routine wakes were
|
|
175
|
+
accepted, how many produced a message, and which routines account for the difference. A routine that
|
|
176
|
+
has been waking without ever reporting shows up there, named, without you having to notice the
|
|
177
|
+
absence of messages first.
|
|
178
|
+
|
|
179
|
+
## Correcting what an agent told someone
|
|
180
|
+
|
|
181
|
+
When one of your bots tells someone something wrong, the fix is to instruct the agent that is talking
|
|
182
|
+
to them, not to message that person yourself.
|
|
145
183
|
|
|
146
184
|
The reason is worth understanding, because the obvious approach quietly fails. Every conversation is
|
|
147
185
|
its own separate agent with its own memory. If you send the visitor a correction from your chat, they
|
|
@@ -156,16 +194,28 @@ own conversation. The agent writes the message itself, in the same voice it has
|
|
|
156
194
|
own memory now holds what it said, so it will not contradict it a moment later. The visitor sees a
|
|
157
195
|
normal message from the assistant they have been talking to, with no sign that anybody stepped in.
|
|
158
196
|
|
|
197
|
+
The same is true of your specialist bots. If a specialist relays for a driver, a supplier or a
|
|
198
|
+
colleague, and you card that person yourself, the specialist never learns you did. It answers their
|
|
199
|
+
next message with no idea what they are replying to. That happened on a live conversation: a driver
|
|
200
|
+
was sent a job by card, and when he came back twelve minutes later with his prices, the bot filed
|
|
201
|
+
them as a passing remark and thanked him. Instruct it the same way, naming its bot and their chat,
|
|
202
|
+
and it writes the message and remembers writing it.
|
|
203
|
+
|
|
159
204
|
Write the intent rather than the exact sentence. This is an instruction to the agent, not text
|
|
160
205
|
delivered word for word, so "tell them we can do Thursday morning but not the afternoon" works better
|
|
161
206
|
than a script.
|
|
162
207
|
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
- The bot is
|
|
166
|
-
|
|
167
|
-
- The
|
|
168
|
-
|
|
208
|
+
Six situations are refused, and each one says why rather than failing quietly:
|
|
209
|
+
|
|
210
|
+
- The bot is your own admin bot. That chat is your conversation with the agent, so instructing it
|
|
211
|
+
there is the agent talking to itself.
|
|
212
|
+
- The bot is bound to nothing. It answers nobody, so there is no agent to instruct.
|
|
213
|
+
- The agent has been switched off, or a specialist's card has been renamed or deleted. Nothing is
|
|
214
|
+
resurrected behind your back; turn it back on, or message the person yourself.
|
|
215
|
+
- The bot is not allowed to talk to that person. Every bot has its own rule about who it answers, and
|
|
216
|
+
a specialist answers a named list and nobody else. Starting a conversation the bot would refuse to
|
|
217
|
+
continue leaves the person holding a message nobody can follow up, so it is refused instead. Most
|
|
218
|
+
often this is a mistyped chat ID.
|
|
169
219
|
- The chat belongs to a connected business account. Those conversations are held separately and this
|
|
170
220
|
route cannot reach them.
|
|
171
221
|
- The chat is a broadcast channel the bot does not allow. A channel post reaches every subscriber and
|
|
@@ -329,6 +379,13 @@ your conversation view shows the button's own wording — "1 passenger", "One wa
|
|
|
329
379
|
chat appears in that chat's conversation, where the person who received it is,
|
|
330
380
|
and not in the conversation you asked for it from.
|
|
331
381
|
|
|
382
|
+
Every card is recorded, whoever sent it. When {{productName}} hands a job to one
|
|
383
|
+
of your specialists and that specialist cards someone, the card now shows up in
|
|
384
|
+
that person's conversation exactly as one you asked for yourself would. Before,
|
|
385
|
+
it did not: the card reached Telegram, the person read it, and your side held no
|
|
386
|
+
record of it at all, so asking {{productName}} what it had sent got an answer
|
|
387
|
+
drawn from Telegram rather than from your own history.
|
|
388
|
+
|
|
332
389
|
The same is now true of most of what Telegram sends. Reply to one of
|
|
333
390
|
{{productName}}'s messages and it sees the message you replied to, so "yes, do
|
|
334
391
|
that one" means something. React to a message with an emoji and it hears the
|
|
@@ -102,6 +102,7 @@ eagerTool(server, "schedule-event", "Create a scheduled event or appointment. A
|
|
|
102
102
|
channel: z.enum(["whatsapp", "telegram"]).describe("Native channel the agent turn is delivered over"),
|
|
103
103
|
destination: z.string().describe("E.164 phone (WhatsApp) or Telegram chat id — must already be a registered admin/account-manager on that channel"),
|
|
104
104
|
prompt: z.string().describe("The instruction the agent runs when the event fires"),
|
|
105
|
+
botId: z.string().optional().describe("Telegram only — the bot that carries this routine. Omit to let the fire-time resolver pick whichever admin bot lists the chat id, which is correct for a single-admin-bot account. Name one to pin the carrier, so the routine cannot silently change bot when another bot's role changes."),
|
|
105
106
|
}).optional().describe("Agent-bearing dispatch: when the event fires, spawns or resumes the admin channel session for `destination` and runs `prompt` with full admin tools, delivering the answer back over the channel. Mutually exclusive with `action`. Always records an event, never a meeting."),
|
|
106
107
|
gate: z.object(gateShape).optional().describe(GATE_DESCRIPTION),
|
|
107
108
|
gateWaived: z.string().optional().describe(GATE_WAIVED_DESCRIPTION),
|
|
@@ -351,6 +352,7 @@ eagerTool(server, "schedule-update", "Update an event's properties or append a n
|
|
|
351
352
|
channel: z.enum(["whatsapp", "telegram"]).describe("Native channel the agent turn is delivered over"),
|
|
352
353
|
destination: z.string().describe("E.164 phone (WhatsApp) or Telegram chat id — must already be a registered admin/account-manager on that channel"),
|
|
353
354
|
prompt: z.string().describe("The instruction the agent runs when the event fires"),
|
|
355
|
+
botId: z.string().optional().describe("Telegram only — the bot that carries this routine. Omit to let the fire-time resolver pick whichever admin bot lists the chat id, which is correct for a single-admin-bot account. Name one to pin the carrier, so the routine cannot silently change bot when another bot's role changes."),
|
|
354
356
|
}).nullable().optional().describe("Set/replace the agent-bearing dispatch, or pass null to clear it. Mutually exclusive with action."),
|
|
355
357
|
gate: z.object(gateShape).nullable().optional().describe(`${GATE_DESCRIPTION} Pass null to clear it.`),
|
|
356
358
|
}, async (params) => {
|