@cadraos/sdk 0.3.14-p46.4 → 0.3.15
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +104 -53
- package/dist/ai-functions/react/index.cjs +176 -0
- package/dist/ai-functions/react/index.cjs.map +1 -0
- package/dist/ai-functions/react/index.d.cts +129 -0
- package/dist/ai-functions/react/index.d.ts +129 -0
- package/dist/ai-functions/react/index.js +153 -0
- package/dist/ai-functions/react/index.js.map +1 -0
- package/dist/ai-functions/server/index.cjs +296 -0
- package/dist/ai-functions/server/index.cjs.map +1 -0
- package/dist/ai-functions/server/index.d.cts +334 -0
- package/dist/ai-functions/server/index.d.ts +334 -0
- package/dist/ai-functions/server/index.js +284 -0
- package/dist/ai-functions/server/index.js.map +1 -0
- package/dist/chat/index.cjs +303 -17
- package/dist/chat/index.cjs.map +1 -1
- package/dist/chat/index.d.cts +211 -0
- package/dist/chat/index.d.ts +211 -0
- package/dist/chat/index.js +303 -17
- package/dist/chat/index.js.map +1 -1
- package/dist/index.cjs +225 -3
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +279 -1
- package/dist/index.d.ts +279 -1
- package/dist/index.js +219 -4
- package/dist/index.js.map +1 -1
- package/dist/kanban/index.cjs +218 -3
- package/dist/kanban/index.cjs.map +1 -1
- package/dist/kanban/index.d.cts +211 -0
- package/dist/kanban/index.d.ts +211 -0
- package/dist/kanban/index.js +218 -3
- package/dist/kanban/index.js.map +1 -1
- package/dist/teams/index.cjs +218 -3
- package/dist/teams/index.cjs.map +1 -1
- package/dist/teams/index.d.cts +211 -0
- package/dist/teams/index.d.ts +211 -0
- package/dist/teams/index.js +218 -3
- package/dist/teams/index.js.map +1 -1
- package/package.json +21 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../src/ai-functions/server/slots.ts","../../../src/ai-functions/server/classify.ts"],"names":[],"mappings":";AAwBO,IAAM,mBAAA,GAAN,cAAkC,KAAA,CAAM;AAAA,EACpC,IAAA;AAAA,EACA,OAAA;AAAA,EACT,WAAA,CAAY,IAAA,EAAc,OAAA,EAAiB,OAAA,EAAiB;AAC1D,IAAA,KAAA,CAAM,OAAO,CAAA;AACb,IAAA,IAAA,CAAK,IAAA,GAAO,qBAAA;AACZ,IAAA,IAAA,CAAK,IAAA,GAAO,IAAA;AACZ,IAAA,IAAA,CAAK,OAAA,GAAU,OAAA;AAAA,EACjB;AACF;AAGO,IAAM,wBAAA,GAAN,cAAuC,mBAAA,CAAoB;AAAA,EAChE,YAAY,OAAA,EAAiB;AAC3B,IAAA,KAAA,CAAM,YAAA,EAAc,OAAA,EAAS,CAAA,kBAAA,EAAqB,OAAO,CAAA,6BAAA,CAA+B,CAAA;AACxF,IAAA,IAAA,CAAK,IAAA,GAAO,0BAAA;AAAA,EACd;AACF;AAGO,IAAM,0BAAA,GAAN,cAAyC,mBAAA,CAAoB;AAAA,EAClE,YAAY,OAAA,EAAiB;AAC3B,IAAA,KAAA,CAAM,cAAA,EAAgB,OAAA,EAAS,CAAA,0BAAA,EAA6B,OAAO,CAAA,EAAA,CAAI,CAAA;AACvE,IAAA,IAAA,CAAK,IAAA,GAAO,4BAAA;AAAA,EACd;AACF;AAGO,IAAM,+BAAA,GAAN,cAA8C,mBAAA,CAAoB;AAAA,EAC9D,WAAA;AAAA,EACA,MAAA;AAAA,EACT,WAAA,CAAY,OAAA,EAAiB,WAAA,EAAqB,MAAA,EAAqC;AACrF,IAAA,KAAA;AAAA,MACE,sBAAA;AAAA,MACA,OAAA;AAAA,MACA,CAAA,CAAA,EAAI,WAAW,CAAA,qBAAA,EAAwB,OAAO,CAAA,GAAA,CAAA,GAAQ,MAAA,CAAO,GAAA,CAAI,CAAC,CAAA,KAAM,CAAA,CAAE,OAAO,CAAA,CAAE,KAAK,IAAI;AAAA,KAC9F;AACA,IAAA,IAAA,CAAK,IAAA,GAAO,iCAAA;AACZ,IAAA,IAAA,CAAK,WAAA,GAAc,WAAA;AACnB,IAAA,IAAA,CAAK,MAAA,GAAS,MAAA;AAAA,EAChB;AACF;AAIA,IAAM,WAAA,GAAc,wBAAA;AAOb,SAAS,sBAAiE,KAAA,EAAa;AAC5F,EAAA,MAAM,IAAA,uBAAW,GAAA,EAAY;AAC7B,EAAA,KAAA,MAAW,QAAQ,KAAA,EAAO;AACxB,IAAA,IAAI,CAAC,WAAA,CAAY,IAAA,CAAK,IAAA,CAAK,GAAG,CAAA,EAAG;AAC/B,MAAA,MAAM,IAAI,KAAA,CAAM,CAAA,8BAAA,EAAiC,IAAA,CAAK,GAAG,CAAA,0CAAA,CAAuC,CAAA;AAAA,IAClG;AACA,IAAA,IAAI,IAAA,CAAK,GAAA,CAAI,IAAA,CAAK,GAAG,CAAA,EAAG,MAAM,IAAI,KAAA,CAAM,CAAA,gCAAA,EAAmC,IAAA,CAAK,GAAG,CAAA,EAAA,CAAI,CAAA;AACvF,IAAA,IAAA,CAAK,GAAA,CAAI,KAAK,GAAG,CAAA;AACjB,IAAA,MAAM,KAAA,uBAAY,GAAA,EAAY;AAC9B,IAAA,KAAA,MAAW,CAAA,IAAK,KAAK,UAAA,EAAY;AAC/B,MAAA,IAAI,CAAC,CAAA,CAAE,IAAA,IAAQ,MAAM,GAAA,CAAI,CAAA,CAAE,IAAI,CAAA,EAAG;AAChC,QAAA,MAAM,IAAI,MAAM,CAAA,MAAA,EAAS,IAAA,CAAK,GAAG,CAAA,kDAAA,EAAqD,CAAA,CAAE,IAAI,CAAA,GAAA,CAAK,CAAA;AAAA,MACnG;AACA,MAAA,KAAA,CAAM,GAAA,CAAI,EAAE,IAAI,CAAA;AAChB,MAAA,IAAI,CAAA,CAAE,SAAS,MAAA,KAAW,CAAC,EAAE,OAAA,IAAW,CAAA,CAAE,OAAA,CAAQ,MAAA,KAAW,CAAA,CAAA,EAAI;AAC/D,QAAA,MAAM,IAAI,MAAM,CAAA,MAAA,EAAS,IAAA,CAAK,GAAG,CAAA,mBAAA,EAAsB,CAAA,CAAE,IAAI,CAAA,gBAAA,CAAkB,CAAA;AAAA,MACjF;AAAA,IACF;AAAA,EACF;AACA,EAAA,OAAO,MAAA,CAAO,OAAO,KAAK,CAAA;AAC5B;AAKO,SAAS,2BAA2B,GAAA,EAA4C;AACrF,EAAA,IAAI,KAAA,GAAQ,GAAA;AACZ,EAAA,IAAI,OAAO,UAAU,QAAA,EAAU;AAC7B,IAAA,MAAM,CAAA,GAAI,MAAM,IAAA,EAAK;AACrB,IAAA,IAAI,CAAC,CAAA,CAAE,UAAA,CAAW,GAAG,GAAG,OAAO,IAAA;AAC/B,IAAA,IAAI;AACF,MAAA,KAAA,GAAQ,IAAA,CAAK,MAAM,CAAC,CAAA;AAAA,IACtB,CAAA,CAAA,MAAQ;AACN,MAAA,OAAO,IAAA;AAAA,IACT;AAAA,EACF;AACA,EAAA,IAAI,KAAA,IAAS,OAAO,KAAA,KAAU,QAAA,EAAU;AACtC,IAAA,MAAM,KAAM,KAAA,CAAoC,WAAA;AAChD,IAAA,IAAI,OAAO,EAAA,KAAO,QAAA,IAAY,EAAA,CAAG,IAAA,EAAK,EAAG,OAAO,EAAE,WAAA,EAAa,EAAA,CAAG,IAAA,EAAK,EAAE;AAAA,EAC3E;AACA,EAAA,OAAO,IAAA;AACT;AA0BO,SAAS,6BACd,OAAA,EACwB;AACxB,EAAA,MAAM,EAAE,OAAM,GAAI,OAAA;AAClB,EAAA,MAAM,KAAA,GAAQ,QAAQ,KAAA,IAAS,GAAA;AAC/B,EAAA,MAAM,KAAA,uBAAY,GAAA,EAAwE;AAE1F,EAAA,OAAO;AAAA,IACL,MAAM,IAAI,GAAA,EAAK;AACb,MAAA,MAAM,GAAA,GAAM,KAAK,GAAA,EAAI;AACrB,MAAA,MAAM,GAAA,GAAM,KAAA,CAAM,GAAA,CAAI,GAAG,CAAA;AACzB,MAAA,IAAI,GAAA,IAAO,GAAA,CAAI,SAAA,GAAY,GAAA,SAAY,GAAA,CAAI,KAAA;AAC3C,MAAA,MAAM,QAAQ,0BAAA,CAA2B,MAAM,KAAA,CAAM,GAAA,CAAI,GAAG,CAAC,CAAA;AAC7D,MAAA,KAAA,CAAM,IAAI,GAAA,EAAK,EAAE,OAAO,SAAA,EAAW,GAAA,GAAM,OAAO,CAAA;AAChD,MAAA,OAAO,KAAA;AAAA,IACT,CAAA;AAAA,IACA,MAAM,GAAA,CAAI,GAAA,EAAK,OAAA,EAAS;AACtB,MAAA,MAAM,MAAM,GAAA,CAAI,GAAA,EAAK,EAAE,WAAA,EAAa,OAAA,CAAQ,aAAa,CAAA;AACzD,MAAA,KAAA,CAAM,OAAO,GAAG,CAAA;AAAA,IAClB,CAAA;AAAA,IACA,MAAM,OAAO,GAAA,EAAK;AAChB,MAAA,MAAM,KAAA,CAAM,OAAO,GAAG,CAAA;AACtB,MAAA,KAAA,CAAM,OAAO,GAAG,CAAA;AAAA,IAClB,CAAA;AAAA,IACA,MAAM,IAAA,GAAO;AACX,MAAA,MAAM,IAAA,GAAO,MAAM,KAAA,CAAM,IAAA,EAAK;AAC9B,MAAA,MAAM,GAAA,uBAAU,GAAA,EAAmC;AACnD,MAAA,KAAA,MAAW,OAAO,IAAA,EAAM;AACtB,QAAA,MAAM,CAAA,GAAI,0BAAA,CAA2B,GAAA,CAAI,KAAK,CAAA;AAC9C,QAAA,IAAI,CAAA,EAAG,GAAA,CAAI,GAAA,CAAI,GAAA,CAAI,KAAK,CAAC,CAAA;AAAA,MAC3B;AACA,MAAA,OAAO,GAAA;AAAA,IACT,CAAA;AAAA,IACA,WAAW,GAAA,EAAK;AACd,MAAA,IAAI,GAAA,EAAK,KAAA,CAAM,MAAA,CAAO,GAAG,CAAA;AAAA,iBACd,KAAA,EAAM;AAAA,IACnB;AAAA,GACF;AACF;AAKA,IAAM,kBAAA,GAAsD,EAAE,MAAA,EAAQ,GAAA,EAAM,MAAM,IAAA,EAAM;AASjF,SAAS,gCAAA,CACd,MACA,UAAA,EAC6B;AAC7B,EAAA,MAAM,SAAsC,EAAC;AAE7C,EAAA,IAAI,UAAA,CAAW,UAAA,KAAe,IAAA,CAAK,UAAA,EAAY;AAC7C,IAAA,MAAA,CAAO,IAAA,CAAK;AAAA,MACV,IAAA,EAAM,aAAA;AAAA,MACN,SAAS,CAAA,QAAA,EAAW,UAAA,CAAW,UAAU,CAAA,mBAAA,EAAsB,KAAK,UAAU,CAAA;AAAA,KAC/E,CAAA;AAAA,EACH;AAEA,EAAA,MAAM,QAAA,GAAW,IAAI,GAAA,CAAI,UAAA,CAAW,UAAA,CAAW,GAAA,CAAI,CAAC,CAAA,KAAM,CAAC,CAAA,CAAE,IAAA,EAAM,CAAC,CAAC,CAAC,CAAA;AACtE,EAAA,MAAM,UAAA,GAAa,IAAI,GAAA,CAAI,IAAA,CAAK,UAAA,CAAW,GAAA,CAAI,CAAC,CAAA,KAAM,CAAC,CAAA,CAAE,IAAA,EAAM,CAAC,CAAC,CAAC,CAAA;AAElE,EAAA,KAAA,MAAW,EAAA,IAAM,KAAK,UAAA,EAAY;AAChC,IAAA,MAAM,EAAA,GAAK,QAAA,CAAS,GAAA,CAAI,EAAA,CAAG,IAAI,CAAA;AAC/B,IAAA,IAAI,CAAC,EAAA,EAAI;AACP,MAAA,MAAA,CAAO,IAAA,CAAK,EAAE,IAAA,EAAM,mBAAA,EAAqB,SAAA,EAAW,EAAA,CAAG,IAAA,EAAM,OAAA,EAAS,CAAA,kBAAA,EAAqB,EAAA,CAAG,IAAI,CAAA,CAAA,CAAA,EAAK,CAAA;AACvG,MAAA;AAAA,IACF;AACA,IAAA,IAAI,EAAA,CAAG,IAAA,KAAS,EAAA,CAAG,IAAA,EAAM;AACvB,MAAA,MAAA,CAAO,IAAA,CAAK;AAAA,QACV,IAAA,EAAM,gBAAA;AAAA,QACN,WAAW,EAAA,CAAG,IAAA;AAAA,QACd,OAAA,EAAS,cAAc,EAAA,CAAG,IAAI,QAAQ,EAAA,CAAG,IAAI,CAAA,kBAAA,EAAqB,EAAA,CAAG,IAAI,CAAA;AAAA,OAC1E,CAAA;AACD,MAAA;AAAA,IACF;AACA,IAAA,IAAI,EAAA,CAAG,OAAA,IAAW,EAAA,CAAG,OAAA,CAAQ,SAAS,CAAA,EAAG;AACvC,MAAA,MAAM,OAAO,IAAI,GAAA,CAAI,EAAA,CAAG,OAAA,IAAW,EAAE,CAAA;AACrC,MAAA,MAAM,OAAA,GAAU,EAAA,CAAG,OAAA,CAAQ,MAAA,CAAO,CAAC,MAAM,CAAC,IAAA,CAAK,GAAA,CAAI,CAAC,CAAC,CAAA;AACrD,MAAA,IAAI,OAAA,CAAQ,SAAS,CAAA,EAAG;AACtB,QAAA,MAAA,CAAO,IAAA,CAAK;AAAA,UACV,IAAA,EAAM,SAAA;AAAA,UACN,WAAW,EAAA,CAAG,IAAA;AAAA,UACd,OAAA,EAAS,CAAA,WAAA,EAAc,EAAA,CAAG,IAAI,qBAAqB,OAAA,CAAQ,GAAA,CAAI,CAAC,CAAA,KAAM,IAAI,CAAC,CAAA,CAAA,CAAG,CAAA,CAAE,IAAA,CAAK,IAAI,CAAC,CAAA;AAAA,SAC3F,CAAA;AAAA,MACH;AAAA,IACF;AACA,IAAA,IAAI,OAAO,GAAG,SAAA,KAAc,QAAA,KAAa,GAAG,IAAA,KAAS,QAAA,IAAY,EAAA,CAAG,IAAA,KAAS,MAAA,CAAA,EAAS;AACpF,MAAA,MAAM,SAAA,GAAY,EAAA,CAAG,SAAA,IAAa,kBAAA,CAAmB,GAAG,IAAI,CAAA;AAC5D,MAAA,IAAI,OAAO,SAAA,KAAc,QAAA,IAAY,SAAA,GAAY,GAAG,SAAA,EAAW;AAC7D,QAAA,MAAA,CAAO,IAAA,CAAK;AAAA,UACV,IAAA,EAAM,YAAA;AAAA,UACN,WAAW,EAAA,CAAG,IAAA;AAAA,UACd,OAAA,EAAS,cAAc,EAAA,CAAG,IAAI,YAAY,SAAS,CAAA,+BAAA,EAAkC,GAAG,SAAS,CAAA;AAAA,SAClG,CAAA;AAAA,MACH;AAAA,IACF;AAAA,EACF;AAEA,EAAA,KAAA,MAAW,EAAA,IAAM,WAAW,UAAA,EAAY;AACtC,IAAA,IAAI,CAAC,GAAG,QAAA,EAAU;AAClB,IAAA,MAAM,EAAA,GAAK,UAAA,CAAW,GAAA,CAAI,EAAA,CAAG,IAAI,CAAA;AACjC,IAAA,IAAI,CAAC,EAAA,IAAM,CAAC,EAAA,CAAG,QAAA,EAAU;AACvB,MAAA,MAAA,CAAO,IAAA,CAAK;AAAA,QACV,IAAA,EAAM,oBAAA;AAAA,QACN,WAAW,EAAA,CAAG,IAAA;AAAA,QACd,OAAA,EAAS,KACL,CAAA,UAAA,EAAa,EAAA,CAAG,IAAI,CAAA,wCAAA,CAAA,GACpB,CAAA,UAAA,EAAa,GAAG,IAAI,CAAA,+BAAA;AAAA,OACzB,CAAA;AAAA,IACH;AAAA,EACF;AAEA,EAAA,OAAO,EAAE,UAAA,EAAY,MAAA,CAAO,MAAA,KAAW,GAAG,MAAA,EAAO;AACnD;AAqBA,SAAS,QAAA,CAAS,OAAkC,GAAA,EAA6B;AAC/E,EAAA,MAAM,OAAO,KAAA,CAAM,IAAA,CAAK,CAAC,CAAA,KAAM,CAAA,CAAE,QAAQ,GAAG,CAAA;AAC5C,EAAA,IAAI,CAAC,IAAA,EAAM,MAAM,IAAI,2BAA2B,GAAG,CAAA;AACnD,EAAA,OAAO,IAAA;AACT;AAEA,SAAS,SAAS,CAAA,EAA+C;AAC/D,EAAA,OAAO,EAAE,aAAa,CAAA,CAAE,WAAA,EAAa,OAAO,CAAA,CAAE,KAAA,EAAO,WAAA,EAAa,CAAA,CAAE,WAAA,EAAY;AAClF;AASO,SAAS,6BAA6B,IAAA,EAAkD;AAC7F,EAAA,MAAM,EAAE,MAAA,EAAQ,KAAA,EAAO,QAAA,EAAS,GAAI,IAAA;AAEpC,EAAA,OAAO;AAAA,IACL,MAAM,SAAA,GAAY;AAChB,MAAA,MAAM,CAAC,SAAA,EAAW,QAAQ,CAAA,GAAI,MAAM,OAAA,CAAQ,GAAA,CAAI,CAAC,MAAA,CAAO,YAAY,IAAA,EAAK,EAAG,QAAA,CAAS,IAAA,EAAM,CAAC,CAAA;AAC5F,MAAA,MAAM,KAAA,GAAQ,IAAI,GAAA,CAAI,SAAA,CAAU,GAAA,CAAI,CAAC,CAAA,KAAM,CAAC,CAAA,CAAE,WAAA,EAAa,CAAC,CAAC,CAAC,CAAA;AAE9D,MAAA,OAAO,KAAA,CAAM,GAAA,CAAI,CAAC,IAAA,KAA4B;AAC5C,QAAA,MAAM,OAAA,GAAU,QAAA,CAAS,GAAA,CAAI,IAAA,CAAK,GAAG,CAAA,IAAK,IAAA;AAC1C,QAAA,MAAM,QAAQ,OAAA,GAAU,KAAA,CAAM,GAAA,CAAI,OAAA,CAAQ,WAAW,CAAA,GAAI,MAAA;AACzD,QAAA,IAAI,MAAA,GAA6C,IAAA;AACjD,QAAA,IAAI,OAAA,EAAS;AACX,UAAA,MAAA,GAAS,KAAA,GACL,gCAAA,CAAiC,IAAA,EAAM,KAAK,CAAA,GAC5C;AAAA,YACE,UAAA,EAAY,KAAA;AAAA,YACZ,MAAA,EAAQ;AAAA,cACN;AAAA,gBACE,IAAA,EAAM,sBAAA;AAAA,gBACN,OAAA,EAAS,CAAA,CAAA,EAAI,OAAA,CAAQ,WAAW,CAAA,sCAAA;AAAA;AAClC;AACF,WACF;AAAA,QACN;AACA,QAAA,OAAO;AAAA,UACL,KAAK,IAAA,CAAK,GAAA;AAAA,UACV,OAAO,IAAA,CAAK,KAAA;AAAA,UACZ,OAAA,EAAS,KAAK,OAAA,IAAW,IAAA;AAAA,UACzB,YAAY,IAAA,CAAK,UAAA;AAAA,UACjB,UAAA,EAAY,KAAK,UAAA,CAAW,GAAA,CAAI,CAAC,CAAA,MAAO,EAAE,GAAG,CAAA,EAAE,CAAE,CAAA;AAAA,UACjD,OAAA;AAAA,UACA,aAAA,EAAe,KAAA,GAAQ,EAAE,GAAG,QAAA,CAAS,KAAK,CAAA,EAAG,UAAA,EAAY,KAAA,CAAM,UAAA,EAAW,GAAI,IAAA;AAAA,UAC9E,MAAA;AAAA,UACA,OAAA,EAAS,SAAA,CACN,MAAA,CAAO,CAAC,CAAA,KAAM,gCAAA,CAAiC,IAAA,EAAM,CAAC,CAAA,CAAE,UAAU,CAAA,CAClE,GAAA,CAAI,QAAQ;AAAA,SACjB;AAAA,MACF,CAAC,CAAA;AAAA,IACH,CAAA;AAAA,IAEA,MAAM,OAAA,CAAQ,EAAE,GAAA,EAAK,aAAY,EAAG;AAClC,MAAA,MAAM,IAAA,GAAO,QAAA,CAAS,KAAA,EAAO,GAAG,CAAA;AAChC,MAAA,MAAM,UAAA,GAAa,MAAM,MAAA,CAAO,WAAA,CAAY,IAAI,WAAW,CAAA;AAC3D,MAAA,MAAM,OAAA,GAAU,gCAAA,CAAiC,IAAA,EAAM,UAAU,CAAA;AACjE,MAAA,IAAI,CAAC,QAAQ,UAAA,EAAY;AACvB,QAAA,MAAM,IAAI,+BAAA,CAAgC,GAAA,EAAK,WAAA,EAAa,QAAQ,MAAM,CAAA;AAAA,MAC5E;AACA,MAAA,MAAM,QAAA,CAAS,GAAA,CAAI,GAAA,EAAK,EAAE,aAAa,CAAA;AACvC,MAAA,OAAO,EAAE,GAAA,EAAK,WAAA,EAAa,WAAA,EAAa,WAAW,WAAA,EAAY;AAAA,IACjE,CAAA;AAAA,IAEA,MAAM,SAAA,CAAU,EAAE,GAAA,EAAI,EAAG;AACvB,MAAA,QAAA,CAAS,OAAO,GAAG,CAAA;AACnB,MAAA,MAAM,QAAA,CAAS,OAAO,GAAG,CAAA;AACzB,MAAA,OAAO,EAAE,GAAA,EAAI;AAAA,IACf,CAAA;AAAA,IAEA,MAAM,cAAc,KAAA,EAAO;AACzB,MAAA,MAAM,SAAA,GAAY,MAAM,MAAA,CAAO,WAAA,CAAY,IAAA,EAAK;AAChD,MAAA,OAAO,KAAA,EAAO,UAAA,GAAa,SAAA,CAAU,MAAA,CAAO,CAAC,MAAM,CAAA,CAAE,UAAA,KAAe,KAAA,CAAM,UAAU,CAAA,GAAI,SAAA;AAAA,IAC1F;AAAA,GACF;AACF;AAMA,eAAsB,OAAA,CACpB,IAAA,EACA,GAAA,EACA,UAAA,EACA,IAAA,EACuC;AACvC,EAAA,QAAA,CAAS,IAAA,CAAK,OAAO,GAAG,CAAA;AACxB,EAAA,MAAM,OAAA,GAAU,MAAM,IAAA,CAAK,QAAA,CAAS,IAAI,GAAG,CAAA;AAC3C,EAAA,IAAI,CAAC,OAAA,EAAS,MAAM,IAAI,yBAAyB,GAAG,CAAA;AACpD,EAAA,OAAO,KAAK,MAAA,CAAO,WAAA,CAAY,IAAa,OAAA,CAAQ,WAAA,EAAa,YAAY,IAAI,CAAA;AACnF;;;ACjXA,SAAS,QAAA,CAAS,QAAiB,GAAA,EAAiC;AAClE,EAAA,IAAI,CAAC,MAAA,IAAU,OAAO,MAAA,KAAW,UAAU,OAAO,MAAA;AAClD,EAAA,MAAM,GAAA,GAAO,OAAmC,GAAG,CAAA;AACnD,EAAA,MAAM,IAAI,OAAO,GAAA,KAAQ,QAAA,GAAW,MAAA,CAAO,GAAG,CAAA,GAAI,GAAA;AAClD,EAAA,OAAO,OAAO,MAAM,QAAA,IAAY,MAAA,CAAO,SAAS,CAAC,CAAA,IAAK,CAAA,IAAK,CAAA,GAAI,CAAA,GAAI,MAAA;AACrE;AAEA,SAAS,QAAA,CAAS,QAAiB,GAAA,EAAiC;AAClE,EAAA,IAAI,CAAC,MAAA,IAAU,OAAO,MAAA,KAAW,UAAU,OAAO,MAAA;AAClD,EAAA,MAAM,GAAA,GAAO,OAAmC,GAAG,CAAA;AACnD,EAAA,OAAO,OAAO,GAAA,KAAQ,QAAA,IAAY,GAAA,GAAM,GAAA,GAAM,MAAA;AAChD;AAMO,SAAS,wBAAwB,KAAA,EAA+C;AACrF,EAAA,MAAM,MAAA,GAAS,QAAA,CAAS,KAAA,EAAO,QAAQ,CAAA;AACvC,EAAA,MAAM,IAAA,GAAO,QAAA,CAAS,KAAA,EAAO,MAAM,CAAA;AACnC,EAAA,MAAM,UAAA,GAAa,QAAA,CAAS,KAAA,EAAO,YAAY,CAAA;AAC/C,EAAA,MAAM,OAAA,GAAU,SAAS,KAAA,EAAO,SAAS,MAAM,OAAO,KAAA,KAAU,WAAW,KAAA,GAAQ,yBAAA,CAAA;AACnF,EAAA,MAAM,UAAU,KAAA,IAAS,OAAO,KAAA,KAAU,QAAA,GAAY,MAAgC,OAAA,GAAU,MAAA;AAEhG,EAAA,MAAM,IAAA,GAAO;AAAA,IACX,GAAI,MAAA,KAAW,MAAA,GAAY,EAAE,MAAA,KAAW,EAAC;AAAA,IACzC,GAAI,UAAA,GAAa,EAAE,UAAA,KAAe,EAAC;AAAA,IACnC;AAAA,GACF;AAEA,EAAA,IAAI,MAAA,KAAW,GAAA,IAAO,IAAA,KAAS,gBAAA,IAAoB,eAAe,cAAA,EAAgB;AAChF,IAAA,MAAM,iBAAA,GACJ,QAAA,CAAS,KAAA,EAAO,YAAY,CAAA,IAAK,QAAA,CAAS,OAAA,EAAS,YAAY,CAAA,IAAK,QAAA,CAAS,OAAA,EAAS,aAAa,CAAA;AACrG,IAAA,OAAO,EAAE,IAAA,EAAM,cAAA,EAAgB,GAAG,IAAA,EAAM,GAAI,iBAAA,KAAsB,MAAA,GAAY,EAAE,iBAAA,EAAkB,GAAI,EAAC,EAAG;AAAA,EAC5G;AACA,EAAA,IAAI,MAAA,KAAW,OAAO,IAAA,KAAS,qBAAA,SAA8B,EAAE,IAAA,EAAM,cAAA,EAAgB,GAAG,IAAA,EAAK;AAC7F,EAAA,IAAI,MAAA,KAAW,OAAO,IAAA,KAAS,oBAAA,SAA6B,EAAE,IAAA,EAAM,WAAA,EAAa,GAAG,IAAA,EAAK;AACzF,EAAA,IAAI,MAAA,KAAW,OAAO,IAAA,KAAS,eAAA,SAAwB,EAAE,IAAA,EAAM,WAAA,EAAa,GAAG,IAAA,EAAK;AACpF,EAAA,IAAI,SAAS,cAAA,IAAkB,IAAA,KAAS,gBAAgB,MAAA,KAAW,GAAA,IAAO,eAAe,SAAA,EAAW;AAClG,IAAA,OAAO,EAAE,IAAA,EAAM,SAAA,EAAW,GAAG,IAAA,EAAK;AAAA,EACpC;AACA,EAAA,IACE,SAAS,cAAA,IACT,MAAA,KAAW,KACV,MAAA,KAAW,MAAA,IAAa,SAAS,WAAA,EAClC;AACA,IAAA,OAAO,EAAE,IAAA,EAAM,SAAA,EAAW,GAAG,IAAA,EAAK;AAAA,EACpC;AACA,EAAA,OAAO,EAAE,IAAA,EAAM,UAAA,EAAY,GAAG,IAAA,EAAK;AACrC","file":"index.js","sourcesContent":["/**\n * Slot catalog, resolver, compatibility and handlers (p93 AIF-017, specs D28).\n *\n * Port of Yobo's app-local `lib/cadra/function-config.ts` semantics (60 s\n * process-local Map cache, cleared on write) MINUS the env fallback: an unset\n * slot is unavailable, never silently served from `process.env`.\n */\n\nimport type { AiFunctionDescriptor, AiFunctionRunResult, AiFunctionRunShorthandOptions, AiFunctionVariables } from '../../types/ai-functions.js';\nimport type {\n AiFunctionSetSlotResult,\n AiFunctionSlot,\n AiFunctionSlotBinding,\n AiFunctionSlotCompatIssue,\n AiFunctionSlotCompatVerdict,\n AiFunctionSlotOption,\n AiFunctionSlotRow,\n AiFunctionSlotStore,\n AiFunctionsClientLike,\n} from './types.js';\n\n// ── errors ──────────────────────────────────────────────────────────────────\n\n/** Base class for slot-module errors. `code` is stable; branch on it, not `instanceof`. */\nexport class AiFunctionSlotError extends Error {\n readonly code: string;\n readonly slotKey: string;\n constructor(code: string, slotKey: string, message: string) {\n super(message);\n this.name = 'AiFunctionSlotError';\n this.code = code;\n this.slotKey = slotKey;\n }\n}\n\n/** `runSlot` on a slot with no binding. No request was sent. */\nexport class AiFunctionSlotUnsetError extends AiFunctionSlotError {\n constructor(slotKey: string) {\n super('slot_unset', slotKey, `AI function slot \"${slotKey}\" is not bound to a function.`);\n this.name = 'AiFunctionSlotUnsetError';\n }\n}\n\n/** A key that is not in the declared catalog. */\nexport class AiFunctionUnknownSlotError extends AiFunctionSlotError {\n constructor(slotKey: string) {\n super('unknown_slot', slotKey, `Unknown AI function slot \"${slotKey}\".`);\n this.name = 'AiFunctionUnknownSlotError';\n }\n}\n\n/** `setSlot` refused: the function's live version does not fit the slot. */\nexport class AiFunctionSlotIncompatibleError extends AiFunctionSlotError {\n readonly functionKey: string;\n readonly issues: AiFunctionSlotCompatIssue[];\n constructor(slotKey: string, functionKey: string, issues: AiFunctionSlotCompatIssue[]) {\n super(\n 'binding_incompatible',\n slotKey,\n `\"${functionKey}\" does not fit slot \"${slotKey}\": ` + issues.map((i) => i.message).join('; ')\n );\n this.name = 'AiFunctionSlotIncompatibleError';\n this.functionKey = functionKey;\n this.issues = issues;\n }\n}\n\n// ── catalog ─────────────────────────────────────────────────────────────────\n\nconst SLOT_KEY_RE = /^[a-z][a-z0-9_]{1,63}$/;\n\n/**\n * Declare the host app's slots. Validates keys (lower_snake, unique) and\n * parameter names, and returns the same array (frozen) so literal key types\n * survive: `runSlot(deps, 'campaign_subject', …)`.\n */\nexport function defineAiFunctionSlots<const T extends readonly AiFunctionSlot[]>(slots: T): T {\n const seen = new Set<string>();\n for (const slot of slots) {\n if (!SLOT_KEY_RE.test(slot.key)) {\n throw new Error(`Invalid AI function slot key \"${slot.key}\" (use lower_snake_case, 2–64 chars).`);\n }\n if (seen.has(slot.key)) throw new Error(`Duplicate AI function slot key \"${slot.key}\".`);\n seen.add(slot.key);\n const names = new Set<string>();\n for (const p of slot.parameters) {\n if (!p.name || names.has(p.name)) {\n throw new Error(`Slot \"${slot.key}\": parameter names must be non-empty and unique (\"${p.name}\").`);\n }\n names.add(p.name);\n if (p.type === 'enum' && (!p.options || p.options.length === 0)) {\n throw new Error(`Slot \"${slot.key}\": enum parameter \"${p.name}\" needs options.`);\n }\n }\n }\n return Object.freeze(slots) as T;\n}\n\n// ── resolver ────────────────────────────────────────────────────────────────\n\n/** Parse a stored value into a binding; anything else is \"unset\". */\nexport function parseAiFunctionSlotBinding(raw: unknown): AiFunctionSlotBinding | null {\n let value = raw;\n if (typeof value === 'string') {\n const t = value.trim();\n if (!t.startsWith('{')) return null;\n try {\n value = JSON.parse(t);\n } catch {\n return null;\n }\n }\n if (value && typeof value === 'object') {\n const fk = (value as { functionKey?: unknown }).functionKey;\n if (typeof fk === 'string' && fk.trim()) return { functionKey: fk.trim() };\n }\n return null;\n}\n\nexport interface AiFunctionSlotResolver {\n /** The binding for `key` (cached for `ttlMs`, including \"unset\"). */\n get(key: string): Promise<AiFunctionSlotBinding | null>;\n /** Store a binding and clear that key's cache. */\n set(key: string, binding: AiFunctionSlotBinding): Promise<void>;\n /** Remove a binding and clear that key's cache. */\n delete(key: string): Promise<void>;\n /** Every stored binding, read fresh from the store (admin view). */\n list(): Promise<Map<string, AiFunctionSlotBinding>>;\n /** Drop one key's cache entry, or all. */\n clearCache(key?: string): void;\n}\n\nexport interface CreateAiFunctionSlotResolverOptions {\n store: AiFunctionSlotStore;\n /** Cache TTL in ms (default 60 000). The cache is per process. */\n ttlMs?: number;\n}\n\n/**\n * Resolve slot → binding with a process-local TTL cache. Writes through this\n * resolver clear the cache so the writing process live-swaps; other processes\n * pick the change up within `ttlMs`.\n */\nexport function createAiFunctionSlotResolver(\n options: CreateAiFunctionSlotResolverOptions\n): AiFunctionSlotResolver {\n const { store } = options;\n const ttlMs = options.ttlMs ?? 60_000;\n const cache = new Map<string, { value: AiFunctionSlotBinding | null; expiresAt: number }>();\n\n return {\n async get(key) {\n const now = Date.now();\n const hit = cache.get(key);\n if (hit && hit.expiresAt > now) return hit.value;\n const value = parseAiFunctionSlotBinding(await store.get(key));\n cache.set(key, { value, expiresAt: now + ttlMs });\n return value;\n },\n async set(key, binding) {\n await store.set(key, { functionKey: binding.functionKey });\n cache.delete(key);\n },\n async delete(key) {\n await store.delete(key);\n cache.delete(key);\n },\n async list() {\n const rows = await store.list();\n const out = new Map<string, AiFunctionSlotBinding>();\n for (const row of rows) {\n const b = parseAiFunctionSlotBinding(row.value);\n if (b) out.set(row.key, b);\n }\n return out;\n },\n clearCache(key) {\n if (key) cache.delete(key);\n else cache.clear();\n },\n };\n}\n\n// ── compatibility (D16 rule on a D27 descriptor) ────────────────────────────\n\n/** Server default maxLength per type when the version sets none (D10). */\nconst DEFAULT_MAX_LENGTH: Partial<Record<string, number>> = { string: 2000, text: 24000 };\n\n/**\n * Does `descriptor` (a function's live version) fit `slot`? Passes iff: same\n * output kind; every slot parameter exists with the same type (`string` ≠\n * `text`); every REQUIRED function parameter is declared by the slot as\n * required; enum options ⊇ the slot's; string/text effective maxLength ≥ the\n * slot's.\n */\nexport function checkAiFunctionSlotCompatibility(\n slot: Pick<AiFunctionSlot, 'outputKind' | 'parameters'>,\n descriptor: Pick<AiFunctionDescriptor, 'outputKind' | 'parameters'>\n): AiFunctionSlotCompatVerdict {\n const issues: AiFunctionSlotCompatIssue[] = [];\n\n if (descriptor.outputKind !== slot.outputKind) {\n issues.push({\n code: 'output_kind',\n message: `returns ${descriptor.outputKind}, the slot expects ${slot.outputKind}`,\n });\n }\n\n const fnParams = new Map(descriptor.parameters.map((p) => [p.name, p]));\n const slotParams = new Map(slot.parameters.map((p) => [p.name, p]));\n\n for (const sp of slot.parameters) {\n const fp = fnParams.get(sp.name);\n if (!fp) {\n issues.push({ code: 'parameter_missing', parameter: sp.name, message: `has no parameter '${sp.name}'` });\n continue;\n }\n if (fp.type !== sp.type) {\n issues.push({\n code: 'parameter_type',\n parameter: sp.name,\n message: `parameter '${sp.name}' is ${fp.type}, the slot passes ${sp.type}`,\n });\n continue;\n }\n if (sp.options && sp.options.length > 0) {\n const have = new Set(fp.options ?? []);\n const missing = sp.options.filter((o) => !have.has(o));\n if (missing.length > 0) {\n issues.push({\n code: 'options',\n parameter: sp.name,\n message: `parameter '${sp.name}' does not accept ${missing.map((m) => `'${m}'`).join(', ')}`,\n });\n }\n }\n if (typeof sp.maxLength === 'number' && (sp.type === 'string' || sp.type === 'text')) {\n const effective = fp.maxLength ?? DEFAULT_MAX_LENGTH[fp.type];\n if (typeof effective === 'number' && effective < sp.maxLength) {\n issues.push({\n code: 'max_length',\n parameter: sp.name,\n message: `parameter '${sp.name}' allows ${effective} characters, the slot may pass ${sp.maxLength}`,\n });\n }\n }\n }\n\n for (const fp of descriptor.parameters) {\n if (!fp.required) continue;\n const sp = slotParams.get(fp.name);\n if (!sp || !sp.required) {\n issues.push({\n code: 'parameter_required',\n parameter: fp.name,\n message: sp\n ? `requires '${fp.name}', which the slot passes only optionally`\n : `requires '${fp.name}', which the slot does not pass`,\n });\n }\n }\n\n return { compatible: issues.length === 0, issues };\n}\n\n// ── handlers ────────────────────────────────────────────────────────────────\n\nexport interface AiFunctionSlotDeps {\n client: AiFunctionsClientLike;\n slots: readonly AiFunctionSlot[];\n resolver: AiFunctionSlotResolver;\n}\n\nexport interface AiFunctionSlotHandlers {\n /** Catalog + binding + live descriptor + compat verdict + compatible choices. */\n listSlots(): Promise<AiFunctionSlotRow[]>;\n /** Bind a slot; refuses an incompatible function (`AiFunctionSlotIncompatibleError`). */\n setSlot(input: { key: string; functionKey: string }): Promise<AiFunctionSetSlotResult>;\n /** Unbind a slot (it becomes unavailable). */\n resetSlot(input: { key: string }): Promise<{ key: string }>;\n /** The org's callable functions, optionally by output kind. */\n listFunctions(input?: { outputKind?: AiFunctionDescriptor['outputKind'] }): Promise<AiFunctionDescriptor[]>;\n}\n\nfunction findSlot(slots: readonly AiFunctionSlot[], key: string): AiFunctionSlot {\n const slot = slots.find((s) => s.key === key);\n if (!slot) throw new AiFunctionUnknownSlotError(key);\n return slot;\n}\n\nfunction toOption(d: AiFunctionDescriptor): AiFunctionSlotOption {\n return { functionKey: d.functionKey, title: d.title, liveVersion: d.liveVersion };\n}\n\n/**\n * Framework-free async handlers. Wrap each in one router entry of the host\n * (tRPC procedure, route handler, …) behind the host's admin permission.\n * Errors from the SDK are rethrown untouched — map them with\n * `classifyAiFunctionError` so a failed catalog read shows as an error, never\n * as an empty list.\n */\nexport function createAiFunctionSlotHandlers(deps: AiFunctionSlotDeps): AiFunctionSlotHandlers {\n const { client, slots, resolver } = deps;\n\n return {\n async listSlots() {\n const [functions, bindings] = await Promise.all([client.aiFunctions.list(), resolver.list()]);\n const byKey = new Map(functions.map((f) => [f.functionKey, f]));\n\n return slots.map((slot): AiFunctionSlotRow => {\n const binding = bindings.get(slot.key) ?? null;\n const bound = binding ? byKey.get(binding.functionKey) : undefined;\n let compat: AiFunctionSlotCompatVerdict | null = null;\n if (binding) {\n compat = bound\n ? checkAiFunctionSlotCompatibility(slot, bound)\n : {\n compatible: false,\n issues: [\n {\n code: 'function_unavailable',\n message: `'${binding.functionKey}' is not published or no longer exists`,\n },\n ],\n };\n }\n return {\n key: slot.key,\n label: slot.label,\n usedFor: slot.usedFor ?? null,\n outputKind: slot.outputKind,\n parameters: slot.parameters.map((p) => ({ ...p })),\n binding,\n boundFunction: bound ? { ...toOption(bound), outputKind: bound.outputKind } : null,\n compat,\n options: functions\n .filter((f) => checkAiFunctionSlotCompatibility(slot, f).compatible)\n .map(toOption),\n };\n });\n },\n\n async setSlot({ key, functionKey }) {\n const slot = findSlot(slots, key);\n const descriptor = await client.aiFunctions.get(functionKey);\n const verdict = checkAiFunctionSlotCompatibility(slot, descriptor);\n if (!verdict.compatible) {\n throw new AiFunctionSlotIncompatibleError(key, functionKey, verdict.issues);\n }\n await resolver.set(key, { functionKey });\n return { key, functionKey, liveVersion: descriptor.liveVersion };\n },\n\n async resetSlot({ key }) {\n findSlot(slots, key);\n await resolver.delete(key);\n return { key };\n },\n\n async listFunctions(input) {\n const functions = await client.aiFunctions.list();\n return input?.outputKind ? functions.filter((f) => f.outputKind === input.outputKind) : functions;\n },\n };\n}\n\n/**\n * Run the function bound to a slot. Unset ⇒ `AiFunctionSlotUnsetError` with no\n * request. Calls use the host's Cadra API key (`public_api`, billed to that org).\n */\nexport async function runSlot<TOutput = unknown>(\n deps: AiFunctionSlotDeps,\n key: string,\n parameters: AiFunctionVariables,\n opts?: AiFunctionRunShorthandOptions\n): Promise<AiFunctionRunResult<TOutput>> {\n findSlot(deps.slots, key);\n const binding = await deps.resolver.get(key);\n if (!binding) throw new AiFunctionSlotUnsetError(key);\n return deps.client.aiFunctions.run<TOutput>(binding.functionKey, parameters, opts);\n}\n","/**\n * Structural SDK-error classifier (p93 AIF-017, specs D28).\n *\n * Reads `status` / `name` / `serverCode` off the thrown value — never\n * `instanceof`: the SDK is often `link:`ed or duplicated in a host bundle, so\n * class identity across module boundaries is a needless failure mode (Yobo\n * `lib/cadra/upstream-error.ts` lesson, F55).\n */\n\nimport type { AiFunctionErrorClassification } from './types.js';\n\nfunction numberAt(source: unknown, key: string): number | undefined {\n if (!source || typeof source !== 'object') return undefined;\n const raw = (source as Record<string, unknown>)[key];\n const n = typeof raw === 'string' ? Number(raw) : raw;\n return typeof n === 'number' && Number.isFinite(n) && n >= 0 ? n : undefined;\n}\n\nfunction stringAt(source: unknown, key: string): string | undefined {\n if (!source || typeof source !== 'object') return undefined;\n const raw = (source as Record<string, unknown>)[key];\n return typeof raw === 'string' && raw ? raw : undefined;\n}\n\n/**\n * Map anything an AI-function call threw to one of\n * `rate_limited | unauthorized | forbidden | not_found | timeout | network | upstream`.\n */\nexport function classifyAiFunctionError(error: unknown): AiFunctionErrorClassification {\n const status = numberAt(error, 'status');\n const name = stringAt(error, 'name');\n const serverCode = stringAt(error, 'serverCode');\n const message = stringAt(error, 'message') ?? (typeof error === 'string' ? error : 'AI function call failed');\n const details = error && typeof error === 'object' ? (error as { details?: unknown }).details : undefined;\n\n const base = {\n ...(status !== undefined ? { status } : {}),\n ...(serverCode ? { serverCode } : {}),\n message,\n };\n\n if (status === 429 || name === 'RateLimitError' || serverCode === 'RATE_LIMITED') {\n const retryAfterSeconds =\n numberAt(error, 'retryAfter') ?? numberAt(details, 'retryAfter') ?? numberAt(details, 'retry_after');\n return { kind: 'rate_limited', ...base, ...(retryAfterSeconds !== undefined ? { retryAfterSeconds } : {}) };\n }\n if (status === 401 || name === 'AuthenticationError') return { kind: 'unauthorized', ...base };\n if (status === 403 || name === 'AuthorizationError') return { kind: 'forbidden', ...base };\n if (status === 404 || name === 'NotFoundError') return { kind: 'not_found', ...base };\n if (name === 'TimeoutError' || name === 'AbortError' || status === 408 || serverCode === 'TIMEOUT') {\n return { kind: 'timeout', ...base };\n }\n if (\n name === 'NetworkError' ||\n status === 0 ||\n (status === undefined && name === 'TypeError')\n ) {\n return { kind: 'network', ...base };\n }\n return { kind: 'upstream', ...base };\n}\n"]}
|
package/dist/chat/index.cjs
CHANGED
|
@@ -75,6 +75,14 @@ var CadraError = class extends Error {
|
|
|
75
75
|
details;
|
|
76
76
|
/** Request ID from server (for debugging) */
|
|
77
77
|
requestId;
|
|
78
|
+
/**
|
|
79
|
+
* The server's own `error.code` exactly as sent on the wire (e.g.
|
|
80
|
+
* `FUNCTION_NOT_PUBLISHED`, `DUPLICATE_REQUEST`, `VARIABLE_TYPE`).
|
|
81
|
+
* Populated by `parseApiError` for EVERY status. `code` keeps its historic
|
|
82
|
+
* per-class values (`conflict`, `server_error`, `validation_error`, …) for
|
|
83
|
+
* compatibility; branch on `serverCode` when you need the precise reason.
|
|
84
|
+
*/
|
|
85
|
+
serverCode;
|
|
78
86
|
constructor(message, code, status, details, requestId) {
|
|
79
87
|
super(message);
|
|
80
88
|
this.name = "CadraError";
|
|
@@ -152,6 +160,12 @@ function parseApiError(status, body, requestId) {
|
|
|
152
160
|
const message = errorBody?.error?.message ?? "An error occurred";
|
|
153
161
|
const code = errorBody?.error?.code ?? "unknown_error";
|
|
154
162
|
const details = errorBody?.error?.details;
|
|
163
|
+
const serverCode = typeof errorBody?.error?.code === "string" ? errorBody.error.code : void 0;
|
|
164
|
+
const error = buildApiError(status, message, code, details, requestId);
|
|
165
|
+
if (serverCode !== void 0) error.serverCode = serverCode;
|
|
166
|
+
return error;
|
|
167
|
+
}
|
|
168
|
+
function buildApiError(status, message, code, details, requestId) {
|
|
155
169
|
switch (status) {
|
|
156
170
|
case 400:
|
|
157
171
|
case 422: {
|
|
@@ -187,6 +201,42 @@ function parseApiError(status, body, requestId) {
|
|
|
187
201
|
}
|
|
188
202
|
}
|
|
189
203
|
|
|
204
|
+
// src/errors/ai-function-errors.ts
|
|
205
|
+
var AiFunctionDuplicateError = class extends ConflictError {
|
|
206
|
+
/** The existing run's execution id. */
|
|
207
|
+
executionId;
|
|
208
|
+
/** The existing run's status (`running`, a terminal status, or `abandoned`). */
|
|
209
|
+
runStatus;
|
|
210
|
+
constructor(message, details, requestId) {
|
|
211
|
+
super(message, details, requestId);
|
|
212
|
+
this.name = "AiFunctionDuplicateError";
|
|
213
|
+
this.serverCode = "DUPLICATE_REQUEST";
|
|
214
|
+
this.executionId = typeof details?.executionId === "string" ? details.executionId : void 0;
|
|
215
|
+
this.runStatus = typeof details?.status === "string" ? details.status : void 0;
|
|
216
|
+
}
|
|
217
|
+
};
|
|
218
|
+
var AiFunctionChargedError = class extends CadraError {
|
|
219
|
+
constructor(source) {
|
|
220
|
+
super(source.message, source.code, source.status, source.details, source.requestId);
|
|
221
|
+
this.name = "AiFunctionChargedError";
|
|
222
|
+
this.serverCode = source.serverCode;
|
|
223
|
+
}
|
|
224
|
+
};
|
|
225
|
+
var AiFunctionParameterError = class extends ValidationError {
|
|
226
|
+
functionKey;
|
|
227
|
+
issues;
|
|
228
|
+
constructor(functionKey, issues) {
|
|
229
|
+
super(
|
|
230
|
+
`Invalid parameters for AI function "${functionKey}": ` + issues.map((i) => `${i.name} (${i.code})`).join(", "),
|
|
231
|
+
issues.map((i) => ({ field: i.name, message: i.code })),
|
|
232
|
+
{ functionKey, issues }
|
|
233
|
+
);
|
|
234
|
+
this.name = "AiFunctionParameterError";
|
|
235
|
+
this.functionKey = functionKey;
|
|
236
|
+
this.issues = issues;
|
|
237
|
+
}
|
|
238
|
+
};
|
|
239
|
+
|
|
190
240
|
// src/utils/retry.ts
|
|
191
241
|
var DEFAULT_RETRY_CONFIG = {
|
|
192
242
|
maxRetries: 3,
|
|
@@ -251,6 +301,10 @@ var HttpClient = class {
|
|
|
251
301
|
constructor(config) {
|
|
252
302
|
this.config = config;
|
|
253
303
|
}
|
|
304
|
+
/** The client-wide request timeout (ms) this client was configured with. */
|
|
305
|
+
get timeoutMs() {
|
|
306
|
+
return this.config.timeout;
|
|
307
|
+
}
|
|
254
308
|
/**
|
|
255
309
|
* Get authorization header value
|
|
256
310
|
*/
|
|
@@ -305,7 +359,8 @@ var HttpClient = class {
|
|
|
305
359
|
headers["Idempotency-Key"] = options.idempotencyKey;
|
|
306
360
|
}
|
|
307
361
|
const controller = new AbortController();
|
|
308
|
-
const
|
|
362
|
+
const timeoutMs = options.timeoutMs ?? this.config.timeout;
|
|
363
|
+
const timeoutId = setTimeout(() => controller.abort(), timeoutMs);
|
|
309
364
|
try {
|
|
310
365
|
const doFetch = this.config.fetch ?? fetch;
|
|
311
366
|
const response = await doFetch(url, {
|
|
@@ -341,7 +396,7 @@ var HttpClient = class {
|
|
|
341
396
|
} catch (error) {
|
|
342
397
|
clearTimeout(timeoutId);
|
|
343
398
|
if (error instanceof Error && error.name === "AbortError") {
|
|
344
|
-
throw new TimeoutError(`Request timed out after ${this.config.timeout}ms`);
|
|
399
|
+
throw new TimeoutError(`Request timed out after ${options.timeoutMs ?? this.config.timeout}ms`);
|
|
345
400
|
}
|
|
346
401
|
if (error instanceof TypeError && error.message.includes("fetch")) {
|
|
347
402
|
throw new NetworkError(`Network error: ${error.message}`);
|
|
@@ -373,7 +428,8 @@ var HttpClient = class {
|
|
|
373
428
|
path,
|
|
374
429
|
body,
|
|
375
430
|
idempotencyKey: options?.idempotencyKey,
|
|
376
|
-
skipRetry: options?.skipRetry
|
|
431
|
+
skipRetry: options?.skipRetry,
|
|
432
|
+
timeoutMs: options?.timeoutMs
|
|
377
433
|
});
|
|
378
434
|
}
|
|
379
435
|
/**
|
|
@@ -1132,6 +1188,10 @@ var ExecutionStreamControllerImpl = class {
|
|
|
1132
1188
|
toolName,
|
|
1133
1189
|
result: data.result,
|
|
1134
1190
|
durationMs: data.durationMs ?? 0,
|
|
1191
|
+
// CAD-243: pass the producer's failure verdict through.
|
|
1192
|
+
...data.isError === true ? { isError: true } : {},
|
|
1193
|
+
...typeof data.status === "string" ? { status: data.status } : {},
|
|
1194
|
+
...typeof data.error === "string" ? { error: data.error } : {},
|
|
1135
1195
|
forwardedFrom: event.data._forwardedFrom,
|
|
1136
1196
|
// CAD-87 S1-001 EventIdentity → (execId, seq) reducer dedup (S1-003).
|
|
1137
1197
|
sourceExecutionId: data.sourceExecutionId ?? data.executionId,
|
|
@@ -3370,6 +3430,156 @@ var RemoteRunnersAPI = class extends BaseResourceAPI {
|
|
|
3370
3430
|
}
|
|
3371
3431
|
};
|
|
3372
3432
|
|
|
3433
|
+
// src/resources/ai-functions.ts
|
|
3434
|
+
var AI_FUNCTION_RUN_TIMEOUT_MS = 31e4;
|
|
3435
|
+
var AI_FUNCTION_DESCRIPTOR_TTL_MS = 6e4;
|
|
3436
|
+
function checkAiFunctionParameters(parameters, variables) {
|
|
3437
|
+
const issues = [];
|
|
3438
|
+
const declared = /* @__PURE__ */ new Set();
|
|
3439
|
+
for (const p of parameters) {
|
|
3440
|
+
declared.add(p.name);
|
|
3441
|
+
const has = Object.prototype.hasOwnProperty.call(variables, p.name);
|
|
3442
|
+
const value = has ? variables[p.name] : void 0;
|
|
3443
|
+
if (value === void 0 || value === null) {
|
|
3444
|
+
if (p.required) issues.push({ name: p.name, code: "missing" });
|
|
3445
|
+
continue;
|
|
3446
|
+
}
|
|
3447
|
+
switch (p.type) {
|
|
3448
|
+
case "number":
|
|
3449
|
+
if (typeof value !== "number" || !Number.isFinite(value)) {
|
|
3450
|
+
issues.push({ name: p.name, code: "type" });
|
|
3451
|
+
}
|
|
3452
|
+
break;
|
|
3453
|
+
case "boolean":
|
|
3454
|
+
if (typeof value !== "boolean") issues.push({ name: p.name, code: "type" });
|
|
3455
|
+
break;
|
|
3456
|
+
case "enum":
|
|
3457
|
+
if (typeof value !== "string") issues.push({ name: p.name, code: "type" });
|
|
3458
|
+
else if (p.options && !p.options.includes(value)) {
|
|
3459
|
+
issues.push({ name: p.name, code: "option" });
|
|
3460
|
+
}
|
|
3461
|
+
break;
|
|
3462
|
+
case "string":
|
|
3463
|
+
case "text":
|
|
3464
|
+
if (typeof value !== "string") issues.push({ name: p.name, code: "type" });
|
|
3465
|
+
else if (typeof p.maxLength === "number" && value.length > p.maxLength) {
|
|
3466
|
+
issues.push({ name: p.name, code: "too_long" });
|
|
3467
|
+
}
|
|
3468
|
+
break;
|
|
3469
|
+
case "image":
|
|
3470
|
+
if (typeof value !== "string") issues.push({ name: p.name, code: "type" });
|
|
3471
|
+
break;
|
|
3472
|
+
}
|
|
3473
|
+
}
|
|
3474
|
+
for (const name of Object.keys(variables)) {
|
|
3475
|
+
if (!declared.has(name)) issues.push({ name, code: "unknown" });
|
|
3476
|
+
}
|
|
3477
|
+
return issues;
|
|
3478
|
+
}
|
|
3479
|
+
var AiFunctionsAPI = class extends BaseResourceAPI {
|
|
3480
|
+
descriptorCache = /* @__PURE__ */ new Map();
|
|
3481
|
+
constructor(http) {
|
|
3482
|
+
super(http, "/api/v1/ai-functions");
|
|
3483
|
+
}
|
|
3484
|
+
/**
|
|
3485
|
+
* List the functions this org can call — the index (D27a). Each entry carries
|
|
3486
|
+
* the live version's typed parameters; never prompt text.
|
|
3487
|
+
*/
|
|
3488
|
+
async list() {
|
|
3489
|
+
const data = await this.httpGet("");
|
|
3490
|
+
const functions = Array.isArray(data) ? data : data?.functions ?? [];
|
|
3491
|
+
for (const d of functions) this.cacheDescriptor(d);
|
|
3492
|
+
return functions;
|
|
3493
|
+
}
|
|
3494
|
+
/**
|
|
3495
|
+
* Get one function's descriptor by key (D27a).
|
|
3496
|
+
* `NotFoundError` (`FUNCTION_NOT_FOUND`) / `ConflictError` (`FUNCTION_NOT_PUBLISHED`).
|
|
3497
|
+
*/
|
|
3498
|
+
async get(functionKey) {
|
|
3499
|
+
const data = await this.httpGet(
|
|
3500
|
+
`/${encodeURIComponent(functionKey)}`
|
|
3501
|
+
);
|
|
3502
|
+
const descriptor = data && typeof data === "object" && "function" in data && !("functionKey" in data) ? data.function : data;
|
|
3503
|
+
this.cacheDescriptor(descriptor, functionKey);
|
|
3504
|
+
return descriptor;
|
|
3505
|
+
}
|
|
3506
|
+
/**
|
|
3507
|
+
* Read one of this org's own runs (safe projection, §6.5).
|
|
3508
|
+
*/
|
|
3509
|
+
async getRun(executionId) {
|
|
3510
|
+
return this.httpGet(`/runs/${encodeURIComponent(executionId)}`);
|
|
3511
|
+
}
|
|
3512
|
+
/** Forget cached descriptors (one key, or all). */
|
|
3513
|
+
clearDescriptorCache(functionKey) {
|
|
3514
|
+
if (functionKey) this.descriptorCache.delete(functionKey);
|
|
3515
|
+
else this.descriptorCache.clear();
|
|
3516
|
+
}
|
|
3517
|
+
async run(refOrKey, parametersOrOptions, shorthandOpts) {
|
|
3518
|
+
let ref;
|
|
3519
|
+
let options;
|
|
3520
|
+
if (typeof refOrKey === "string") {
|
|
3521
|
+
ref = { functionKey: refOrKey };
|
|
3522
|
+
options = { ...shorthandOpts ?? {}, variables: parametersOrOptions };
|
|
3523
|
+
} else {
|
|
3524
|
+
ref = refOrKey;
|
|
3525
|
+
options = parametersOrOptions;
|
|
3526
|
+
}
|
|
3527
|
+
const variables = options.variables ?? {};
|
|
3528
|
+
const functionKey = "functionKey" in ref ? ref.functionKey : void 0;
|
|
3529
|
+
const shouldCheck = functionKey !== void 0 && options.version === void 0 && options.validate !== false;
|
|
3530
|
+
if (shouldCheck) {
|
|
3531
|
+
const descriptor = await this.getCachedDescriptor(functionKey);
|
|
3532
|
+
const issues = checkAiFunctionParameters(descriptor.parameters, variables);
|
|
3533
|
+
if (issues.length > 0) {
|
|
3534
|
+
throw new AiFunctionParameterError(functionKey, issues);
|
|
3535
|
+
}
|
|
3536
|
+
}
|
|
3537
|
+
const body = {
|
|
3538
|
+
ref,
|
|
3539
|
+
variables,
|
|
3540
|
+
version: options.version,
|
|
3541
|
+
idempotencyKey: options.idempotencyKey ?? generateExecutionId(),
|
|
3542
|
+
params: options.params
|
|
3543
|
+
};
|
|
3544
|
+
try {
|
|
3545
|
+
return await this.httpPost("/run", body, {
|
|
3546
|
+
skipRetry: true,
|
|
3547
|
+
timeoutMs: Math.max(AI_FUNCTION_RUN_TIMEOUT_MS, this.http.timeoutMs ?? 0)
|
|
3548
|
+
});
|
|
3549
|
+
} catch (error) {
|
|
3550
|
+
throw this.mapRunError(error, functionKey);
|
|
3551
|
+
}
|
|
3552
|
+
}
|
|
3553
|
+
// ── internals ──────────────────────────────────────────────────────────────
|
|
3554
|
+
cacheDescriptor(descriptor, key) {
|
|
3555
|
+
if (!descriptor || typeof descriptor !== "object") return;
|
|
3556
|
+
const cacheKey = key ?? descriptor.functionKey;
|
|
3557
|
+
if (!cacheKey) return;
|
|
3558
|
+
this.descriptorCache.set(cacheKey, {
|
|
3559
|
+
descriptor,
|
|
3560
|
+
expiresAt: Date.now() + AI_FUNCTION_DESCRIPTOR_TTL_MS
|
|
3561
|
+
});
|
|
3562
|
+
}
|
|
3563
|
+
async getCachedDescriptor(functionKey) {
|
|
3564
|
+
const hit = this.descriptorCache.get(functionKey);
|
|
3565
|
+
if (hit && hit.expiresAt > Date.now()) return hit.descriptor;
|
|
3566
|
+
return this.get(functionKey);
|
|
3567
|
+
}
|
|
3568
|
+
mapRunError(error, functionKey) {
|
|
3569
|
+
if (!(error instanceof CadraError)) return error;
|
|
3570
|
+
if (error.serverCode === "DUPLICATE_REQUEST") {
|
|
3571
|
+
return new AiFunctionDuplicateError(error.message, error.details, error.requestId);
|
|
3572
|
+
}
|
|
3573
|
+
if (error.details?.charged === true) {
|
|
3574
|
+
return new AiFunctionChargedError(error);
|
|
3575
|
+
}
|
|
3576
|
+
if (functionKey && error.serverCode?.startsWith("VARIABLE_")) {
|
|
3577
|
+
this.descriptorCache.delete(functionKey);
|
|
3578
|
+
}
|
|
3579
|
+
return error;
|
|
3580
|
+
}
|
|
3581
|
+
};
|
|
3582
|
+
|
|
3373
3583
|
// src/client.ts
|
|
3374
3584
|
var DEFAULT_BASE_URL = "https://api.cadraos.com";
|
|
3375
3585
|
var DEFAULT_TIMEOUT = 3e4;
|
|
@@ -3416,6 +3626,10 @@ var CadraClient = class {
|
|
|
3416
3626
|
* Remote runner operations (list)
|
|
3417
3627
|
*/
|
|
3418
3628
|
remoteRunners;
|
|
3629
|
+
/**
|
|
3630
|
+
* AI function operations (list, get, run, getRun) — p93
|
|
3631
|
+
*/
|
|
3632
|
+
aiFunctions;
|
|
3419
3633
|
/**
|
|
3420
3634
|
* Create a new AI SaaS client
|
|
3421
3635
|
*
|
|
@@ -3505,6 +3719,7 @@ var CadraClient = class {
|
|
|
3505
3719
|
this.kanban = new KanbanAPI(this.httpClient, getStreamConfig);
|
|
3506
3720
|
this.remoteAgents = new RemoteAgentsAPI(this.httpClient, getStreamConfig);
|
|
3507
3721
|
this.remoteRunners = new RemoteRunnersAPI(this.httpClient);
|
|
3722
|
+
this.aiFunctions = new AiFunctionsAPI(this.httpClient);
|
|
3508
3723
|
}
|
|
3509
3724
|
/**
|
|
3510
3725
|
* Validate client options
|
|
@@ -4194,6 +4409,32 @@ function useExecutionStream(options) {
|
|
|
4194
4409
|
};
|
|
4195
4410
|
}
|
|
4196
4411
|
|
|
4412
|
+
// src/chat/utils/toolOutcome.ts
|
|
4413
|
+
var MAX_ERROR_CHARS = 500;
|
|
4414
|
+
function asRecord(value) {
|
|
4415
|
+
return value && typeof value === "object" && !Array.isArray(value) ? value : null;
|
|
4416
|
+
}
|
|
4417
|
+
function errorFrom(value) {
|
|
4418
|
+
if (typeof value === "string" && value.trim()) return value;
|
|
4419
|
+
const rec = asRecord(value);
|
|
4420
|
+
if (rec && typeof rec.message === "string" && rec.message.trim()) return rec.message;
|
|
4421
|
+
return void 0;
|
|
4422
|
+
}
|
|
4423
|
+
function isFailurePayload(result) {
|
|
4424
|
+
const rec = asRecord(result);
|
|
4425
|
+
if (!rec) return false;
|
|
4426
|
+
return rec.success === false || rec.isError === true;
|
|
4427
|
+
}
|
|
4428
|
+
function cap(text) {
|
|
4429
|
+
return text.length > MAX_ERROR_CHARS ? `${text.slice(0, MAX_ERROR_CHARS)}\u2026` : text;
|
|
4430
|
+
}
|
|
4431
|
+
function resolveToolOutcome(input) {
|
|
4432
|
+
const failed = input.isError === true || input.status === "failed" || input.success === false || input.payloadFailure === true || isFailurePayload(input.result);
|
|
4433
|
+
if (!failed) return { status: "completed" };
|
|
4434
|
+
const error = errorFrom(input.error) ?? errorFrom(asRecord(input.result)?.error) ?? "Tool call failed";
|
|
4435
|
+
return { status: "failed", error: cap(error) };
|
|
4436
|
+
}
|
|
4437
|
+
|
|
4197
4438
|
// src/chat/hooks/history-cache.ts
|
|
4198
4439
|
var DEFAULT_HISTORY_STALE_MS = 1e4;
|
|
4199
4440
|
var cache = /* @__PURE__ */ new Map();
|
|
@@ -4369,9 +4610,10 @@ function applyEventInner(state, event) {
|
|
|
4369
4610
|
if (tc) {
|
|
4370
4611
|
toolCalls.set(event.id, {
|
|
4371
4612
|
...tc,
|
|
4372
|
-
status: "completed",
|
|
4613
|
+
status: event.status ?? "completed",
|
|
4373
4614
|
result: event.result,
|
|
4374
|
-
durationMs: event.durationMs
|
|
4615
|
+
durationMs: event.durationMs,
|
|
4616
|
+
...event.error !== void 0 ? { error: event.error } : {}
|
|
4375
4617
|
});
|
|
4376
4618
|
return { ...state, toolCalls };
|
|
4377
4619
|
}
|
|
@@ -4380,8 +4622,9 @@ function applyEventInner(state, event) {
|
|
|
4380
4622
|
name: event.toolName ?? "unknown",
|
|
4381
4623
|
args: {},
|
|
4382
4624
|
result: event.result,
|
|
4383
|
-
status: "completed",
|
|
4384
|
-
durationMs: event.durationMs
|
|
4625
|
+
status: event.status ?? "completed",
|
|
4626
|
+
durationMs: event.durationMs,
|
|
4627
|
+
...event.error !== void 0 ? { error: event.error } : {}
|
|
4385
4628
|
});
|
|
4386
4629
|
if (state.seenToolBlockIds.has(event.id)) {
|
|
4387
4630
|
return { ...state, toolCalls };
|
|
@@ -4631,8 +4874,16 @@ function useAgentChat(options) {
|
|
|
4631
4874
|
const streamMsgId = streamingMessageIdRef.current;
|
|
4632
4875
|
setMessages((prev) => {
|
|
4633
4876
|
const resolvedContent = streamingContentRef.current || finalOutput || "";
|
|
4877
|
+
const streamIdx = prev.findIndex((msg) => msg.id === streamMsgId);
|
|
4878
|
+
let turnStart = 0;
|
|
4879
|
+
for (let i = streamIdx - 1; i >= 0; i--) {
|
|
4880
|
+
if (prev[i].role === "user") {
|
|
4881
|
+
turnStart = i + 1;
|
|
4882
|
+
break;
|
|
4883
|
+
}
|
|
4884
|
+
}
|
|
4634
4885
|
const duplicateExists = resolvedContent && prev.some(
|
|
4635
|
-
(msg) => msg.id !== streamMsgId && msg.role === "assistant" && !msg.isStreaming && msg.content === resolvedContent
|
|
4886
|
+
(msg, idx) => idx >= turnStart && msg.id !== streamMsgId && msg.role === "assistant" && !msg.isStreaming && msg.content === resolvedContent
|
|
4636
4887
|
);
|
|
4637
4888
|
if (duplicateExists) {
|
|
4638
4889
|
return prev.filter((msg) => msg.id !== streamMsgId);
|
|
@@ -4753,6 +5004,17 @@ function useAgentChat(options) {
|
|
|
4753
5004
|
const resultToolCallId = log.metadata?.toolCallId;
|
|
4754
5005
|
const result = log.metadata?.output;
|
|
4755
5006
|
const durationMs = log.durationMs;
|
|
5007
|
+
const outcome = resolveToolOutcome({
|
|
5008
|
+
result,
|
|
5009
|
+
success: log.metadata?.success,
|
|
5010
|
+
payloadFailure: log.metadata?.payloadFailure,
|
|
5011
|
+
isError: log.metadata?.isError,
|
|
5012
|
+
error: log.metadata?.error
|
|
5013
|
+
});
|
|
5014
|
+
const outcomeFields = {
|
|
5015
|
+
status: outcome.status,
|
|
5016
|
+
...outcome.error ? { error: outcome.error } : {}
|
|
5017
|
+
};
|
|
4756
5018
|
let matchedToolCall = resultToolCallId ? pendingToolCallsRef.current.get(resultToolCallId) : void 0;
|
|
4757
5019
|
if (!matchedToolCall) {
|
|
4758
5020
|
for (const [, tc] of pendingToolCallsRef.current) {
|
|
@@ -4766,7 +5028,7 @@ function useAgentChat(options) {
|
|
|
4766
5028
|
const completedToolCall = {
|
|
4767
5029
|
...matchedToolCall,
|
|
4768
5030
|
result,
|
|
4769
|
-
|
|
5031
|
+
...outcomeFields,
|
|
4770
5032
|
durationMs
|
|
4771
5033
|
};
|
|
4772
5034
|
updateToolCall(completedToolCall);
|
|
@@ -4777,7 +5039,7 @@ function useAgentChat(options) {
|
|
|
4777
5039
|
name: resultToolName || "unknown",
|
|
4778
5040
|
args: {},
|
|
4779
5041
|
result,
|
|
4780
|
-
|
|
5042
|
+
...outcomeFields,
|
|
4781
5043
|
durationMs
|
|
4782
5044
|
};
|
|
4783
5045
|
updateToolCall(lateToolCall);
|
|
@@ -4788,7 +5050,8 @@ function useAgentChat(options) {
|
|
|
4788
5050
|
id: resultToolCallId,
|
|
4789
5051
|
toolName: resultToolName,
|
|
4790
5052
|
result,
|
|
4791
|
-
durationMs
|
|
5053
|
+
durationMs,
|
|
5054
|
+
...outcomeFields
|
|
4792
5055
|
});
|
|
4793
5056
|
firedToolResultsRef.current.add(resultToolCallId);
|
|
4794
5057
|
}
|
|
@@ -4898,6 +5161,17 @@ function useAgentChat(options) {
|
|
|
4898
5161
|
const resultToolCallId = log.metadata?.toolCallId;
|
|
4899
5162
|
const result = log.metadata?.output;
|
|
4900
5163
|
const durationMs = log.durationMs;
|
|
5164
|
+
const outcome = resolveToolOutcome({
|
|
5165
|
+
result,
|
|
5166
|
+
success: log.metadata?.success,
|
|
5167
|
+
payloadFailure: log.metadata?.payloadFailure,
|
|
5168
|
+
isError: log.metadata?.isError,
|
|
5169
|
+
error: log.metadata?.error
|
|
5170
|
+
});
|
|
5171
|
+
const outcomeFields = {
|
|
5172
|
+
status: outcome.status,
|
|
5173
|
+
...outcome.error ? { error: outcome.error } : {}
|
|
5174
|
+
};
|
|
4901
5175
|
let matchedToolCall = resultToolCallId ? pendingToolCallsRef.current.get(resultToolCallId) : void 0;
|
|
4902
5176
|
if (!matchedToolCall) {
|
|
4903
5177
|
for (const [, tc] of pendingToolCallsRef.current) {
|
|
@@ -4911,7 +5185,7 @@ function useAgentChat(options) {
|
|
|
4911
5185
|
const completedToolCall = {
|
|
4912
5186
|
...matchedToolCall,
|
|
4913
5187
|
result,
|
|
4914
|
-
|
|
5188
|
+
...outcomeFields,
|
|
4915
5189
|
durationMs
|
|
4916
5190
|
};
|
|
4917
5191
|
updateToolCall(completedToolCall);
|
|
@@ -4922,7 +5196,7 @@ function useAgentChat(options) {
|
|
|
4922
5196
|
name: resultToolName || "unknown",
|
|
4923
5197
|
args: {},
|
|
4924
5198
|
result,
|
|
4925
|
-
|
|
5199
|
+
...outcomeFields,
|
|
4926
5200
|
durationMs
|
|
4927
5201
|
};
|
|
4928
5202
|
updateToolCall(lateToolCall);
|
|
@@ -4933,7 +5207,8 @@ function useAgentChat(options) {
|
|
|
4933
5207
|
id: resultToolCallId,
|
|
4934
5208
|
toolName: resultToolName,
|
|
4935
5209
|
result,
|
|
4936
|
-
durationMs
|
|
5210
|
+
durationMs,
|
|
5211
|
+
...outcomeFields
|
|
4937
5212
|
});
|
|
4938
5213
|
}
|
|
4939
5214
|
if (resultToolCallId) {
|
|
@@ -5182,12 +5457,22 @@ function useAgentChat(options) {
|
|
|
5182
5457
|
if (SILENT_TOOL_NAMES.has(toolName) || isUuidLikeToolName(toolName)) return;
|
|
5183
5458
|
if (firedToolResultsRef.current.has(toolCallId)) return;
|
|
5184
5459
|
const existing = pendingToolCallsRef.current.get(toolCallId);
|
|
5185
|
-
if (existing && existing.status === "completed") return;
|
|
5460
|
+
if (existing && (existing.status === "completed" || existing.status === "failed")) return;
|
|
5461
|
+
const outcome = resolveToolOutcome({
|
|
5462
|
+
result: data.result,
|
|
5463
|
+
isError: data.isError,
|
|
5464
|
+
status: data.status,
|
|
5465
|
+
error: data.error
|
|
5466
|
+
});
|
|
5467
|
+
const outcomeFields = {
|
|
5468
|
+
status: outcome.status,
|
|
5469
|
+
...outcome.error ? { error: outcome.error } : {}
|
|
5470
|
+
};
|
|
5186
5471
|
if (existing) {
|
|
5187
5472
|
const completedToolCall = {
|
|
5188
5473
|
...existing,
|
|
5189
5474
|
result: data.result,
|
|
5190
|
-
|
|
5475
|
+
...outcomeFields,
|
|
5191
5476
|
durationMs: data.durationMs
|
|
5192
5477
|
};
|
|
5193
5478
|
updateToolCall(completedToolCall);
|
|
@@ -5198,7 +5483,7 @@ function useAgentChat(options) {
|
|
|
5198
5483
|
name: toolName,
|
|
5199
5484
|
args: {},
|
|
5200
5485
|
result: data.result,
|
|
5201
|
-
|
|
5486
|
+
...outcomeFields,
|
|
5202
5487
|
durationMs: data.durationMs
|
|
5203
5488
|
};
|
|
5204
5489
|
updateToolCall(lateToolCall);
|
|
@@ -5209,6 +5494,7 @@ function useAgentChat(options) {
|
|
|
5209
5494
|
toolName,
|
|
5210
5495
|
result: data.result,
|
|
5211
5496
|
durationMs: data.durationMs,
|
|
5497
|
+
...outcomeFields,
|
|
5212
5498
|
// CAD-87 S1-003: (execId, seq) reducer dedup for replayed events.
|
|
5213
5499
|
execId: data.sourceExecutionId,
|
|
5214
5500
|
seq: data.seq
|