dominds 1.15.4 → 1.15.5
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/apps/assigned-port.d.ts +3 -3
- package/dist/apps/resolution-file.d.ts +2 -2
- package/dist/apps/run-app-json.d.ts +3 -3
- package/dist/apps-host/client.d.ts +2 -2
- package/dist/apps-host/host.js +6 -7
- package/dist/apps-host/ipc-types.d.ts +2 -2
- package/dist/docs/app-constitution.md +1 -1
- package/dist/docs/app-constitution.zh.md +1 -1
- package/dist/docs/tellask-result-unification.md +280 -0
- package/dist/llm/kernel-driver/drive.js +52 -29
- package/dist/llm/kernel-driver/fbr.d.ts +1 -1
- package/dist/llm/kernel-driver/fbr.js +2 -1
- package/dist/mcp/supervisor.js +4 -6
- package/dist/runtime/tool-result-messages.d.ts +2 -1
- package/dist/runtime/tool-result-messages.js +13 -12
- package/dist/shared/utils/fbr.js +8 -12
- package/dist/shared/utils/inter-dialog-format.js +4 -6
- package/dist/tool.d.ts +9 -1
- package/dist/tool.js +20 -0
- package/dist/tools/apply-patch.js +2 -1
- package/dist/tools/ctrl.js +53 -50
- package/dist/tools/env.js +7 -6
- package/dist/tools/fs.js +64 -59
- package/dist/tools/mcp.js +6 -5
- package/dist/tools/mem.js +35 -34
- package/dist/tools/os.js +30 -29
- package/dist/tools/plan.js +12 -10
- package/dist/tools/ripgrep.js +17 -10
- package/dist/tools/team_mgmt.js +23 -22
- package/dist/tools/toolset-manual.js +12 -11
- package/dist/tools/txt.d.ts +2 -2
- package/dist/tools/txt.js +61 -77
- package/package.json +4 -4
- package/webapp/dist/assets/{_basePickBy-DsirmCgI.js → _basePickBy-QPiPxkcd.js} +3 -3
- package/webapp/dist/assets/_basePickBy-QPiPxkcd.js.map +1 -0
- package/webapp/dist/assets/{_baseUniq-tR6G8loB.js → _baseUniq-Dxi782ML.js} +2 -2
- package/webapp/dist/assets/_baseUniq-Dxi782ML.js.map +1 -0
- package/webapp/dist/assets/{arc-CzxpASkZ.js → arc-CmoWlJCk.js} +2 -2
- package/webapp/dist/assets/arc-CmoWlJCk.js.map +1 -0
- package/webapp/dist/assets/{architectureDiagram-2XIMDMQ5-BSH7H5oI.js → architectureDiagram-VXUJARFQ-Cj8eAVGw.js} +8 -26
- package/webapp/dist/assets/architectureDiagram-VXUJARFQ-Cj8eAVGw.js.map +1 -0
- package/webapp/dist/assets/{blockDiagram-WCTKOSBZ-DpLIr7yO.js → blockDiagram-VD42YOAC-DCSpBIH9.js} +170 -187
- package/webapp/dist/assets/blockDiagram-VD42YOAC-DCSpBIH9.js.map +1 -0
- package/webapp/dist/assets/{c4Diagram-IC4MRINW-WuYKgWfY.js → c4Diagram-YG6GDRKO-BLnTx0I5.js} +4 -4
- package/webapp/dist/assets/c4Diagram-YG6GDRKO-BLnTx0I5.js.map +1 -0
- package/webapp/dist/assets/{channel-B-v9dqLN.js → channel-CHTZ0PXJ.js} +2 -2
- package/webapp/dist/assets/channel-CHTZ0PXJ.js.map +1 -0
- package/webapp/dist/assets/{chunk-4BX2VUAB-MtFUfKZy.js → chunk-4BX2VUAB-D9vwOR-u.js} +2 -2
- package/webapp/dist/assets/chunk-4BX2VUAB-D9vwOR-u.js.map +1 -0
- package/webapp/dist/assets/{chunk-55IACEB6-rY9AJdzj.js → chunk-55IACEB6-Bls-7sze.js} +2 -2
- package/webapp/dist/assets/chunk-55IACEB6-Bls-7sze.js.map +1 -0
- package/webapp/dist/assets/{chunk-WL4C6EOR-DDCnEwft.js → chunk-B4BG7PRW-BXRfjHmI.js} +121 -171
- package/webapp/dist/assets/chunk-B4BG7PRW-BXRfjHmI.js.map +1 -0
- package/webapp/dist/assets/{chunk-NQ4KR5QH-CK365lrr.js → chunk-DI55MBZ5-BPJLdjOS.js} +7 -9
- package/webapp/dist/assets/chunk-DI55MBZ5-BPJLdjOS.js.map +1 -0
- package/webapp/dist/assets/{chunk-FMBD7UC4-B-RtOs7e.js → chunk-FMBD7UC4-ETqcFoxP.js} +2 -2
- package/webapp/dist/assets/chunk-FMBD7UC4-ETqcFoxP.js.map +1 -0
- package/webapp/dist/assets/{chunk-KX2RTZJC-DH9UrpuG.js → chunk-QN33PNHL-B-dPkZ9T.js} +2 -2
- package/webapp/dist/assets/chunk-QN33PNHL-B-dPkZ9T.js.map +1 -0
- package/webapp/dist/assets/{chunk-QZHKN3VN-BCaWPGDm.js → chunk-QZHKN3VN-BqX4sv4Q.js} +2 -2
- package/webapp/dist/assets/chunk-QZHKN3VN-BqX4sv4Q.js.map +1 -0
- package/webapp/dist/assets/{chunk-JSJVCQXG-Da1d3uS4.js → chunk-TZMSLE5B-BnfBq8PA.js} +6 -14
- package/webapp/dist/assets/chunk-TZMSLE5B-BnfBq8PA.js.map +1 -0
- package/webapp/dist/assets/{classDiagram-VBA2DB6C-CvMBU4WA.js → classDiagram-2ON5EDUG-w89KWhQq.js} +6 -7
- package/webapp/dist/assets/classDiagram-2ON5EDUG-w89KWhQq.js.map +1 -0
- package/webapp/dist/assets/{classDiagram-v2-RAHNMMFH-CvMBU4WA.js → classDiagram-v2-WZHVMYZB-w89KWhQq.js} +6 -7
- package/webapp/dist/assets/classDiagram-v2-WZHVMYZB-w89KWhQq.js.map +1 -0
- package/webapp/dist/assets/{clone-r98jR0MC.js → clone-D7jwWk83.js} +2 -2
- package/webapp/dist/assets/clone-D7jwWk83.js.map +1 -0
- package/webapp/dist/assets/{cose-bilkent-S5V4N54A-t6J60Ogk.js → cose-bilkent-S5V4N54A-CHdRDUYT.js} +2 -2
- package/webapp/dist/assets/cose-bilkent-S5V4N54A-CHdRDUYT.js.map +1 -0
- package/webapp/dist/assets/cytoscape.esm-Bm8DJGmZ.js.map +1 -1
- package/webapp/dist/assets/{dagre-KLK3FWXG-BlqmY2DV.js → dagre-6UL2VRFP-CfltZHNg.js} +7 -7
- package/webapp/dist/assets/dagre-6UL2VRFP-CfltZHNg.js.map +1 -0
- package/webapp/dist/assets/defaultLocale-B2RvLBDe.js.map +1 -1
- package/webapp/dist/assets/{diagram-E7M64L7V-FwCHeIUD.js → diagram-PSM6KHXK-Bp_jHEhR.js} +10 -10
- package/webapp/dist/assets/diagram-PSM6KHXK-Bp_jHEhR.js.map +1 -0
- package/webapp/dist/assets/{diagram-IFDJBPK2-NhtmkuZG.js → diagram-QEK2KX5R-Cdvy6Ep9.js} +8 -9
- package/webapp/dist/assets/diagram-QEK2KX5R-Cdvy6Ep9.js.map +1 -0
- package/webapp/dist/assets/{diagram-P4PSJMXO-B9FcmokX.js → diagram-S2PKOQOG-BwUE6huD.js} +8 -8
- package/webapp/dist/assets/diagram-S2PKOQOG-BwUE6huD.js.map +1 -0
- package/webapp/dist/assets/{erDiagram-INFDFZHY-DHKmWvtB.js → erDiagram-Q2GNP2WA-_GQN3dnV.js} +75 -96
- package/webapp/dist/assets/erDiagram-Q2GNP2WA-_GQN3dnV.js.map +1 -0
- package/webapp/dist/assets/{flowDiagram-PKNHOUZH-C7Zi8I7T.js → flowDiagram-NV44I4VS-Dhbd5FE4.js} +81 -98
- package/webapp/dist/assets/flowDiagram-NV44I4VS-Dhbd5FE4.js.map +1 -0
- package/webapp/dist/assets/{ganttDiagram-A5KZAMGK-Cv2T8tz_.js → ganttDiagram-JELNMOA3-BKQtJ_t7.js} +3 -28
- package/webapp/dist/assets/ganttDiagram-JELNMOA3-BKQtJ_t7.js.map +1 -0
- package/webapp/dist/assets/{gitGraphDiagram-K3NZZRJ6-DztaipJU.js → gitGraphDiagram-V2S2FVAM-BcW7gX3_.js} +46 -38
- package/webapp/dist/assets/gitGraphDiagram-V2S2FVAM-BcW7gX3_.js.map +1 -0
- package/webapp/dist/assets/graph-CE4HL0aU.js +425 -0
- package/webapp/dist/assets/graph-CE4HL0aU.js.map +1 -0
- package/webapp/dist/assets/{index-hve5MWPs.js → index-JCkFg05X.js} +1111 -1027
- package/webapp/dist/assets/{index-hve5MWPs.js.map → index-JCkFg05X.js.map} +1 -1
- package/webapp/dist/assets/{index-YaxF76or.css → index-xvYYeHuy.css} +1 -1
- package/webapp/dist/assets/{infoDiagram-LFFYTUFH-VgsbBPZP.js → infoDiagram-HS3SLOUP-B9IsDiBf.js} +7 -7
- package/webapp/dist/assets/infoDiagram-HS3SLOUP-B9IsDiBf.js.map +1 -0
- package/webapp/dist/assets/init-ZxktEp_H.js.map +1 -1
- package/webapp/dist/assets/{journeyDiagram-4ABVD52K-OO8sev-Y.js → journeyDiagram-XKPGCS4Q-BpJK6b4f.js} +5 -5
- package/webapp/dist/assets/journeyDiagram-XKPGCS4Q-BpJK6b4f.js.map +1 -0
- package/webapp/dist/assets/{kanban-definition-K7BYSVSG-DiYCC1Ig.js → kanban-definition-3W4ZIXB7-D0vLghpg.js} +3 -5
- package/webapp/dist/assets/kanban-definition-3W4ZIXB7-D0vLghpg.js.map +1 -0
- package/webapp/dist/assets/{layout-DdZSgGdu.js → layout-C9CTTdmU.js} +5 -5
- package/webapp/dist/assets/layout-C9CTTdmU.js.map +1 -0
- package/webapp/dist/assets/{linear-7-aHtaFi.js → linear-DoEKTEMq.js} +2 -2
- package/webapp/dist/assets/linear-DoEKTEMq.js.map +1 -0
- package/webapp/dist/assets/{mindmap-definition-YRQLILUH-IG3I-RdD.js → mindmap-definition-VGOIOE7T-D09DtFPK.js} +5 -7
- package/webapp/dist/assets/mindmap-definition-VGOIOE7T-D09DtFPK.js.map +1 -0
- package/webapp/dist/assets/ordinal-CxptdPJm.js.map +1 -1
- package/webapp/dist/assets/{pieDiagram-SKSYHLDU-z68KJT5r.js → pieDiagram-ADFJNKIX-BcM3GR1l.js} +8 -8
- package/webapp/dist/assets/pieDiagram-ADFJNKIX-BcM3GR1l.js.map +1 -0
- package/webapp/dist/assets/{quadrantDiagram-337W2JSQ-DaENWdO6.js → quadrantDiagram-AYHSOK5B-D8DjF5Pg.js} +3 -3
- package/webapp/dist/assets/quadrantDiagram-AYHSOK5B-D8DjF5Pg.js.map +1 -0
- package/webapp/dist/assets/{requirementDiagram-Z7DCOOCP-ROTFv4sa.js → requirementDiagram-UZGBJVZJ-D2J7OgDl.js} +6 -16
- package/webapp/dist/assets/requirementDiagram-UZGBJVZJ-D2J7OgDl.js.map +1 -0
- package/webapp/dist/assets/{sankeyDiagram-WA2Y5GQK-CK7qtpzw.js → sankeyDiagram-TZEHDZUN-BHweOFUp.js} +2 -2
- package/webapp/dist/assets/sankeyDiagram-TZEHDZUN-BHweOFUp.js.map +1 -0
- package/webapp/dist/assets/{sequenceDiagram-2WXFIKYE-R5lDySeI.js → sequenceDiagram-WL72ISMW-BDCBaUSI.js} +201 -601
- package/webapp/dist/assets/sequenceDiagram-WL72ISMW-BDCBaUSI.js.map +1 -0
- package/webapp/dist/assets/{stateDiagram-RAJIS63D-sr7msF5U.js → stateDiagram-FKZM4ZOC-jwEbpF4Z.js} +9 -9
- package/webapp/dist/assets/stateDiagram-FKZM4ZOC-jwEbpF4Z.js.map +1 -0
- package/webapp/dist/assets/{stateDiagram-v2-FVOUBMTO-X663liwS.js → stateDiagram-v2-4FDKWEC3-Blk529CR.js} +5 -5
- package/webapp/dist/assets/stateDiagram-v2-4FDKWEC3-Blk529CR.js.map +1 -0
- package/webapp/dist/assets/{timeline-definition-YZTLITO2-Bw0TdG26.js → timeline-definition-IT6M3QCI-BQO-9msf.js} +3 -3
- package/webapp/dist/assets/timeline-definition-IT6M3QCI-BQO-9msf.js.map +1 -0
- package/webapp/dist/assets/{treemap-KZPCXAKY-D_sjKwI7.js → treemap-GDKQZRPO-Bc2g2vuB.js} +24 -37
- package/webapp/dist/assets/treemap-GDKQZRPO-Bc2g2vuB.js.map +1 -0
- package/webapp/dist/assets/{xychartDiagram-JWTSCODW-C65ESjTc.js → xychartDiagram-PRI3JC2R-DKzNu-Hu.js} +4 -4
- package/webapp/dist/assets/xychartDiagram-PRI3JC2R-DKzNu-Hu.js.map +1 -0
- package/webapp/dist/index.html +2 -2
- package/webapp/dist/assets/_basePickBy-DsirmCgI.js.map +0 -1
- package/webapp/dist/assets/_baseUniq-tR6G8loB.js.map +0 -1
- package/webapp/dist/assets/arc-CzxpASkZ.js.map +0 -1
- package/webapp/dist/assets/architectureDiagram-2XIMDMQ5-BSH7H5oI.js.map +0 -1
- package/webapp/dist/assets/blockDiagram-WCTKOSBZ-DpLIr7yO.js.map +0 -1
- package/webapp/dist/assets/c4Diagram-IC4MRINW-WuYKgWfY.js.map +0 -1
- package/webapp/dist/assets/channel-B-v9dqLN.js.map +0 -1
- package/webapp/dist/assets/chunk-4BX2VUAB-MtFUfKZy.js.map +0 -1
- package/webapp/dist/assets/chunk-55IACEB6-rY9AJdzj.js.map +0 -1
- package/webapp/dist/assets/chunk-FMBD7UC4-B-RtOs7e.js.map +0 -1
- package/webapp/dist/assets/chunk-JSJVCQXG-Da1d3uS4.js.map +0 -1
- package/webapp/dist/assets/chunk-KX2RTZJC-DH9UrpuG.js.map +0 -1
- package/webapp/dist/assets/chunk-NQ4KR5QH-CK365lrr.js.map +0 -1
- package/webapp/dist/assets/chunk-QZHKN3VN-BCaWPGDm.js.map +0 -1
- package/webapp/dist/assets/chunk-WL4C6EOR-DDCnEwft.js.map +0 -1
- package/webapp/dist/assets/classDiagram-VBA2DB6C-CvMBU4WA.js.map +0 -1
- package/webapp/dist/assets/classDiagram-v2-RAHNMMFH-CvMBU4WA.js.map +0 -1
- package/webapp/dist/assets/clone-r98jR0MC.js.map +0 -1
- package/webapp/dist/assets/cose-bilkent-S5V4N54A-t6J60Ogk.js.map +0 -1
- package/webapp/dist/assets/dagre-KLK3FWXG-BlqmY2DV.js.map +0 -1
- package/webapp/dist/assets/diagram-E7M64L7V-FwCHeIUD.js.map +0 -1
- package/webapp/dist/assets/diagram-IFDJBPK2-NhtmkuZG.js.map +0 -1
- package/webapp/dist/assets/diagram-P4PSJMXO-B9FcmokX.js.map +0 -1
- package/webapp/dist/assets/erDiagram-INFDFZHY-DHKmWvtB.js.map +0 -1
- package/webapp/dist/assets/flowDiagram-PKNHOUZH-C7Zi8I7T.js.map +0 -1
- package/webapp/dist/assets/ganttDiagram-A5KZAMGK-Cv2T8tz_.js.map +0 -1
- package/webapp/dist/assets/gitGraphDiagram-K3NZZRJ6-DztaipJU.js.map +0 -1
- package/webapp/dist/assets/graph-C5yf62Vs.js +0 -782
- package/webapp/dist/assets/graph-C5yf62Vs.js.map +0 -1
- package/webapp/dist/assets/infoDiagram-LFFYTUFH-VgsbBPZP.js.map +0 -1
- package/webapp/dist/assets/ishikawaDiagram-PHBUUO56-C7j3YWdw.js +0 -966
- package/webapp/dist/assets/ishikawaDiagram-PHBUUO56-C7j3YWdw.js.map +0 -1
- package/webapp/dist/assets/journeyDiagram-4ABVD52K-OO8sev-Y.js.map +0 -1
- package/webapp/dist/assets/kanban-definition-K7BYSVSG-DiYCC1Ig.js.map +0 -1
- package/webapp/dist/assets/layout-DdZSgGdu.js.map +0 -1
- package/webapp/dist/assets/linear-7-aHtaFi.js.map +0 -1
- package/webapp/dist/assets/mindmap-definition-YRQLILUH-IG3I-RdD.js.map +0 -1
- package/webapp/dist/assets/pieDiagram-SKSYHLDU-z68KJT5r.js.map +0 -1
- package/webapp/dist/assets/quadrantDiagram-337W2JSQ-DaENWdO6.js.map +0 -1
- package/webapp/dist/assets/requirementDiagram-Z7DCOOCP-ROTFv4sa.js.map +0 -1
- package/webapp/dist/assets/sankeyDiagram-WA2Y5GQK-CK7qtpzw.js.map +0 -1
- package/webapp/dist/assets/sequenceDiagram-2WXFIKYE-R5lDySeI.js.map +0 -1
- package/webapp/dist/assets/stateDiagram-RAJIS63D-sr7msF5U.js.map +0 -1
- package/webapp/dist/assets/stateDiagram-v2-FVOUBMTO-X663liwS.js.map +0 -1
- package/webapp/dist/assets/timeline-definition-YZTLITO2-Bw0TdG26.js.map +0 -1
- package/webapp/dist/assets/treemap-KZPCXAKY-D_sjKwI7.js.map +0 -1
- package/webapp/dist/assets/vennDiagram-LZ73GAT5-DhlHIHid.js +0 -2487
- package/webapp/dist/assets/vennDiagram-LZ73GAT5-DhlHIHid.js.map +0 -1
- package/webapp/dist/assets/xychartDiagram-JWTSCODW-C65ESjTc.js.map +0 -1
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { DomindsAppInstallJson } from '@longrun-ai/kernel/app-json';
|
|
2
2
|
import type { AppsResolutionEntry } from './resolution-file';
|
|
3
3
|
export type AssignedPortResolutionReason = 'no_frontend' | 'kept_existing' | 'selected_default' | 'allocated_stable_range' | 'reassigned_from_existing_conflict' | 'reassigned_from_existing_unbindable';
|
|
4
4
|
export type AssignedPortResolution = Readonly<{
|
|
@@ -16,13 +16,13 @@ export type AssignedPortResolution = Readonly<{
|
|
|
16
16
|
*/
|
|
17
17
|
export declare function resolveStableAssignedPort(params: {
|
|
18
18
|
appId: string;
|
|
19
|
-
installJson:
|
|
19
|
+
installJson: DomindsAppInstallJson;
|
|
20
20
|
existingApps: ReadonlyArray<AppsResolutionEntry>;
|
|
21
21
|
existingAssignedPort: number | null;
|
|
22
22
|
}): Promise<number | null>;
|
|
23
23
|
export declare function resolveStableAssignedPortWithReason(params: {
|
|
24
24
|
appId: string;
|
|
25
|
-
installJson:
|
|
25
|
+
installJson: DomindsAppInstallJson;
|
|
26
26
|
existingApps: ReadonlyArray<AppsResolutionEntry>;
|
|
27
27
|
existingAssignedPort: number | null;
|
|
28
28
|
}): Promise<AssignedPortResolution>;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { type
|
|
1
|
+
import { type DomindsAppInstallJson } from '@longrun-ai/kernel/app-json';
|
|
2
2
|
export type AppsResolutionSchemaVersion = 1;
|
|
3
3
|
export type AppsResolutionSource = Readonly<{
|
|
4
4
|
kind: 'npx';
|
|
@@ -12,7 +12,7 @@ export type AppsResolutionEntry = Readonly<{
|
|
|
12
12
|
enabled: boolean;
|
|
13
13
|
source: AppsResolutionSource;
|
|
14
14
|
assignedPort: number | null;
|
|
15
|
-
installJson:
|
|
15
|
+
installJson: DomindsAppInstallJson;
|
|
16
16
|
}>;
|
|
17
17
|
export type AppsResolutionFile = Readonly<{
|
|
18
18
|
schemaVersion: AppsResolutionSchemaVersion;
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { type
|
|
1
|
+
import { type DomindsAppInstallJson } from '@longrun-ai/kernel/app-json';
|
|
2
2
|
export declare function runDomindsAppJsonViaNpx(params: {
|
|
3
3
|
spec: string;
|
|
4
4
|
cwdAbs: string;
|
|
5
|
-
}): Promise<
|
|
5
|
+
}): Promise<DomindsAppInstallJson>;
|
|
6
6
|
export declare function runDomindsAppJsonViaLocalPackage(params: {
|
|
7
7
|
packageRootAbs: string;
|
|
8
|
-
}): Promise<
|
|
8
|
+
}): Promise<DomindsAppInstallJson>;
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
import type { DomindsAppDynamicToolsetsContext, DomindsAppReminderOwnerApplyContext, DomindsAppReminderOwnerRenderContext, DomindsAppReminderOwnerUpdateContext, DomindsAppRunControlContext, DomindsAppRunControlResult } from '@longrun-ai/kernel/app-host-contract';
|
|
2
|
-
import type { DomindsAppHostReminderUpdateResult, DomindsAppHostToolResult,
|
|
2
|
+
import type { DomindsAppHostReminderUpdateResult, DomindsAppHostToolResult, DomindsAppInstallJson, DomindsAppReminderApplyRequest, DomindsAppReminderApplyResult } from '@longrun-ai/kernel/app-json';
|
|
3
3
|
import type { ChatMessage } from '../llm/client';
|
|
4
4
|
import type { ToolArguments } from '../tool';
|
|
5
5
|
import type { AppsHostMessageToKernel } from './ipc-types';
|
|
6
6
|
export type EnabledAppForHost = Readonly<{
|
|
7
7
|
appId: string;
|
|
8
8
|
runtimePort: number | null;
|
|
9
|
-
installJson:
|
|
9
|
+
installJson: DomindsAppInstallJson;
|
|
10
10
|
hostSourceVersion: string | null;
|
|
11
11
|
}>;
|
|
12
12
|
export type AppsHostClient = Readonly<{
|
package/dist/apps-host/host.js
CHANGED
|
@@ -33,12 +33,14 @@ function isStringArray(value) {
|
|
|
33
33
|
return Array.isArray(value) && value.every((item) => typeof item === 'string');
|
|
34
34
|
}
|
|
35
35
|
function isToolCallOutput(value) {
|
|
36
|
-
if (typeof value === 'string')
|
|
37
|
-
return true;
|
|
38
36
|
if (!isRecord(value))
|
|
39
37
|
return false;
|
|
40
38
|
if (typeof value['content'] !== 'string')
|
|
41
39
|
return false;
|
|
40
|
+
const outcome = value['outcome'];
|
|
41
|
+
if (outcome !== 'success' && outcome !== 'failure' && outcome !== 'partial_failure') {
|
|
42
|
+
return false;
|
|
43
|
+
}
|
|
42
44
|
const contentItems = value['contentItems'];
|
|
43
45
|
return contentItems === undefined || Array.isArray(contentItems);
|
|
44
46
|
}
|
|
@@ -183,15 +185,12 @@ function isChatMessage(value) {
|
|
|
183
185
|
return true;
|
|
184
186
|
}
|
|
185
187
|
function normalizeToolResult(value) {
|
|
186
|
-
if (isToolCallOutput(value)) {
|
|
187
|
-
return { output: value };
|
|
188
|
-
}
|
|
189
188
|
if (!isRecord(value)) {
|
|
190
|
-
throw new Error('Invalid app tool result: expected
|
|
189
|
+
throw new Error('Invalid app tool result: expected { output: { content, outcome, contentItems? }, ... }');
|
|
191
190
|
}
|
|
192
191
|
const output = value['output'];
|
|
193
192
|
if (!isToolCallOutput(output)) {
|
|
194
|
-
throw new Error('Invalid app tool result: output must be
|
|
193
|
+
throw new Error('Invalid app tool result: output must be { content, outcome, contentItems? }');
|
|
195
194
|
}
|
|
196
195
|
const reminderRequestsRaw = value['reminderRequests'];
|
|
197
196
|
if (reminderRequestsRaw !== undefined && !Array.isArray(reminderRequestsRaw)) {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { DomindsAppRunControlResult } from '@longrun-ai/kernel/app-host-contract';
|
|
2
|
-
import type { DomindsAppDialogReminderRequestBatch, DomindsAppHostReminderUpdateResult,
|
|
2
|
+
import type { DomindsAppDialogReminderRequestBatch, DomindsAppHostReminderUpdateResult, DomindsAppInstallJson, DomindsAppReminderApplyRequest, DomindsAppReminderApplyResult, DomindsAppReminderState } from '@longrun-ai/kernel/app-json';
|
|
3
3
|
import type { LanguageCode } from '@longrun-ai/kernel/types/language';
|
|
4
4
|
import type { ChatMessage } from '../llm/client';
|
|
5
5
|
import type { ToolArguments, ToolCallOutput } from '../tool';
|
|
@@ -13,7 +13,7 @@ export type AppsHostKernelInitMessage = Readonly<{
|
|
|
13
13
|
apps: ReadonlyArray<Readonly<{
|
|
14
14
|
appId: string;
|
|
15
15
|
runtimePort: number | null;
|
|
16
|
-
installJson:
|
|
16
|
+
installJson: DomindsAppInstallJson;
|
|
17
17
|
}>>;
|
|
18
18
|
}>;
|
|
19
19
|
export type AppsHostKernelToolCallMessage = Readonly<{
|
|
@@ -222,7 +222,7 @@ Recommended user mental model:
|
|
|
222
222
|
|
|
223
223
|
(Current: implemented) existing anchors:
|
|
224
224
|
|
|
225
|
-
- JSON schema: `dominds/main/apps/app-json.ts` (`
|
|
225
|
+
- JSON schema: `dominds/main/apps/app-json.ts` (`DomindsAppInstallJson`).
|
|
226
226
|
- Apps configuration file: `dominds/main/apps/configuration-file.ts`.
|
|
227
227
|
- Apps resolution file: `dominds/main/apps/resolution-file.ts`.
|
|
228
228
|
|
|
@@ -221,7 +221,7 @@ Install JSON 是 app 与 Kernel/CLI 之间的**安装/运行握手载荷**。它
|
|
|
221
221
|
|
|
222
222
|
(现状:已实现)install json schema 与 apps 配置/解析锚点仍可参考:
|
|
223
223
|
|
|
224
|
-
- JSON schema:`dominds/main/apps/app-json.ts`(`
|
|
224
|
+
- JSON schema:`dominds/main/apps/app-json.ts`(`DomindsAppInstallJson`)。
|
|
225
225
|
- `.apps/configuration.yaml`:`dominds/main/apps/configuration-file.ts`。
|
|
226
226
|
- `.apps/resolution.yaml`:`dominds/main/apps/resolution-file.ts`。
|
|
227
227
|
|
|
@@ -0,0 +1,280 @@
|
|
|
1
|
+
# Tellask Result Unification
|
|
2
|
+
|
|
3
|
+
## Purpose
|
|
4
|
+
|
|
5
|
+
This document captures the agreed direction for the current tellask refactor so the
|
|
6
|
+
implementation can stay aligned while multiple storage, runtime, provider, and frontend
|
|
7
|
+
paths are being simplified at the same time.
|
|
8
|
+
|
|
9
|
+
The goal is not to preserve old technical symmetry for its own sake. The goal is to make
|
|
10
|
+
tellask behave as one coherent business feature with fewer special cases.
|
|
11
|
+
|
|
12
|
+
## Agreed Direction
|
|
13
|
+
|
|
14
|
+
- Keep `tellask_call_record` as the tellask-family call record.
|
|
15
|
+
- Keep one unified tellask business result type:
|
|
16
|
+
- `tellask_result_record`
|
|
17
|
+
- `tellask_result_msg`
|
|
18
|
+
- `tellask_result_evt`
|
|
19
|
+
- Keep carryover special and separate:
|
|
20
|
+
- rename `tellask_carryover_result_record` to `tellask_carryover_record`
|
|
21
|
+
- rename `tellask_carryover_result_msg` to `tellask_carryover_msg`
|
|
22
|
+
- rename `tellask_call_carryover_evt` / `tellask_carryover_result_evt` style names into a single
|
|
23
|
+
`tellask_carryover_evt`
|
|
24
|
+
- Inline tellask result rendering is no longer the target model.
|
|
25
|
+
- Tellask results should render as separate bubbles.
|
|
26
|
+
- Call-site UI may still exist for pending / settled state, but result body should not depend on
|
|
27
|
+
inline rendering.
|
|
28
|
+
- `replyTellask*` is not a separate business result family to unify on its own.
|
|
29
|
+
`replyTellask*` is a mechanism that produces a tellask result.
|
|
30
|
+
- `askHuman` should move into the tellask result flow instead of being represented as a normal
|
|
31
|
+
user bubble.
|
|
32
|
+
- Q4H answers should not be persisted as `human_text_record` for askHuman result rendering.
|
|
33
|
+
|
|
34
|
+
## Current Problem
|
|
35
|
+
|
|
36
|
+
Tellask business semantics are currently split across too many layers:
|
|
37
|
+
|
|
38
|
+
- `tellask_call_record`
|
|
39
|
+
- call start
|
|
40
|
+
- `tellask_call_result_record`
|
|
41
|
+
- local inline tellask business result
|
|
42
|
+
- `tellask_response_record`
|
|
43
|
+
- sideline / subdialog response bubble
|
|
44
|
+
- `tellask_result_record`
|
|
45
|
+
- thin technical pair record added later for call/result parity
|
|
46
|
+
- `tellask_carryover_result_record`
|
|
47
|
+
- special cross-course carryover
|
|
48
|
+
|
|
49
|
+
This produces several kinds of debt:
|
|
50
|
+
|
|
51
|
+
- one business feature has multiple result record types
|
|
52
|
+
- one business result message name has mixed semantics
|
|
53
|
+
- frontend uses different event families for inline vs separate-bubble tellask results
|
|
54
|
+
- `askHuman` answer flow still re-enters the generic user-message path
|
|
55
|
+
- provider/runtime logic has had to invent technical projection types that are not the real
|
|
56
|
+
business model
|
|
57
|
+
|
|
58
|
+
## Business Model After Refactor
|
|
59
|
+
|
|
60
|
+
### Tellask Call
|
|
61
|
+
|
|
62
|
+
`tellask_call_record` remains the start record for tellask-family tool invocation.
|
|
63
|
+
|
|
64
|
+
It still covers:
|
|
65
|
+
|
|
66
|
+
- `tellask`
|
|
67
|
+
- `tellaskSessionless`
|
|
68
|
+
- `tellaskBack`
|
|
69
|
+
- `askHuman`
|
|
70
|
+
- `freshBootsReasoning`
|
|
71
|
+
- `replyTellask`
|
|
72
|
+
- `replyTellaskSessionless`
|
|
73
|
+
- `replyTellaskBack`
|
|
74
|
+
|
|
75
|
+
### Tellask Result
|
|
76
|
+
|
|
77
|
+
`tellask_result_record` becomes the single business result record for tellask outcomes.
|
|
78
|
+
|
|
79
|
+
It should absorb the business payload currently split across:
|
|
80
|
+
|
|
81
|
+
- `tellask_call_result_record`
|
|
82
|
+
- `tellask_response_record`
|
|
83
|
+
|
|
84
|
+
It should be rich enough to carry the actual tellask business context, not just a thin tool pair.
|
|
85
|
+
|
|
86
|
+
### Tellask Carryover
|
|
87
|
+
|
|
88
|
+
Carryover stays separate because it is not a normal call/result pair outcome.
|
|
89
|
+
|
|
90
|
+
Its essence is:
|
|
91
|
+
|
|
92
|
+
- cross-course continuation
|
|
93
|
+
- special context anchor semantics
|
|
94
|
+
- intentionally not part of standard call/result unification
|
|
95
|
+
|
|
96
|
+
So it should remain independent under shorter names:
|
|
97
|
+
|
|
98
|
+
- `tellask_carryover_record`
|
|
99
|
+
- `tellask_carryover_msg`
|
|
100
|
+
- `tellask_carryover_evt`
|
|
101
|
+
|
|
102
|
+
## Message And Event Model
|
|
103
|
+
|
|
104
|
+
### Result Bubble Direction
|
|
105
|
+
|
|
106
|
+
Tellask business results should render as separate bubbles.
|
|
107
|
+
|
|
108
|
+
That means the frontend event model should converge toward:
|
|
109
|
+
|
|
110
|
+
- `tellask_call_start_evt`
|
|
111
|
+
- call-site lifecycle start
|
|
112
|
+
- `tellask_result_evt`
|
|
113
|
+
- business result bubble creation / replay
|
|
114
|
+
- status updates for the related call site
|
|
115
|
+
- `tellask_carryover_evt`
|
|
116
|
+
- special carryover bubble
|
|
117
|
+
|
|
118
|
+
The old split:
|
|
119
|
+
|
|
120
|
+
- `tellask_call_result_evt`
|
|
121
|
+
- `tellask_response_evt`
|
|
122
|
+
|
|
123
|
+
should be collapsed into `tellask_result_evt`.
|
|
124
|
+
|
|
125
|
+
### Frontend Behavior
|
|
126
|
+
|
|
127
|
+
Frontend call-site handling should become simpler:
|
|
128
|
+
|
|
129
|
+
- call site shows pending / settled / carried-over state
|
|
130
|
+
- tellask result body is shown in a separate bubble
|
|
131
|
+
- no dependency on inline result body rendering
|
|
132
|
+
|
|
133
|
+
This applies to:
|
|
134
|
+
|
|
135
|
+
- local tellask failures
|
|
136
|
+
- sideline/subdialog responses
|
|
137
|
+
- askHuman pending/final result display
|
|
138
|
+
|
|
139
|
+
## AskHuman Direction
|
|
140
|
+
|
|
141
|
+
`askHuman` should behave as part of the tellask family, not as a detour into the generic user
|
|
142
|
+
message path.
|
|
143
|
+
|
|
144
|
+
### Desired Flow
|
|
145
|
+
|
|
146
|
+
1. `askHuman` call starts as a tellask-family call.
|
|
147
|
+
2. A temporary tellask-style result is shown while waiting.
|
|
148
|
+
3. When the human answers, the final askHuman result is represented as a tellask result.
|
|
149
|
+
4. The answer should not be kept as a normal user bubble for this purpose.
|
|
150
|
+
|
|
151
|
+
### Important Clarification
|
|
152
|
+
|
|
153
|
+
The runtime may still need the answer content to continue the next generation round.
|
|
154
|
+
|
|
155
|
+
But that technical need must not force the product model to keep askHuman answers as
|
|
156
|
+
`human_text_record` or ordinary user-style UI bubbles.
|
|
157
|
+
|
|
158
|
+
The tellask business model is the source of truth.
|
|
159
|
+
|
|
160
|
+
## ReplyTellask Direction
|
|
161
|
+
|
|
162
|
+
`replyTellask*` should not be treated as a separate business result family.
|
|
163
|
+
|
|
164
|
+
The correct business interpretation is:
|
|
165
|
+
|
|
166
|
+
- `replyTellask*` is an action that produces a tellask result
|
|
167
|
+
- the tellask result is the business object
|
|
168
|
+
- `replyTellask*` itself does not need another parallel business-unification effort
|
|
169
|
+
|
|
170
|
+
In practice this means the refactor should avoid introducing extra local-only reply result models
|
|
171
|
+
just to satisfy old technical pairing assumptions.
|
|
172
|
+
|
|
173
|
+
## Tellask Result Record Shape
|
|
174
|
+
|
|
175
|
+
The unified `tellask_result_record` should be rich and business-oriented.
|
|
176
|
+
|
|
177
|
+
It should not flatten every field at top level.
|
|
178
|
+
|
|
179
|
+
Preferred shape:
|
|
180
|
+
|
|
181
|
+
- keep truly global result fields at top level
|
|
182
|
+
- move stable field groups into optional nested structures
|
|
183
|
+
- inside a nested structure, fields should be required whenever that structure is present
|
|
184
|
+
|
|
185
|
+
Suggested top-level concerns:
|
|
186
|
+
|
|
187
|
+
- record identity / timestamp / course refs
|
|
188
|
+
- `callId`
|
|
189
|
+
- `callName`
|
|
190
|
+
- `status`
|
|
191
|
+
- `content`
|
|
192
|
+
|
|
193
|
+
Suggested nested groups:
|
|
194
|
+
|
|
195
|
+
- `call`
|
|
196
|
+
- original tellask call context
|
|
197
|
+
- example fields:
|
|
198
|
+
- `tellaskContent`
|
|
199
|
+
- `mentionList`
|
|
200
|
+
- `sessionSlug`
|
|
201
|
+
- `responder`
|
|
202
|
+
- who produced the business result
|
|
203
|
+
- example fields:
|
|
204
|
+
- `responderId`
|
|
205
|
+
- `agentId`
|
|
206
|
+
- `originMemberId`
|
|
207
|
+
- `route`
|
|
208
|
+
- navigation / callee metadata when applicable
|
|
209
|
+
- example fields:
|
|
210
|
+
- `calleeDialogId`
|
|
211
|
+
- `calleeCourse`
|
|
212
|
+
- `calleeGenseq`
|
|
213
|
+
|
|
214
|
+
The exact final union can be refined during implementation, but the important rule is:
|
|
215
|
+
|
|
216
|
+
- business grouping first
|
|
217
|
+
- technical pairing concerns do not get to dictate the field model
|
|
218
|
+
|
|
219
|
+
## Provider / Runtime Interpretation
|
|
220
|
+
|
|
221
|
+
The unified tellask result model is the business truth.
|
|
222
|
+
|
|
223
|
+
Provider/runtime projection must adapt to it, not the other way around.
|
|
224
|
+
|
|
225
|
+
This means:
|
|
226
|
+
|
|
227
|
+
- do not invent thin technical result types as the canonical tellask model
|
|
228
|
+
- if the provider layer needs a particular call/result projection, derive it from the business
|
|
229
|
+
message
|
|
230
|
+
- do not let tool-pair convenience decide what fields are allowed to exist
|
|
231
|
+
|
|
232
|
+
## Files Expected To Change
|
|
233
|
+
|
|
234
|
+
The refactor will likely touch at least these areas:
|
|
235
|
+
|
|
236
|
+
- `packages/kernel/src/types/storage.ts`
|
|
237
|
+
- `packages/kernel/src/types/chat-message.ts`
|
|
238
|
+
- `packages/kernel/src/types/dialog.ts`
|
|
239
|
+
- `main/persistence.ts`
|
|
240
|
+
- `main/dialog.ts`
|
|
241
|
+
- `main/priming.ts`
|
|
242
|
+
- `main/dialog-fork.ts`
|
|
243
|
+
- `main/llm/kernel-driver/tellask-special.ts`
|
|
244
|
+
- `main/llm/kernel-driver/drive.ts`
|
|
245
|
+
- `main/server/websocket-handler.ts`
|
|
246
|
+
- `main/llm/gen/openai.ts`
|
|
247
|
+
- `main/llm/gen/openai-compatible.ts`
|
|
248
|
+
- `main/llm/gen/codex.ts`
|
|
249
|
+
- `main/llm/gen/anthropic.ts`
|
|
250
|
+
- `main/llm/gen/mock.ts`
|
|
251
|
+
- `webapp/src/components/dominds-dialog-container.ts`
|
|
252
|
+
- `webapp/src/components/dominds-app.tsx`
|
|
253
|
+
|
|
254
|
+
Tests will also need a broad update wherever old tellask inline/result/carryover names are asserted.
|
|
255
|
+
|
|
256
|
+
## Implementation Checklist
|
|
257
|
+
|
|
258
|
+
- Redefine `tellask_result_record` as the single business result record.
|
|
259
|
+
- Remove `tellask_call_result_record`.
|
|
260
|
+
- Remove `tellask_response_record`.
|
|
261
|
+
- Rename carryover record/msg/evt to shorter names.
|
|
262
|
+
- Replace old tellask result event split with unified `tellask_result_evt`.
|
|
263
|
+
- Update replay and restore to rebuild unified tellask result messages.
|
|
264
|
+
- Update frontend to render tellask results as separate bubbles.
|
|
265
|
+
- Keep call-site lifecycle status, but stop depending on inline result body.
|
|
266
|
+
- Route askHuman answer flow through tellask result rendering instead of normal user-bubble
|
|
267
|
+
persistence.
|
|
268
|
+
- Revisit provider projection after the business model is in place, not before.
|
|
269
|
+
|
|
270
|
+
## Review Standard For This Refactor
|
|
271
|
+
|
|
272
|
+
Behavior review should focus on current product semantics, not historical storage compatibility.
|
|
273
|
+
|
|
274
|
+
Primary questions:
|
|
275
|
+
|
|
276
|
+
- Does the user now see one coherent tellask result model?
|
|
277
|
+
- Are local tellask failures and sideline tellask responses rendered the same way?
|
|
278
|
+
- Does askHuman now behave like tellask instead of like an unrelated user-message path?
|
|
279
|
+
- Does carryover remain special without polluting the unified tellask result model?
|
|
280
|
+
- Did we remove result-path branching instead of just moving it around?
|
|
@@ -787,6 +787,18 @@ async function emitAssistantSaying(dlg, content) {
|
|
|
787
787
|
await dlg.sayingChunk(content);
|
|
788
788
|
await dlg.sayingFinish();
|
|
789
789
|
}
|
|
790
|
+
function resolveFuncToolFollowupMode(tool) {
|
|
791
|
+
return tool?.followupMode ?? 'immediate';
|
|
792
|
+
}
|
|
793
|
+
function shouldImmediatelyFollowUpSuccessfulToolResult(tool) {
|
|
794
|
+
return resolveFuncToolFollowupMode(tool) === 'immediate';
|
|
795
|
+
}
|
|
796
|
+
function shouldImmediatelyFollowUpToolOutcome(tool, outcome) {
|
|
797
|
+
if (outcome === 'failure' || outcome === 'partial_failure') {
|
|
798
|
+
return true;
|
|
799
|
+
}
|
|
800
|
+
return shouldImmediatelyFollowUpSuccessfulToolResult(tool);
|
|
801
|
+
}
|
|
790
802
|
async function executeFunctionCalls(args) {
|
|
791
803
|
const functionPromises = args.funcCalls.map(async (func) => {
|
|
792
804
|
throwIfAborted(args.abortSignal, args.dlg);
|
|
@@ -796,19 +808,23 @@ async function executeFunctionCalls(args) {
|
|
|
796
808
|
const preparedInvocationArgs = tool !== undefined ? (0, tool_1.resolveFuncToolInvocationArguments)(tool, argsStr) : null;
|
|
797
809
|
await args.dlg.funcCallRequested(func.id, func.name, argsStr);
|
|
798
810
|
let result;
|
|
811
|
+
let outcome = 'success';
|
|
799
812
|
let rethrowError;
|
|
800
813
|
if (!tool) {
|
|
814
|
+
outcome = 'failure';
|
|
815
|
+
const output = (0, tool_1.toolFailure)(`Tool '${func.name}' not found`);
|
|
801
816
|
result = {
|
|
802
817
|
type: 'func_result_msg',
|
|
803
818
|
id: func.id,
|
|
804
819
|
name: func.name,
|
|
805
|
-
content:
|
|
820
|
+
content: output.content,
|
|
806
821
|
role: 'tool',
|
|
807
822
|
genseq: callGenseq,
|
|
808
823
|
};
|
|
809
824
|
}
|
|
810
825
|
else {
|
|
811
826
|
if (!preparedInvocationArgs || !preparedInvocationArgs.ok) {
|
|
827
|
+
outcome = 'failure';
|
|
812
828
|
const errorText = preparedInvocationArgs?.error ?? 'Arguments could not be prepared for tool invocation';
|
|
813
829
|
log_1.log.warn('kernel-driver rejected function call arguments before execution', undefined, {
|
|
814
830
|
funcName: func.name,
|
|
@@ -819,7 +835,7 @@ async function executeFunctionCalls(args) {
|
|
|
819
835
|
type: 'func_result_msg',
|
|
820
836
|
id: func.id,
|
|
821
837
|
name: func.name,
|
|
822
|
-
content: `Invalid arguments: ${errorText}
|
|
838
|
+
content: (0, tool_1.toolFailure)(`Invalid arguments: ${errorText}`).content,
|
|
823
839
|
role: 'tool',
|
|
824
840
|
genseq: callGenseq,
|
|
825
841
|
};
|
|
@@ -829,40 +845,36 @@ async function executeFunctionCalls(args) {
|
|
|
829
845
|
throwIfAborted(args.abortSignal, args.dlg);
|
|
830
846
|
const output = await tool.call(args.dlg, args.agent, preparedInvocationArgs.args);
|
|
831
847
|
throwIfAborted(args.abortSignal, args.dlg);
|
|
832
|
-
|
|
833
|
-
? { content: output, contentItems: undefined }
|
|
834
|
-
: {
|
|
835
|
-
content: typeof output.content === 'string' ? output.content : String(output),
|
|
836
|
-
contentItems: Array.isArray(output.contentItems)
|
|
837
|
-
? output.contentItems
|
|
838
|
-
: undefined,
|
|
839
|
-
};
|
|
848
|
+
outcome = output.outcome;
|
|
840
849
|
result = {
|
|
841
850
|
type: 'func_result_msg',
|
|
842
851
|
id: func.id,
|
|
843
852
|
name: func.name,
|
|
844
|
-
content:
|
|
845
|
-
contentItems:
|
|
853
|
+
content: output.content,
|
|
854
|
+
contentItems: Array.isArray(output.contentItems) ? [...output.contentItems] : undefined,
|
|
846
855
|
role: 'tool',
|
|
847
856
|
genseq: callGenseq,
|
|
848
857
|
};
|
|
849
858
|
}
|
|
850
859
|
catch (err) {
|
|
860
|
+
outcome = 'failure';
|
|
851
861
|
const errText = err instanceof Error ? `${err.name}: ${err.message}` : String(err);
|
|
862
|
+
const failureOutput = (0, tool_1.toolFailure)(`Function '${func.name}' execution failed: ${errText}`);
|
|
852
863
|
result = {
|
|
853
864
|
type: 'func_result_msg',
|
|
854
865
|
id: func.id,
|
|
855
866
|
name: func.name,
|
|
856
|
-
content:
|
|
867
|
+
content: failureOutput.content,
|
|
857
868
|
role: 'tool',
|
|
858
869
|
genseq: callGenseq,
|
|
859
870
|
};
|
|
860
871
|
if (args.abortSignal?.aborted || err instanceof KernelDriverInterruptedError) {
|
|
872
|
+
const interruptedOutput = (0, tool_1.toolFailure)(`Function '${func.name}' interrupted before completion: ${errText}`);
|
|
861
873
|
result = {
|
|
862
874
|
type: 'func_result_msg',
|
|
863
875
|
id: func.id,
|
|
864
876
|
name: func.name,
|
|
865
|
-
content:
|
|
877
|
+
content: interruptedOutput.content,
|
|
866
878
|
role: 'tool',
|
|
867
879
|
genseq: callGenseq,
|
|
868
880
|
};
|
|
@@ -875,14 +887,14 @@ async function executeFunctionCalls(args) {
|
|
|
875
887
|
if (rethrowError !== undefined) {
|
|
876
888
|
throw rethrowError;
|
|
877
889
|
}
|
|
878
|
-
return result;
|
|
890
|
+
return { outcome, result };
|
|
879
891
|
});
|
|
880
892
|
return await Promise.all(functionPromises);
|
|
881
893
|
}
|
|
882
894
|
async function executeFunctionRound(args) {
|
|
883
895
|
if (args.funcCalls.length === 0) {
|
|
884
896
|
return {
|
|
885
|
-
|
|
897
|
+
hasImmediateFollowupToolCalls: false,
|
|
886
898
|
shouldStopAfterReplyTool: false,
|
|
887
899
|
pairedMessages: [],
|
|
888
900
|
tellaskToolOutputs: [],
|
|
@@ -910,13 +922,25 @@ async function executeFunctionRound(args) {
|
|
|
910
922
|
callbacks: args.callbacks,
|
|
911
923
|
});
|
|
912
924
|
throwIfAborted(args.abortSignal, args.dlg);
|
|
913
|
-
const
|
|
925
|
+
const genericExecutions = await executeFunctionCalls({
|
|
914
926
|
dlg: args.dlg,
|
|
915
927
|
agent: args.agent,
|
|
916
928
|
agentTools: args.agentTools,
|
|
917
929
|
funcCalls: tellaskRound.normalCalls,
|
|
918
930
|
abortSignal: args.abortSignal,
|
|
919
931
|
});
|
|
932
|
+
const funcToolByName = new Map(args.agentTools
|
|
933
|
+
.filter((tool) => tool.type === 'func')
|
|
934
|
+
.map((tool) => [tool.name, tool]));
|
|
935
|
+
const genericOutcomeByCallId = new Map(genericExecutions.map((execution) => [execution.result.id, execution.outcome]));
|
|
936
|
+
const hasImmediateFollowupToolCalls = tellaskRound.normalCalls.some((call) => {
|
|
937
|
+
const tool = funcToolByName.get(call.name);
|
|
938
|
+
const outcome = genericOutcomeByCallId.get(call.id);
|
|
939
|
+
if (outcome === undefined) {
|
|
940
|
+
throw new Error(`kernel-driver function outcome invariant violation: missing outcome for call id '${call.id}' (${call.name})`);
|
|
941
|
+
}
|
|
942
|
+
return shouldImmediatelyFollowUpToolOutcome(tool, outcome);
|
|
943
|
+
});
|
|
920
944
|
const resultByCallId = new Map();
|
|
921
945
|
const register = (result) => {
|
|
922
946
|
const existing = resultByCallId.get(result.id);
|
|
@@ -928,8 +952,8 @@ async function executeFunctionRound(args) {
|
|
|
928
952
|
for (const result of tellaskRound.tellaskResults) {
|
|
929
953
|
register(result);
|
|
930
954
|
}
|
|
931
|
-
for (const
|
|
932
|
-
register(result);
|
|
955
|
+
for (const execution of genericExecutions) {
|
|
956
|
+
register(execution.result);
|
|
933
957
|
}
|
|
934
958
|
const pairedMessages = [];
|
|
935
959
|
const tellaskCallMsgById = new Map(tellaskRound.tellaskCallMessages.map((msg) => [msg.id, msg]));
|
|
@@ -961,7 +985,7 @@ async function executeFunctionRound(args) {
|
|
|
961
985
|
throw new Error(`kernel-driver function result invariant violation: missing result for call id '${call.id}' (${call.name})`);
|
|
962
986
|
}
|
|
963
987
|
return {
|
|
964
|
-
|
|
988
|
+
hasImmediateFollowupToolCalls,
|
|
965
989
|
shouldStopAfterReplyTool: tellaskRound.shouldStopAfterReplyTool,
|
|
966
990
|
pairedMessages,
|
|
967
991
|
tellaskToolOutputs: [...tellaskRound.toolOutputs],
|
|
@@ -1900,19 +1924,18 @@ async function driveDialogStreamCore(dlg, callbacks, humanPrompt, driveOptions)
|
|
|
1900
1924
|
// Tool execution may have created pending Q4H/subdialogs mid-round. Respect the
|
|
1901
1925
|
// dialog's actual suspension state here so auto-continue is decided in one place.
|
|
1902
1926
|
const suspensionAfterToolRound = await dlg.getSuspensionStatus({
|
|
1903
|
-
allowPendingSubdialogs: routed.
|
|
1927
|
+
allowPendingSubdialogs: routed.hasImmediateFollowupToolCalls,
|
|
1904
1928
|
});
|
|
1905
1929
|
if (!suspensionAfterToolRound.canDrive) {
|
|
1906
1930
|
await resetDiligenceBudgetAfterQ4H(dlg, team);
|
|
1907
1931
|
break;
|
|
1908
1932
|
}
|
|
1909
|
-
//
|
|
1910
|
-
// LLM
|
|
1911
|
-
// transcript/context inputs and therefore must not
|
|
1912
|
-
|
|
1913
|
-
|
|
1914
|
-
|
|
1915
|
-
if (!shouldContinue) {
|
|
1933
|
+
// Start an immediate post-tool generation only when this round produced tool outputs that
|
|
1934
|
+
// warrant same-drive LLM reaction right away. Provider-native side-channel UI events are
|
|
1935
|
+
// meaningful output, but they are not transcript/context inputs and therefore must not
|
|
1936
|
+
// trigger another immediate generation round by themselves.
|
|
1937
|
+
const shouldStartImmediatePostToolGeneration = routed.hasImmediateFollowupToolCalls || routed.tellaskToolOutputs.length > 0;
|
|
1938
|
+
if (!shouldStartImmediatePostToolGeneration) {
|
|
1916
1939
|
const healthFirst = await maybeContinueWithHealthPromptBeforeDiligence({
|
|
1917
1940
|
dlg,
|
|
1918
1941
|
providerCfg,
|
|
@@ -1939,7 +1962,7 @@ async function driveDialogStreamCore(dlg, callbacks, humanPrompt, driveOptions)
|
|
|
1939
1962
|
}
|
|
1940
1963
|
break;
|
|
1941
1964
|
}
|
|
1942
|
-
if (
|
|
1965
|
+
if (shouldStartImmediatePostToolGeneration) {
|
|
1943
1966
|
continue;
|
|
1944
1967
|
}
|
|
1945
1968
|
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import type { LanguageCode } from '@longrun-ai/kernel/types/language';
|
|
2
2
|
import type { DialogFbrState } from '@longrun-ai/kernel/types/storage';
|
|
3
|
-
import type
|
|
3
|
+
import { type FuncTool } from '../../tool';
|
|
4
4
|
import type { ChatMessage } from '../client';
|
|
5
5
|
export declare const FBR_LOW_NOISE_CONCLUSION_TOOL_NAME = "presentLowNoiseHighlyInformativeConclusion";
|
|
6
6
|
export declare const FBR_UNREASONABLE_SITUATION_TOOL_NAME = "presentUnreasonableSituation";
|
|
@@ -16,6 +16,7 @@ exports.advanceFbrState = advanceFbrState;
|
|
|
16
16
|
exports.buildFbrPromptForState = buildFbrPromptForState;
|
|
17
17
|
const fbr_body_1 = require("../../runtime/fbr-body");
|
|
18
18
|
const inter_dialog_format_1 = require("../../runtime/inter-dialog-format");
|
|
19
|
+
const tool_1 = require("../../tool");
|
|
19
20
|
exports.FBR_LOW_NOISE_CONCLUSION_TOOL_NAME = 'presentLowNoiseHighlyInformativeConclusion';
|
|
20
21
|
exports.FBR_UNREASONABLE_SITUATION_TOOL_NAME = 'presentUnreasonableSituation';
|
|
21
22
|
function buildFbrConclusionToolDescription(args) {
|
|
@@ -40,7 +41,7 @@ function extractFbrConclusionToolArgs(rawArgs) {
|
|
|
40
41
|
return { content: normalized };
|
|
41
42
|
}
|
|
42
43
|
async function callFbrConclusionTool(_dlg, _caller, rawArgs) {
|
|
43
|
-
return extractFbrConclusionToolArgs(rawArgs).content;
|
|
44
|
+
return (0, tool_1.toolSuccess)(extractFbrConclusionToolArgs(rawArgs).content);
|
|
44
45
|
}
|
|
45
46
|
function buildFbrConclusionTools(language) {
|
|
46
47
|
return [
|