@sixb/core 0.1.7 → 0.1.9
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/actions/delegated-admission.d.ts +24 -0
- package/dist/actions/delegated-admission.d.ts.map +1 -0
- package/dist/actions/descriptor.d.ts +29 -0
- package/dist/actions/descriptor.d.ts.map +1 -0
- package/dist/actions/execution.d.ts +5 -5
- package/dist/actions/execution.d.ts.map +1 -1
- package/dist/actions/index.js +78 -84
- package/dist/actions/index.js.map +1 -1
- package/dist/actions/request.d.ts.map +1 -1
- package/dist/actions/run-authorization.d.ts +20 -0
- package/dist/actions/run-authorization.d.ts.map +1 -0
- package/dist/actions/run-dispatch.d.ts +3 -1
- package/dist/actions/run-dispatch.d.ts.map +1 -1
- package/dist/actions/types/context.d.ts +2 -0
- package/dist/actions/types/context.d.ts.map +1 -1
- package/dist/actions/validation.d.ts +1 -1
- package/dist/actions/validation.d.ts.map +1 -1
- package/dist/actions/worker.js +33 -37
- package/dist/actions/worker.js.map +2 -2
- package/dist/agents/adapters.d.ts +8 -125
- package/dist/agents/adapters.d.ts.map +1 -1
- package/dist/agents/authority.d.ts +1 -1
- package/dist/agents/authority.d.ts.map +1 -1
- package/dist/agents/{context.d.ts → context/entries.d.ts} +3 -3
- package/dist/agents/context/entries.d.ts.map +1 -0
- package/dist/agents/context/index.d.ts +4 -0
- package/dist/agents/context/index.d.ts.map +1 -0
- package/dist/agents/context/index.js +19 -0
- package/dist/agents/{streams.js.map → context/index.js.map} +1 -1
- package/dist/agents/context-model.d.ts +1 -1
- package/dist/agents/context-model.d.ts.map +1 -1
- package/dist/agents/context-resolution.d.ts +1 -1
- package/dist/agents/context-resolution.d.ts.map +1 -1
- package/dist/agents/errors.d.ts +0 -9
- package/dist/agents/errors.d.ts.map +1 -1
- package/dist/agents/execution.d.ts.map +1 -1
- package/dist/agents/identity.d.ts +3 -0
- package/dist/agents/identity.d.ts.map +1 -0
- package/dist/agents/index.d.ts +7 -7
- package/dist/agents/index.d.ts.map +1 -1
- package/dist/agents/index.js +193 -205
- package/dist/agents/index.js.map +1 -1
- package/dist/agents/message.d.ts +5 -6
- package/dist/agents/message.d.ts.map +1 -1
- package/dist/agents/model-loop.d.ts +4 -0
- package/dist/agents/model-loop.d.ts.map +1 -1
- package/dist/agents/request.d.ts +1 -1
- package/dist/agents/request.d.ts.map +1 -1
- package/dist/agents/streams/index.d.ts +4 -0
- package/dist/agents/streams/index.d.ts.map +1 -0
- package/dist/agents/streams/index.js +20 -0
- package/dist/{chunk-y64skrwp.js.map → agents/streams/index.js.map} +1 -1
- package/dist/agents/streams/internal.d.ts +3 -0
- package/dist/agents/streams/internal.d.ts.map +1 -0
- package/dist/agents/streams/internal.js +40 -0
- package/dist/agents/{context.js.map → streams/internal.js.map} +1 -1
- package/dist/agents/{streams.d.ts → streams/protocol.d.ts} +5 -5
- package/dist/agents/streams/protocol.d.ts.map +1 -0
- package/dist/agents/tool-definition.d.ts +0 -1
- package/dist/agents/tool-definition.d.ts.map +1 -1
- package/dist/agents/types.d.ts +1 -1
- package/dist/agents/types.d.ts.map +1 -1
- package/dist/agents/validation.d.ts +0 -4
- package/dist/agents/validation.d.ts.map +1 -1
- package/dist/ai-usage/execution.d.ts.map +1 -1
- package/dist/auth/index.d.ts +0 -1
- package/dist/auth/index.d.ts.map +1 -1
- package/dist/auth/index.js +96 -105
- package/dist/auth/index.js.map +1 -1
- package/dist/auth/strategy.js +8 -9
- package/dist/auth/strategy.js.map +1 -1
- package/dist/authorization/decision.d.ts +10 -2
- package/dist/authorization/decision.d.ts.map +1 -1
- package/dist/authorization/grant-kinds.d.ts +2 -1
- package/dist/authorization/grant-kinds.d.ts.map +1 -1
- package/dist/authorization/index.d.ts +1 -1
- package/dist/authorization/index.d.ts.map +1 -1
- package/dist/authorization/index.js +51 -53
- package/dist/authorization/index.js.map +1 -1
- package/dist/blob-storage/browser.js +15 -17
- package/dist/blob-storage/browser.js.map +1 -1
- package/dist/blob-storage/index.js +36 -38
- package/dist/blob-storage/index.js.map +1 -1
- package/dist/bootstrap/discovery.d.ts +20 -1
- package/dist/bootstrap/discovery.d.ts.map +1 -1
- package/dist/bootstrap/index.d.ts +2 -2
- package/dist/bootstrap/index.d.ts.map +1 -1
- package/dist/bootstrap/index.js +79 -81
- package/dist/bootstrap/index.js.map +1 -1
- package/dist/bootstrap/ontology-type-manifest.d.ts.map +1 -1
- package/dist/broker/index.js +8 -10
- package/dist/broker/index.js.map +1 -1
- package/dist/{chunk-k34z5rvh.js → chunk-0rdrecsb.js} +18 -18
- package/dist/{chunk-k34z5rvh.js.map → chunk-0rdrecsb.js.map} +2 -2
- package/dist/{chunk-3fqt22c4.js → chunk-0w35wavj.js} +360 -168
- package/dist/chunk-0w35wavj.js.map +14 -0
- package/dist/chunk-0y39rgsb.js +43 -0
- package/dist/{chunk-c15dr03f.js.map → chunk-0y39rgsb.js.map} +2 -2
- package/dist/{chunk-hdz94br2.js → chunk-17kfctj6.js} +23 -13
- package/dist/chunk-17kfctj6.js.map +10 -0
- package/dist/{chunk-e4rvtvpw.js → chunk-1enhpacz.js} +418 -233
- package/dist/chunk-1enhpacz.js.map +34 -0
- package/dist/{chunk-5gd7tpv6.js → chunk-2c4j899j.js} +4 -4
- package/dist/{chunk-5gd7tpv6.js.map → chunk-2c4j899j.js.map} +2 -2
- package/dist/{chunk-7ds9620f.js → chunk-38zv5rkr.js} +24 -8
- package/dist/chunk-38zv5rkr.js.map +10 -0
- package/dist/{chunk-w3e09qqk.js → chunk-39tqv9hz.js} +24 -24
- package/dist/{chunk-w3e09qqk.js.map → chunk-39tqv9hz.js.map} +2 -2
- package/dist/{chunk-04b07a9q.js → chunk-3bh94gbw.js} +13 -13
- package/dist/{chunk-04b07a9q.js.map → chunk-3bh94gbw.js.map} +2 -2
- package/dist/{chunk-8m5ejdpn.js → chunk-3f7veca0.js} +4 -4
- package/dist/{chunk-8m5ejdpn.js.map → chunk-3f7veca0.js.map} +2 -2
- package/dist/chunk-3frsnm7x.js +32 -0
- package/dist/chunk-3frsnm7x.js.map +11 -0
- package/dist/{chunk-n2w475r0.js → chunk-3tgwrcyh.js} +81 -81
- package/dist/{chunk-n2w475r0.js.map → chunk-3tgwrcyh.js.map} +2 -2
- package/dist/{chunk-qv38twt8.js → chunk-52hbv0ak.js} +192 -171
- package/dist/{chunk-qv38twt8.js.map → chunk-52hbv0ak.js.map} +6 -6
- package/dist/{chunk-nf4r78r4.js → chunk-5a4a52tq.js} +4 -4
- package/dist/{chunk-nf4r78r4.js.map → chunk-5a4a52tq.js.map} +2 -2
- package/dist/{chunk-rte5sm3z.js → chunk-5hz0fnca.js} +23 -23
- package/dist/{chunk-rte5sm3z.js.map → chunk-5hz0fnca.js.map} +2 -2
- package/dist/chunk-653vwrzr.js +39 -0
- package/dist/chunk-653vwrzr.js.map +10 -0
- package/dist/{chunk-qw9gvjv5.js → chunk-72w2pxk7.js} +13 -13
- package/dist/{chunk-qw9gvjv5.js.map → chunk-72w2pxk7.js.map} +2 -2
- package/dist/chunk-7apz6hg4.js +50 -0
- package/dist/{chunk-jq43kdvk.js.map → chunk-7apz6hg4.js.map} +2 -2
- package/dist/chunk-7bs40fe1.js +218 -0
- package/dist/{chunk-08twe8m6.js.map → chunk-7bs40fe1.js.map} +3 -3
- package/dist/chunk-7zgecwy1.js +113 -0
- package/dist/chunk-7zgecwy1.js.map +10 -0
- package/dist/{chunk-tn7xcs2n.js → chunk-860dwwy0.js} +93 -30
- package/dist/chunk-860dwwy0.js.map +14 -0
- package/dist/chunk-8vj0rjgs.js +165 -0
- package/dist/chunk-8vj0rjgs.js.map +15 -0
- package/dist/{chunk-7y0f6rf1.js → chunk-92vk7gta.js} +58 -58
- package/dist/chunk-92vk7gta.js.map +10 -0
- package/dist/{chunk-gbrpsx4m.js → chunk-93csa55g.js} +72 -16
- package/dist/chunk-93csa55g.js.map +11 -0
- package/dist/{chunk-d8qkxt2v.js → chunk-98cw09sw.js} +7 -7
- package/dist/chunk-98cw09sw.js.map +10 -0
- package/dist/chunk-9qsh3p5y.js +111 -0
- package/dist/chunk-9qsh3p5y.js.map +11 -0
- package/dist/{chunk-4a849fr1.js → chunk-9tc8dxmn.js} +1 -1
- package/dist/{chunk-z2sery1b.js → chunk-9vx5e9g1.js} +68 -28
- package/dist/chunk-9vx5e9g1.js.map +11 -0
- package/dist/{chunk-9aehf39w.js → chunk-an5tt9y0.js} +353 -353
- package/dist/{chunk-9aehf39w.js.map → chunk-an5tt9y0.js.map} +2 -2
- package/dist/{chunk-x0qhkqje.js → chunk-ap0g1g74.js} +37 -37
- package/dist/{chunk-x0qhkqje.js.map → chunk-ap0g1g74.js.map} +2 -2
- package/dist/chunk-awbhdqyc.js +252 -0
- package/dist/chunk-awbhdqyc.js.map +10 -0
- package/dist/{chunk-ka3a2ft3.js → chunk-b19g04jk.js} +12 -12
- package/dist/{chunk-ka3a2ft3.js.map → chunk-b19g04jk.js.map} +2 -2
- package/dist/chunk-br3k6qbf.js +436 -0
- package/dist/chunk-br3k6qbf.js.map +12 -0
- package/dist/{chunk-dbc80ad7.js → chunk-c5rkjrgp.js} +28 -28
- package/dist/{chunk-dbc80ad7.js.map → chunk-c5rkjrgp.js.map} +2 -2
- package/dist/{chunk-dktq02ne.js → chunk-cqr3acm1.js} +4 -4
- package/dist/{chunk-dktq02ne.js.map → chunk-cqr3acm1.js.map} +2 -2
- package/dist/chunk-d62kjtbg.js +7 -0
- package/dist/{chunk-zcnhxkvd.js.map → chunk-d62kjtbg.js.map} +2 -2
- package/dist/{chunk-74drx9gd.js → chunk-dfm066qg.js} +10 -10
- package/dist/{chunk-74drx9gd.js.map → chunk-dfm066qg.js.map} +2 -2
- package/dist/{chunk-atmkaf60.js → chunk-dmn70ztd.js} +30 -34
- package/dist/chunk-dmn70ztd.js.map +11 -0
- package/dist/chunk-dz5h08xv.js +1887 -0
- package/dist/chunk-dz5h08xv.js.map +25 -0
- package/dist/{chunk-p2vqaxkc.js → chunk-e0d1rzef.js} +27 -22
- package/dist/{chunk-p2vqaxkc.js.map → chunk-e0d1rzef.js.map} +3 -3
- package/dist/{chunk-5sz8ta9r.js → chunk-e1c18xjx.js} +52 -52
- package/dist/{chunk-5sz8ta9r.js.map → chunk-e1c18xjx.js.map} +2 -2
- package/dist/{chunk-ha58tjtt.js → chunk-emyyk7dx.js} +59 -55
- package/dist/{chunk-ha58tjtt.js.map → chunk-emyyk7dx.js.map} +3 -3
- package/dist/{chunk-3kv70xwp.js → chunk-ey1nk510.js} +18 -2
- package/dist/chunk-ey1nk510.js.map +10 -0
- package/dist/chunk-f0rwz2vh.js +152 -0
- package/dist/chunk-f0rwz2vh.js.map +11 -0
- package/dist/{chunk-2xns679x.js → chunk-f4w3yp4f.js} +171 -36
- package/dist/chunk-f4w3yp4f.js.map +12 -0
- package/dist/{chunk-979ww6b3.js → chunk-fb3feg1e.js} +29 -29
- package/dist/{chunk-979ww6b3.js.map → chunk-fb3feg1e.js.map} +2 -2
- package/dist/{chunk-rre42skh.js → chunk-g00bfdq6.js} +729 -296
- package/dist/{chunk-rre42skh.js.map → chunk-g00bfdq6.js.map} +11 -7
- package/dist/{chunk-p03r0h5s.js → chunk-g53f0e4j.js} +76 -202
- package/dist/chunk-g53f0e4j.js.map +15 -0
- package/dist/chunk-g6cke204.js +124 -0
- package/dist/chunk-g6cke204.js.map +10 -0
- package/dist/{chunk-51fjndv0.js → chunk-gfdh9kqa.js} +4 -4
- package/dist/{chunk-51fjndv0.js.map → chunk-gfdh9kqa.js.map} +2 -2
- package/dist/chunk-h1gfhhbh.js +602 -0
- package/dist/chunk-h1gfhhbh.js.map +18 -0
- package/dist/chunk-h3v76ams.js +32 -0
- package/dist/{chunk-08m3b6w8.js.map → chunk-h3v76ams.js.map} +2 -2
- package/dist/chunk-hpr1r6av.js +4006 -0
- package/dist/chunk-hpr1r6av.js.map +44 -0
- package/dist/{chunk-jecn6t54.js → chunk-jgwb25gc.js} +74 -74
- package/dist/{chunk-jecn6t54.js.map → chunk-jgwb25gc.js.map} +2 -2
- package/dist/{chunk-rp1mvzb4.js → chunk-jjy0fhrn.js} +40 -35
- package/dist/{chunk-rp1mvzb4.js.map → chunk-jjy0fhrn.js.map} +3 -3
- package/dist/{chunk-4nxeacx7.js → chunk-jmfet9r4.js} +6 -6
- package/dist/{chunk-4nxeacx7.js.map → chunk-jmfet9r4.js.map} +2 -2
- package/dist/{chunk-64sr682n.js → chunk-k3cqkkn2.js} +61 -55
- package/dist/chunk-k3cqkkn2.js.map +12 -0
- package/dist/{chunk-s5y30bc9.js → chunk-kxwa347f.js} +51 -49
- package/dist/{chunk-s5y30bc9.js.map → chunk-kxwa347f.js.map} +4 -4
- package/dist/{chunk-2ab72m2h.js → chunk-m2ca93my.js} +3 -3
- package/dist/{chunk-2ab72m2h.js.map → chunk-m2ca93my.js.map} +2 -2
- package/dist/{chunk-qjycjdj6.js → chunk-m3z3x9v0.js} +106 -65
- package/dist/{chunk-qjycjdj6.js.map → chunk-m3z3x9v0.js.map} +3 -3
- package/dist/{chunk-6ed5bwnd.js → chunk-mjbk2djy.js} +2092 -1714
- package/dist/chunk-mjbk2djy.js.map +57 -0
- package/dist/{chunk-5jcdmjam.js → chunk-mmagke4x.js} +6 -6
- package/dist/{chunk-5jcdmjam.js.map → chunk-mmagke4x.js.map} +2 -2
- package/dist/chunk-mrp7k0pw.js +147 -0
- package/dist/chunk-mrp7k0pw.js.map +10 -0
- package/dist/{chunk-d63tybny.js → chunk-ms2tmn1k.js} +139 -139
- package/dist/{chunk-d63tybny.js.map → chunk-ms2tmn1k.js.map} +2 -2
- package/dist/{chunk-xdpwpkha.js → chunk-ppytyr6w.js} +156 -179
- package/dist/{chunk-xdpwpkha.js.map → chunk-ppytyr6w.js.map} +3 -5
- package/dist/{chunk-trxxmgnf.js → chunk-pqajwytd.js} +10 -10
- package/dist/{chunk-trxxmgnf.js.map → chunk-pqajwytd.js.map} +3 -3
- package/dist/{chunk-qjzp9xyb.js → chunk-pr2h4bv4.js} +33 -35
- package/dist/chunk-pr2h4bv4.js.map +12 -0
- package/dist/{chunk-xwnf87e1.js → chunk-q5gz3g2j.js} +64 -64
- package/dist/{chunk-xwnf87e1.js.map → chunk-q5gz3g2j.js.map} +2 -2
- package/dist/{chunk-agsvg9ar.js → chunk-qf954wje.js} +6 -6
- package/dist/{chunk-agsvg9ar.js.map → chunk-qf954wje.js.map} +2 -2
- package/dist/{chunk-wjgm6jjt.js → chunk-qhcpj9wc.js} +166 -132
- package/dist/chunk-qhcpj9wc.js.map +14 -0
- package/dist/{chunk-tpnd31c1.js → chunk-r29fxdhn.js} +12 -12
- package/dist/{chunk-tpnd31c1.js.map → chunk-r29fxdhn.js.map} +2 -2
- package/dist/{chunk-b49dgvsj.js → chunk-r2y23egw.js} +3 -3
- package/dist/{chunk-b49dgvsj.js.map → chunk-r2y23egw.js.map} +2 -2
- package/dist/{chunk-2b5qtban.js → chunk-r4tfx1sf.js} +142 -89
- package/dist/chunk-r4tfx1sf.js.map +15 -0
- package/dist/{chunk-4rh2m6zg.js → chunk-rb1xx120.js} +13 -13
- package/dist/{chunk-4rh2m6zg.js.map → chunk-rb1xx120.js.map} +2 -2
- package/dist/chunk-s3csryxe.js +152 -0
- package/dist/chunk-s3csryxe.js.map +11 -0
- package/dist/chunk-s670k14v.js +60 -0
- package/dist/{chunk-407j3msh.js.map → chunk-s670k14v.js.map} +2 -2
- package/dist/chunk-skz0hst3.js +788 -0
- package/dist/chunk-skz0hst3.js.map +19 -0
- package/dist/chunk-v4jbb3rs.js +403 -0
- package/dist/chunk-v4jbb3rs.js.map +10 -0
- package/dist/{chunk-d2ndstdf.js → chunk-vf691g1r.js} +61 -59
- package/dist/{chunk-d2ndstdf.js.map → chunk-vf691g1r.js.map} +2 -2
- package/dist/{chunk-1kamz6j0.js → chunk-vsj3mdfj.js} +8 -8
- package/dist/{chunk-1kamz6j0.js.map → chunk-vsj3mdfj.js.map} +2 -2
- package/dist/{chunk-9dzba0f2.js → chunk-wjasrj67.js} +8 -8
- package/dist/{chunk-9dzba0f2.js.map → chunk-wjasrj67.js.map} +2 -2
- package/dist/{chunk-1evzqhks.js → chunk-wr8qp979.js} +6 -6
- package/dist/{chunk-1evzqhks.js.map → chunk-wr8qp979.js.map} +2 -2
- package/dist/{chunk-n6jxh8sw.js → chunk-wy0qdqfm.js} +18 -18
- package/dist/{chunk-n6jxh8sw.js.map → chunk-wy0qdqfm.js.map} +2 -2
- package/dist/{chunk-8tsf6dmc.js → chunk-x57ycxq0.js} +204 -204
- package/dist/{chunk-8tsf6dmc.js.map → chunk-x57ycxq0.js.map} +2 -2
- package/dist/chunk-x9v4cx1d.js +139 -0
- package/dist/chunk-x9v4cx1d.js.map +10 -0
- package/dist/{chunk-kt81c11h.js → chunk-xfbydgzy.js} +27 -27
- package/dist/{chunk-kt81c11h.js.map → chunk-xfbydgzy.js.map} +2 -2
- package/dist/{chunk-vjjv9mrb.js → chunk-xyr8kppc.js} +22 -22
- package/dist/{chunk-vjjv9mrb.js.map → chunk-xyr8kppc.js.map} +3 -3
- package/dist/chunk-ypbtykv6.js +1537 -0
- package/dist/chunk-ypbtykv6.js.map +19 -0
- package/dist/{chunk-ry24jbr1.js → chunk-yv79ncbv.js} +10 -10
- package/dist/{chunk-ry24jbr1.js.map → chunk-yv79ncbv.js.map} +2 -2
- package/dist/{chunk-xc7hq65b.js → chunk-z30bv4ga.js} +80 -33
- package/dist/chunk-z30bv4ga.js.map +11 -0
- package/dist/{chunk-8ydjhh27.js → chunk-z3y411fq.js} +11 -7
- package/dist/{chunk-8ydjhh27.js.map → chunk-z3y411fq.js.map} +3 -3
- package/dist/{chunk-9t8f5xfx.js → chunk-z5rnrmz1.js} +10 -10
- package/dist/{chunk-9t8f5xfx.js.map → chunk-z5rnrmz1.js.map} +2 -2
- package/dist/{chunk-96swp2wd.js → chunk-z667z3sg.js} +3 -3
- package/dist/{chunk-96swp2wd.js.map → chunk-z667z3sg.js.map} +2 -2
- package/dist/chunk-z8fx5cgb.js +159 -0
- package/dist/chunk-z8fx5cgb.js.map +11 -0
- package/dist/{chunk-xhy826cz.js → chunk-zcnq6105.js} +7 -7
- package/dist/{chunk-xhy826cz.js.map → chunk-zcnq6105.js.map} +2 -2
- package/dist/{chunk-yt8wphsx.js → chunk-zvx7h87b.js} +3 -3
- package/dist/{chunk-yt8wphsx.js.map → chunk-zvx7h87b.js.map} +2 -2
- package/dist/connectors/connections/internal.js +9 -10
- package/dist/connectors/connections/internal.js.map +1 -1
- package/dist/datasets/builders.d.ts +11 -2
- package/dist/datasets/builders.d.ts.map +1 -1
- package/dist/datasets/changes.d.ts +14 -4
- package/dist/datasets/changes.d.ts.map +1 -1
- package/dist/datasets/execution.d.ts +15 -1
- package/dist/datasets/execution.d.ts.map +1 -1
- package/dist/datasets/index.d.ts +1 -0
- package/dist/datasets/index.d.ts.map +1 -1
- package/dist/datasets/sequence.d.ts +7 -0
- package/dist/datasets/sequence.d.ts.map +1 -0
- package/dist/datasets/types.d.ts +1 -0
- package/dist/datasets/types.d.ts.map +1 -1
- package/dist/datasets/validation.d.ts.map +1 -1
- package/dist/datasets/write.d.ts +37 -0
- package/dist/datasets/write.d.ts.map +1 -0
- package/dist/datasets/write.js +13 -0
- package/dist/datasets/write.js.map +9 -0
- package/dist/edits/index.js +7 -8
- package/dist/edits/index.js.map +1 -1
- package/dist/error-reporting/internal.js +22 -24
- package/dist/error-reporting/internal.js.map +1 -1
- package/dist/errors/internal.d.ts +1 -1
- package/dist/errors/internal.d.ts.map +1 -1
- package/dist/errors/internal.js +22 -24
- package/dist/errors/internal.js.map +1 -1
- package/dist/errors/redaction.d.ts +8 -0
- package/dist/errors/redaction.d.ts.map +1 -0
- package/dist/errors/types.d.ts +4 -0
- package/dist/errors/types.d.ts.map +1 -1
- package/dist/events/execution.d.ts.map +1 -1
- package/dist/events/index.js +60 -63
- package/dist/events/index.js.map +1 -1
- package/dist/events/scope.js +4 -5
- package/dist/events/scope.js.map +1 -1
- package/dist/events/selectors/index.js +9 -10
- package/dist/events/selectors/index.js.map +1 -1
- package/dist/events/types/datasets.d.ts +2 -6
- package/dist/events/types/datasets.d.ts.map +1 -1
- package/dist/execution/agent.d.ts +3 -3
- package/dist/execution/agent.d.ts.map +1 -1
- package/dist/execution/agent.js +70 -75
- package/dist/execution/agent.js.map +1 -1
- package/dist/execution/authorization.d.ts +58 -20
- package/dist/execution/authorization.d.ts.map +1 -1
- package/dist/execution/authorized-object-reader.d.ts +69 -0
- package/dist/execution/authorized-object-reader.d.ts.map +1 -0
- package/dist/execution/durable.d.ts +1 -0
- package/dist/execution/durable.d.ts.map +1 -1
- package/dist/execution/index.d.ts +1 -1
- package/dist/execution/index.d.ts.map +1 -1
- package/dist/execution/primitive.d.ts +2 -0
- package/dist/execution/primitive.d.ts.map +1 -1
- package/dist/execution/primitive.js +63 -64
- package/dist/execution/primitive.js.map +3 -3
- package/dist/execution/request.d.ts +12 -0
- package/dist/execution/request.d.ts.map +1 -1
- package/dist/execution/request.js +97 -71
- package/dist/execution/request.js.map +3 -3
- package/dist/execution/scopes.d.ts +16 -0
- package/dist/execution/scopes.d.ts.map +1 -1
- package/dist/execution/types.d.ts +9 -0
- package/dist/execution/types.d.ts.map +1 -1
- package/dist/http/api-routes.d.ts +2 -0
- package/dist/http/api-routes.d.ts.map +1 -1
- package/dist/http/index.js +10 -11
- package/dist/http/index.js.map +1 -1
- package/dist/index.d.ts +21 -14
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +455 -463
- package/dist/index.js.map +1 -1
- package/dist/lake-storage/definition-updates.d.ts.map +1 -1
- package/dist/lake-storage/errors.d.ts +5 -1
- package/dist/lake-storage/errors.d.ts.map +1 -1
- package/dist/lake-storage/in-memory.d.ts +1 -0
- package/dist/lake-storage/in-memory.d.ts.map +1 -1
- package/dist/lake-storage/index.d.ts +6 -1
- package/dist/lake-storage/index.d.ts.map +1 -1
- package/dist/lake-storage/index.js +40 -27
- package/dist/lake-storage/index.js.map +1 -1
- package/dist/lake-storage/merge-validation.d.ts.map +1 -1
- package/dist/lake-storage/merge.d.ts +13 -2
- package/dist/lake-storage/merge.d.ts.map +1 -1
- package/dist/lake-storage/source-ordering.d.ts +19 -0
- package/dist/lake-storage/source-ordering.d.ts.map +1 -0
- package/dist/lake-storage/sql-transforms.d.ts +2 -1
- package/dist/lake-storage/sql-transforms.d.ts.map +1 -1
- package/dist/lake-storage/types.d.ts +10 -5
- package/dist/lake-storage/types.d.ts.map +1 -1
- package/dist/lake-storage/version-inputs.d.ts +4 -0
- package/dist/lake-storage/version-inputs.d.ts.map +1 -0
- package/dist/logging/index.d.ts +3 -4
- package/dist/logging/index.d.ts.map +1 -1
- package/dist/logging/index.js +18 -40
- package/dist/logging/index.js.map +1 -1
- package/dist/logging/internal.d.ts +5 -0
- package/dist/logging/internal.d.ts.map +1 -0
- package/dist/logging/internal.js +43 -0
- package/dist/logging/internal.js.map +9 -0
- package/dist/materialization/index.js +46 -49
- package/dist/materialization/index.js.map +1 -1
- package/dist/materializer/index.js +137 -142
- package/dist/materializer/index.js.map +1 -1
- package/dist/models/errors.d.ts +4 -0
- package/dist/models/errors.d.ts.map +1 -1
- package/dist/models/execution/binding.d.ts +9 -0
- package/dist/models/execution/binding.d.ts.map +1 -0
- package/dist/models/execution/errors.d.ts +9 -0
- package/dist/models/execution/errors.d.ts.map +1 -0
- package/dist/models/execution/index.d.ts +11 -0
- package/dist/models/execution/index.d.ts.map +1 -0
- package/dist/models/execution/index.js +55 -0
- package/dist/models/execution/index.js.map +9 -0
- package/dist/models/execution/model-call-accounting.d.ts +17 -0
- package/dist/models/execution/model-call-accounting.d.ts.map +1 -0
- package/dist/models/execution/model-call-admission.d.ts +47 -0
- package/dist/models/execution/model-call-admission.d.ts.map +1 -0
- package/dist/models/execution/model-call-limits.d.ts +15 -0
- package/dist/models/execution/model-call-limits.d.ts.map +1 -0
- package/dist/models/execution/model-call-recorder.d.ts +40 -0
- package/dist/models/execution/model-call-recorder.d.ts.map +1 -0
- package/dist/models/execution/model-call-recovery.d.ts +12 -0
- package/dist/models/execution/model-call-recovery.d.ts.map +1 -0
- package/dist/models/execution/recovery-queue.d.ts +5 -0
- package/dist/models/execution/recovery-queue.d.ts.map +1 -0
- package/dist/models/execution/types.d.ts +44 -0
- package/dist/models/execution/types.d.ts.map +1 -0
- package/dist/models/execution/usage.d.ts +5 -0
- package/dist/models/execution/usage.d.ts.map +1 -0
- package/dist/models/execution.d.ts +6 -0
- package/dist/models/execution.d.ts.map +1 -0
- package/dist/models/generation-types.d.ts +40 -0
- package/dist/models/generation-types.d.ts.map +1 -0
- package/dist/models/index.d.ts +1 -0
- package/dist/models/index.d.ts.map +1 -1
- package/dist/models/index.js +42 -43
- package/dist/models/index.js.map +1 -1
- package/dist/models/language-model.d.ts +3 -0
- package/dist/models/language-model.d.ts.map +1 -1
- package/dist/models/output.d.ts +5 -0
- package/dist/models/output.d.ts.map +1 -0
- package/dist/models/resolve.d.ts +4 -0
- package/dist/models/resolve.d.ts.map +1 -0
- package/dist/objects/authorized-ontology-view.d.ts +25 -0
- package/dist/objects/authorized-ontology-view.d.ts.map +1 -0
- package/dist/objects/execution.d.ts +1 -1
- package/dist/objects/execution.d.ts.map +1 -1
- package/dist/objects/index.js +75 -84
- package/dist/objects/index.js.map +1 -1
- package/dist/objects/link/authorization.d.ts +2 -7
- package/dist/objects/link/authorization.d.ts.map +1 -1
- package/dist/objects/query/executor.d.ts +4 -2
- package/dist/objects/query/executor.d.ts.map +1 -1
- package/dist/objects/query/index.js +67 -73
- package/dist/objects/query/index.js.map +1 -1
- package/dist/objects/query/links.d.ts +22 -1
- package/dist/objects/query/links.d.ts.map +1 -1
- package/dist/objects/query/selected-read-admission.d.ts +27 -0
- package/dist/objects/query/selected-read-admission.d.ts.map +1 -0
- package/dist/objects/query/validate.d.ts +60 -2
- package/dist/objects/query/validate.d.ts.map +1 -1
- package/dist/objects/sdk/object-handle.d.ts.map +1 -1
- package/dist/objects/sdk/object-set.d.ts.map +1 -1
- package/dist/objects/sdk/runtime-query-executor.d.ts +2 -7
- package/dist/objects/sdk/runtime-query-executor.d.ts.map +1 -1
- package/dist/objects/sdk/telemetry-channel.d.ts.map +1 -1
- package/dist/objects/service/list-service.d.ts +2 -3
- package/dist/objects/service/list-service.d.ts.map +1 -1
- package/dist/objects/telemetry/history.d.ts +8 -6
- package/dist/objects/telemetry/history.d.ts.map +1 -1
- package/dist/objects/telemetry/index.d.ts +2 -2
- package/dist/objects/telemetry/index.d.ts.map +1 -1
- package/dist/objects/telemetry/workload.d.ts +11 -0
- package/dist/objects/telemetry/workload.d.ts.map +1 -0
- package/dist/ontology/index.d.ts +2 -2
- package/dist/ontology/index.d.ts.map +1 -1
- package/dist/ontology/index.js +61 -111
- package/dist/ontology/index.js.map +1 -1
- package/dist/ontology/inference/index.d.ts +2 -1
- package/dist/ontology/inference/index.d.ts.map +1 -1
- package/dist/ontology/internal.d.ts +7 -1
- package/dist/ontology/internal.d.ts.map +1 -1
- package/dist/ontology/internal.js +65 -121
- package/dist/ontology/internal.js.map +3 -4
- package/dist/ontology/json-schema.d.ts +10 -6
- package/dist/ontology/json-schema.d.ts.map +1 -1
- package/dist/ontology/link-path-selection.d.ts +35 -0
- package/dist/ontology/link-path-selection.d.ts.map +1 -0
- package/dist/ontology/refs.d.ts +2 -0
- package/dist/ontology/refs.d.ts.map +1 -1
- package/dist/ontology/tokens.d.ts +2 -1
- package/dist/ontology/tokens.d.ts.map +1 -1
- package/dist/pipelines/execution.d.ts.map +1 -1
- package/dist/pipelines/index.js +57 -63
- package/dist/pipelines/index.js.map +1 -1
- package/dist/pipelines/request.d.ts.map +1 -1
- package/dist/projections/execution.d.ts.map +1 -1
- package/dist/projections/internal.js +58 -64
- package/dist/projections/internal.js.map +1 -1
- package/dist/projections/run-dispatch.d.ts.map +1 -1
- package/dist/query.d.ts +0 -1
- package/dist/query.d.ts.map +1 -1
- package/dist/query.js +11 -15
- package/dist/query.js.map +1 -1
- package/dist/queues/index.d.ts +2 -1
- package/dist/queues/index.d.ts.map +1 -1
- package/dist/queues/index.js +6 -7
- package/dist/queues/index.js.map +1 -1
- package/dist/queues/types.d.ts +3 -20
- package/dist/queues/types.d.ts.map +1 -1
- package/dist/rules/execution.d.ts.map +1 -1
- package/dist/rules/internal.js +4 -5
- package/dist/rules/internal.js.map +1 -1
- package/dist/runtime/create.d.ts +6 -2
- package/dist/runtime/create.d.ts.map +1 -1
- package/dist/runtime/definitions.d.ts +2 -0
- package/dist/runtime/definitions.d.ts.map +1 -1
- package/dist/runtime/host.d.ts +4 -1
- package/dist/runtime/host.d.ts.map +1 -1
- package/dist/runtime/internal.d.ts +1 -0
- package/dist/runtime/internal.d.ts.map +1 -1
- package/dist/runtime/internal.js +13 -14
- package/dist/runtime/internal.js.map +1 -1
- package/dist/runtime/resolve-definitions.d.ts +2 -0
- package/dist/runtime/resolve-definitions.d.ts.map +1 -1
- package/dist/runtime/sixb.d.ts +6 -0
- package/dist/runtime/sixb.d.ts.map +1 -1
- package/dist/runtime/types.d.ts +3 -0
- package/dist/runtime/types.d.ts.map +1 -1
- package/dist/sandboxes/errors.d.ts +4 -0
- package/dist/sandboxes/errors.d.ts.map +1 -1
- package/dist/sandboxes/index.d.ts +2 -2
- package/dist/sandboxes/index.d.ts.map +1 -1
- package/dist/sandboxes/index.js +14 -13
- package/dist/sandboxes/index.js.map +1 -1
- package/dist/sandboxes/sandbox.d.ts +35 -7
- package/dist/sandboxes/sandbox.d.ts.map +1 -1
- package/dist/scheduler/index.js +9 -10
- package/dist/scheduler/index.js.map +1 -1
- package/dist/schedules/execution.d.ts +2 -1
- package/dist/schedules/execution.d.ts.map +1 -1
- package/dist/schedules/index.js +31 -33
- package/dist/schedules/index.js.map +1 -1
- package/dist/security/every.d.ts +4 -1
- package/dist/security/every.d.ts.map +1 -1
- package/dist/security/grants.d.ts +7 -2
- package/dist/security/grants.d.ts.map +1 -1
- package/dist/security/index.d.ts +1 -1
- package/dist/security/index.d.ts.map +1 -1
- package/dist/security/registry.d.ts +1 -0
- package/dist/security/registry.d.ts.map +1 -1
- package/dist/security/types.d.ts +7 -1
- package/dist/security/types.d.ts.map +1 -1
- package/dist/security/validation.d.ts +2 -0
- package/dist/security/validation.d.ts.map +1 -1
- package/dist/shares/access-plan.d.ts +22 -0
- package/dist/shares/access-plan.d.ts.map +1 -0
- package/dist/shares/builders.d.ts +14 -0
- package/dist/shares/builders.d.ts.map +1 -0
- package/dist/shares/compiler.d.ts +14 -0
- package/dist/shares/compiler.d.ts.map +1 -0
- package/dist/shares/errors.d.ts +4 -0
- package/dist/shares/errors.d.ts.map +1 -0
- package/dist/shares/execution.d.ts +57 -0
- package/dist/shares/execution.d.ts.map +1 -0
- package/dist/shares/index.d.ts +10 -0
- package/dist/shares/index.d.ts.map +1 -0
- package/dist/shares/internal.d.ts +3 -0
- package/dist/shares/internal.d.ts.map +1 -0
- package/dist/shares/internal.js +231 -0
- package/dist/shares/internal.js.map +10 -0
- package/dist/shares/intersection.d.ts +9 -0
- package/dist/shares/intersection.d.ts.map +1 -0
- package/dist/shares/session-protocol.d.ts +41 -0
- package/dist/shares/session-protocol.d.ts.map +1 -0
- package/dist/shares/types.d.ts +51 -0
- package/dist/shares/types.d.ts.map +1 -0
- package/dist/shares/validation.d.ts +11 -0
- package/dist/shares/validation.d.ts.map +1 -0
- package/dist/storage/action-runs/failure.js +7 -9
- package/dist/storage/action-runs/failure.js.map +1 -1
- package/dist/storage/action-runs/provider.js +4 -8
- package/dist/storage/action-runs/provider.js.map +1 -1
- package/dist/storage/agents/in-memory.d.ts.map +1 -1
- package/dist/storage/agents/provider.js +26 -30
- package/dist/storage/agents/provider.js.map +1 -1
- package/dist/storage/agents/types.d.ts +0 -3
- package/dist/storage/agents/types.d.ts.map +1 -1
- package/dist/storage/ai-cost/attribution.d.ts +4 -0
- package/dist/storage/ai-cost/attribution.d.ts.map +1 -0
- package/dist/storage/ai-cost/groups.d.ts +3 -0
- package/dist/storage/ai-cost/groups.d.ts.map +1 -1
- package/dist/storage/ai-cost/provider.d.ts +1 -0
- package/dist/storage/ai-cost/provider.d.ts.map +1 -1
- package/dist/storage/ai-cost/provider.js +30 -143
- package/dist/storage/ai-cost/provider.js.map +3 -4
- package/dist/storage/ai-cost/types.d.ts +15 -0
- package/dist/storage/ai-cost/types.d.ts.map +1 -1
- package/dist/storage/ai-limits/enforcement.js +14 -16
- package/dist/storage/ai-limits/enforcement.js.map +1 -1
- package/dist/storage/ai-limits/provider.js +56 -57
- package/dist/storage/ai-limits/provider.js.map +1 -1
- package/dist/storage/auth/in-memory.d.ts +1 -1
- package/dist/storage/auth/in-memory.d.ts.map +1 -1
- package/dist/storage/connector-connections/provider.js +34 -36
- package/dist/storage/connector-connections/provider.js.map +2 -2
- package/dist/storage/executions/in-memory.d.ts +3 -0
- package/dist/storage/executions/in-memory.d.ts.map +1 -1
- package/dist/storage/executions/provider.d.ts +6 -2
- package/dist/storage/executions/provider.d.ts.map +1 -1
- package/dist/storage/executions/provider.js +35 -12
- package/dist/storage/executions/provider.js.map +3 -3
- package/dist/storage/executions/run-link.d.ts +7 -0
- package/dist/storage/executions/run-link.d.ts.map +1 -1
- package/dist/storage/executions/types.d.ts +6 -2
- package/dist/storage/executions/types.d.ts.map +1 -1
- package/dist/storage/executions/validation.d.ts +8 -0
- package/dist/storage/executions/validation.d.ts.map +1 -1
- package/dist/storage/in-memory/index.d.ts +8 -0
- package/dist/storage/in-memory/index.d.ts.map +1 -1
- package/dist/storage/index.d.ts +14 -9
- package/dist/storage/index.d.ts.map +1 -1
- package/dist/storage/index.js +221 -227
- package/dist/storage/index.js.map +1 -1
- package/dist/storage/internal.d.ts +10 -0
- package/dist/storage/internal.d.ts.map +1 -0
- package/dist/storage/internal.js +47 -0
- package/dist/storage/internal.js.map +9 -0
- package/dist/storage/objects/execution-limits.d.ts +25 -0
- package/dist/storage/objects/execution-limits.d.ts.map +1 -0
- package/dist/storage/objects/guard.d.ts +16 -0
- package/dist/storage/objects/guard.d.ts.map +1 -0
- package/dist/storage/objects/in-memory/index.d.ts +3 -0
- package/dist/storage/objects/in-memory/index.d.ts.map +1 -0
- package/dist/storage/objects/in-memory/keys.d.ts +10 -0
- package/dist/storage/objects/in-memory/keys.d.ts.map +1 -0
- package/dist/storage/objects/in-memory/query.d.ts +31 -0
- package/dist/storage/objects/in-memory/query.d.ts.map +1 -0
- package/dist/storage/objects/in-memory/read-scope.d.ts +18 -0
- package/dist/storage/objects/in-memory/read-scope.d.ts.map +1 -0
- package/dist/storage/objects/in-memory/read-source.d.ts +10 -0
- package/dist/storage/objects/in-memory/read-source.d.ts.map +1 -0
- package/dist/storage/objects/in-memory/selected-reader.d.ts +9 -0
- package/dist/storage/objects/in-memory/selected-reader.d.ts.map +1 -0
- package/dist/storage/objects/{in-memory.d.ts → in-memory/storage.d.ts} +13 -10
- package/dist/storage/objects/in-memory/storage.d.ts.map +1 -0
- package/dist/storage/objects/index.d.ts +4 -1
- package/dist/storage/objects/index.d.ts.map +1 -1
- package/dist/storage/objects/keys.d.ts +1 -1
- package/dist/storage/objects/keys.d.ts.map +1 -1
- package/dist/storage/objects/read-scope.d.ts +25 -0
- package/dist/storage/objects/read-scope.d.ts.map +1 -0
- package/dist/storage/objects/types.d.ts +114 -22
- package/dist/storage/objects/types.d.ts.map +1 -1
- package/dist/storage/ontology/provider.js +105 -109
- package/dist/storage/ontology/provider.js.map +1 -1
- package/dist/storage/operation-scope.d.ts +3 -0
- package/dist/storage/operation-scope.d.ts.map +1 -1
- package/dist/storage/operation-scope.js +18 -17
- package/dist/storage/operation-scope.js.map +1 -1
- package/dist/storage/pipeline-runs/provider.js +4 -6
- package/dist/storage/pipeline-runs/provider.js.map +1 -1
- package/dist/storage/projection-runs/provider.js +66 -70
- package/dist/storage/projection-runs/provider.js.map +1 -1
- package/dist/storage/share-grants/errors.d.ts +8 -0
- package/dist/storage/share-grants/errors.d.ts.map +1 -0
- package/dist/storage/share-grants/in-memory.d.ts +11 -0
- package/dist/storage/share-grants/in-memory.d.ts.map +1 -0
- package/dist/storage/share-grants/index.d.ts +5 -0
- package/dist/storage/share-grants/index.d.ts.map +1 -0
- package/dist/storage/share-grants/provider.d.ts +4 -0
- package/dist/storage/share-grants/provider.d.ts.map +1 -0
- package/dist/storage/share-grants/provider.js +22 -0
- package/dist/storage/share-grants/provider.js.map +9 -0
- package/dist/storage/share-grants/record.d.ts +11 -0
- package/dist/storage/share-grants/record.d.ts.map +1 -0
- package/dist/storage/share-grants/types.d.ts +97 -0
- package/dist/storage/share-grants/types.d.ts.map +1 -0
- package/dist/storage/share-sessions/errors.d.ts +8 -0
- package/dist/storage/share-sessions/errors.d.ts.map +1 -0
- package/dist/storage/share-sessions/in-memory.d.ts +14 -0
- package/dist/storage/share-sessions/in-memory.d.ts.map +1 -0
- package/dist/storage/share-sessions/index.d.ts +5 -0
- package/dist/storage/share-sessions/index.d.ts.map +1 -0
- package/dist/storage/share-sessions/provider.d.ts +3 -0
- package/dist/storage/share-sessions/provider.d.ts.map +1 -0
- package/dist/storage/share-sessions/provider.js +19 -0
- package/dist/storage/share-sessions/provider.js.map +9 -0
- package/dist/storage/share-sessions/record.d.ts +8 -0
- package/dist/storage/share-sessions/record.d.ts.map +1 -0
- package/dist/storage/share-sessions/types.d.ts +50 -0
- package/dist/storage/share-sessions/types.d.ts.map +1 -0
- package/dist/storage/sync-runs/provider.js +4 -6
- package/dist/storage/sync-runs/provider.js.map +1 -1
- package/dist/storage/transaction.d.ts +2 -1
- package/dist/storage/transaction.d.ts.map +1 -1
- package/dist/storage/types.d.ts +8 -0
- package/dist/storage/types.d.ts.map +1 -1
- package/dist/storage/webhook-runs/provider.js +4 -6
- package/dist/storage/webhook-runs/provider.js.map +1 -1
- package/dist/storage/workflow-runs/in-memory.d.ts.map +1 -1
- package/dist/storage/workflow-runs/provider.js +13 -18
- package/dist/storage/workflow-runs/provider.js.map +1 -1
- package/dist/storage/workflow-runs/types.d.ts +0 -3
- package/dist/storage/workflow-runs/types.d.ts.map +1 -1
- package/dist/syncs/execution.d.ts.map +1 -1
- package/dist/syncs/index.js +55 -62
- package/dist/syncs/index.js.map +1 -1
- package/dist/syncs/request.d.ts.map +1 -1
- package/dist/testing/action-execution.d.ts +4 -1
- package/dist/testing/action-execution.d.ts.map +1 -1
- package/dist/testing/agent-execution.d.ts +1 -0
- package/dist/testing/agent-execution.d.ts.map +1 -1
- package/dist/testing/agent-storage-contract.d.ts.map +1 -1
- package/dist/testing/ai-model-call-groups-contract.d.ts.map +1 -1
- package/dist/testing/dataset-sequence-contract.d.ts +4 -0
- package/dist/testing/dataset-sequence-contract.d.ts.map +1 -0
- package/dist/testing/effective-storage-contract.d.ts.map +1 -1
- package/dist/testing/execution-storage-contract.d.ts +4 -0
- package/dist/testing/execution-storage-contract.d.ts.map +1 -1
- package/dist/testing/execution.d.ts +1 -0
- package/dist/testing/execution.d.ts.map +1 -1
- package/dist/testing/index.d.ts +3 -0
- package/dist/testing/index.d.ts.map +1 -1
- package/dist/testing/index.js +3087 -1328
- package/dist/testing/index.js.map +17 -13
- package/dist/testing/lake-merge-storage-contract.d.ts +1 -0
- package/dist/testing/lake-merge-storage-contract.d.ts.map +1 -1
- package/dist/testing/lake-storage-contract.d.ts.map +1 -1
- package/dist/testing/object-read-scope-contract.d.ts +22 -0
- package/dist/testing/object-read-scope-contract.d.ts.map +1 -0
- package/dist/testing/share-grant-storage-contract.d.ts +10 -0
- package/dist/testing/share-grant-storage-contract.d.ts.map +1 -0
- package/dist/testing/share-session-storage-contract.d.ts +9 -0
- package/dist/testing/share-session-storage-contract.d.ts.map +1 -0
- package/dist/testing/workflow-execution.d.ts +1 -0
- package/dist/testing/workflow-execution.d.ts.map +1 -1
- package/dist/webhooks/internal.js +51 -56
- package/dist/webhooks/internal.js.map +2 -2
- package/dist/workers/index.js +11 -13
- package/dist/workers/index.js.map +2 -2
- package/dist/workflows/execution.d.ts.map +1 -1
- package/dist/workflows/failure.d.ts +2 -0
- package/dist/workflows/failure.d.ts.map +1 -1
- package/dist/workflows/index.js +135 -140
- package/dist/workflows/index.js.map +1 -1
- package/dist/workflows/request.d.ts.map +1 -1
- package/dist/workflows/run-dispatch.d.ts +0 -1
- package/dist/workflows/run-dispatch.d.ts.map +1 -1
- package/dist/workflows/types.d.ts +2 -0
- package/dist/workflows/types.d.ts.map +1 -1
- package/package.json +72 -30
- package/src/actions/delegated-admission.ts +72 -0
- package/src/actions/descriptor.ts +58 -0
- package/src/actions/execution.ts +99 -24
- package/src/actions/request.ts +136 -19
- package/src/actions/run-authorization.ts +53 -0
- package/src/actions/run-dispatch.ts +10 -7
- package/src/actions/types/context.ts +2 -0
- package/src/actions/validation.ts +2 -1
- package/src/agents/adapters.ts +34 -429
- package/src/agents/authority.ts +3 -4
- package/src/agents/{context.ts → context/entries.ts} +4 -4
- package/src/agents/context/index.ts +15 -0
- package/src/agents/context-model.ts +1 -1
- package/src/agents/context-resolution.ts +2 -5
- package/src/agents/errors.ts +0 -10
- package/src/agents/execution.ts +13 -5
- package/src/agents/identity.ts +4 -0
- package/src/agents/index.ts +5 -24
- package/src/agents/message.ts +5 -6
- package/src/agents/model-loop.ts +62 -6
- package/src/agents/request.ts +27 -29
- package/src/agents/streams/index.ts +18 -0
- package/src/agents/streams/internal.ts +19 -0
- package/src/agents/{streams.ts → streams/protocol.ts} +5 -5
- package/src/agents/tool-definition.ts +0 -19
- package/src/agents/types.ts +1 -1
- package/src/agents/validation.ts +9 -72
- package/src/ai-usage/execution.ts +4 -11
- package/src/auth/index.ts +0 -1
- package/src/authorization/decision.ts +29 -14
- package/src/authorization/grant-kinds.ts +10 -0
- package/src/authorization/index.ts +1 -0
- package/src/bootstrap/discovery.ts +84 -24
- package/src/bootstrap/index.ts +8 -1
- package/src/bootstrap/ontology-type-manifest.ts +12 -6
- package/src/datasets/builders.ts +23 -2
- package/src/datasets/changes.ts +16 -4
- package/src/datasets/execution.ts +76 -5
- package/src/datasets/index.ts +1 -0
- package/src/datasets/sequence.ts +77 -0
- package/src/datasets/types.ts +1 -0
- package/src/datasets/validation.ts +26 -0
- package/src/datasets/write.ts +240 -0
- package/src/errors/internal.ts +90 -10
- package/src/errors/redaction.ts +98 -0
- package/src/errors/types.ts +4 -0
- package/src/events/execution.ts +57 -7
- package/src/events/types/datasets.ts +2 -6
- package/src/execution/agent.ts +6 -7
- package/src/execution/authorization.ts +470 -90
- package/src/execution/authorized-object-reader.ts +695 -0
- package/src/execution/durable.ts +21 -3
- package/src/execution/index.ts +1 -0
- package/src/execution/primitive.ts +5 -1
- package/src/execution/request.ts +66 -13
- package/src/execution/scopes.ts +36 -6
- package/src/execution/types.ts +8 -0
- package/src/http/api-routes.ts +45 -0
- package/src/index.ts +56 -33
- package/src/lake-storage/definition-updates.ts +9 -0
- package/src/lake-storage/errors.ts +6 -1
- package/src/lake-storage/in-memory.ts +53 -17
- package/src/lake-storage/index.ts +10 -1
- package/src/lake-storage/merge-validation.ts +12 -2
- package/src/lake-storage/merge.ts +40 -2
- package/src/lake-storage/source-ordering.ts +95 -0
- package/src/lake-storage/sql-transforms.ts +2 -1
- package/src/lake-storage/types.ts +10 -5
- package/src/lake-storage/version-inputs.ts +14 -0
- package/src/logging/index.ts +2 -33
- package/src/logging/internal.ts +43 -0
- package/src/models/errors.ts +12 -0
- package/src/models/execution/binding.ts +29 -0
- package/src/models/execution/errors.ts +18 -0
- package/src/models/execution/index.ts +26 -0
- package/src/models/execution/model-call-accounting.ts +211 -0
- package/src/models/execution/model-call-admission.ts +127 -0
- package/src/models/execution/model-call-limits.ts +135 -0
- package/src/models/execution/model-call-recorder.ts +235 -0
- package/src/models/execution/model-call-recovery.ts +125 -0
- package/src/models/execution/recovery-queue.ts +31 -0
- package/src/models/execution/types.ts +58 -0
- package/src/models/execution/usage.ts +23 -0
- package/src/models/execution.ts +207 -0
- package/src/models/generation-types.ts +50 -0
- package/src/models/index.ts +8 -0
- package/src/models/language-model.ts +3 -0
- package/src/models/output.ts +45 -0
- package/src/models/resolve.ts +27 -0
- package/src/objects/authorized-ontology-view.ts +512 -0
- package/src/objects/execution.ts +99 -144
- package/src/objects/link/authorization.ts +3 -2
- package/src/objects/query/executor.ts +45 -34
- package/src/objects/query/links.ts +84 -25
- package/src/objects/query/selected-read-admission.ts +310 -0
- package/src/objects/query/validate.ts +353 -36
- package/src/objects/sdk/object-handle.ts +2 -8
- package/src/objects/sdk/object-set.ts +10 -11
- package/src/objects/sdk/runtime-query-executor.ts +8 -28
- package/src/objects/sdk/telemetry-channel.ts +11 -7
- package/src/objects/service/list-service.ts +15 -29
- package/src/objects/telemetry/history.ts +297 -17
- package/src/objects/telemetry/index.ts +2 -2
- package/src/objects/telemetry/workload.ts +79 -0
- package/src/ontology/index.ts +7 -2
- package/src/ontology/inference/index.ts +4 -1
- package/src/ontology/internal.ts +35 -1
- package/src/ontology/json-schema.ts +13 -12
- package/src/ontology/link-path-selection.ts +193 -0
- package/src/ontology/refs.ts +19 -0
- package/src/ontology/tokens.ts +15 -8
- package/src/pipelines/execution.ts +30 -7
- package/src/pipelines/request.ts +5 -0
- package/src/projections/execution.ts +72 -11
- package/src/projections/run-dispatch.ts +7 -12
- package/src/query.ts +0 -1
- package/src/queues/index.ts +4 -2
- package/src/queues/types.ts +6 -25
- package/src/rules/execution.ts +20 -8
- package/src/runtime/create.ts +7 -2
- package/src/runtime/definitions.ts +2 -0
- package/src/runtime/host.ts +27 -7
- package/src/runtime/internal.ts +1 -0
- package/src/runtime/resolve-definitions.ts +9 -0
- package/src/runtime/sixb.ts +27 -2
- package/src/runtime/types.ts +3 -0
- package/src/sandboxes/errors.ts +5 -0
- package/src/sandboxes/index.ts +3 -0
- package/src/sandboxes/sandbox.ts +35 -7
- package/src/schedules/execution.ts +24 -2
- package/src/security/every.ts +4 -0
- package/src/security/grants.ts +45 -3
- package/src/security/index.ts +1 -0
- package/src/security/registry.ts +3 -0
- package/src/security/types.ts +8 -0
- package/src/security/validation.ts +3 -0
- package/src/shares/access-plan.ts +225 -0
- package/src/shares/builders.ts +381 -0
- package/src/shares/compiler.ts +359 -0
- package/src/shares/errors.ts +3 -0
- package/src/shares/execution.ts +394 -0
- package/src/shares/index.ts +28 -0
- package/src/shares/internal.ts +9 -0
- package/src/shares/intersection.ts +178 -0
- package/src/shares/session-protocol.ts +258 -0
- package/src/shares/types.ts +76 -0
- package/src/shares/validation.ts +40 -0
- package/src/storage/agents/in-memory.ts +0 -3
- package/src/storage/agents/types.ts +0 -3
- package/src/storage/ai-cost/analytics.ts +1 -1
- package/src/storage/ai-cost/attribution.ts +15 -0
- package/src/storage/ai-cost/groups.ts +5 -1
- package/src/storage/ai-cost/provider.ts +1 -0
- package/src/storage/ai-cost/types.ts +7 -0
- package/src/storage/auth/in-memory.ts +1 -1
- package/src/storage/executions/in-memory.ts +13 -10
- package/src/storage/executions/provider.ts +34 -1
- package/src/storage/executions/run-link.ts +29 -0
- package/src/storage/executions/types.ts +6 -2
- package/src/storage/executions/validation.ts +78 -1
- package/src/storage/in-memory/index.ts +37 -3
- package/src/storage/index.ts +54 -29
- package/src/storage/internal.ts +20 -0
- package/src/storage/objects/execution-limits.ts +283 -0
- package/src/storage/objects/guard.ts +55 -0
- package/src/storage/objects/in-memory/index.ts +2 -0
- package/src/storage/objects/in-memory/keys.ts +46 -0
- package/src/storage/objects/in-memory/query.ts +754 -0
- package/src/storage/objects/in-memory/read-scope.ts +211 -0
- package/src/storage/objects/in-memory/read-source.ts +10 -0
- package/src/storage/objects/in-memory/selected-reader.ts +252 -0
- package/src/storage/objects/in-memory/storage.ts +589 -0
- package/src/storage/objects/index.ts +21 -0
- package/src/storage/objects/keys.ts +1 -1
- package/src/storage/objects/read-scope.ts +672 -0
- package/src/storage/objects/types.ts +123 -19
- package/src/storage/operation-scope.ts +16 -0
- package/src/storage/share-grants/errors.ts +14 -0
- package/src/storage/share-grants/in-memory.ts +107 -0
- package/src/storage/share-grants/index.ts +14 -0
- package/src/storage/share-grants/provider.ts +11 -0
- package/src/storage/share-grants/record.ts +347 -0
- package/src/storage/share-grants/types.ts +112 -0
- package/src/storage/share-sessions/errors.ts +14 -0
- package/src/storage/share-sessions/in-memory.ts +105 -0
- package/src/storage/share-sessions/index.ts +11 -0
- package/src/storage/share-sessions/provider.ts +9 -0
- package/src/storage/share-sessions/record.ts +176 -0
- package/src/storage/share-sessions/types.ts +57 -0
- package/src/storage/transaction.ts +14 -2
- package/src/storage/types.ts +27 -0
- package/src/storage/workflow-runs/in-memory.ts +0 -2
- package/src/storage/workflow-runs/types.ts +0 -3
- package/src/syncs/execution.ts +25 -5
- package/src/syncs/request.ts +5 -0
- package/src/testing/action-execution.ts +9 -2
- package/src/testing/agent-execution.ts +3 -0
- package/src/testing/agent-storage-contract.ts +0 -5
- package/src/testing/ai-model-call-groups-contract.ts +74 -2
- package/src/testing/dataset-sequence-contract.ts +373 -0
- package/src/testing/effective-storage-contract.ts +34 -0
- package/src/testing/execution-storage-contract.ts +138 -1
- package/src/testing/execution.ts +6 -0
- package/src/testing/index.ts +16 -0
- package/src/testing/lake-merge-storage-contract.ts +3 -0
- package/src/testing/lake-storage-contract.ts +58 -0
- package/src/testing/object-read-scope-contract.ts +939 -0
- package/src/testing/share-grant-storage-contract.ts +325 -0
- package/src/testing/share-session-storage-contract.ts +235 -0
- package/src/testing/workflow-execution.ts +4 -0
- package/src/workflows/execution.ts +53 -14
- package/src/workflows/failure.ts +62 -1
- package/src/workflows/request.ts +5 -9
- package/src/workflows/run-dispatch.ts +0 -3
- package/src/workflows/types.ts +2 -0
- package/src/workflows/validation.ts +1 -1
- package/dist/agents/context.d.ts.map +0 -1
- package/dist/agents/context.js +0 -23
- package/dist/agents/streams.d.ts.map +0 -1
- package/dist/agents/streams.js +0 -55
- package/dist/chunk-08m3b6w8.js +0 -32
- package/dist/chunk-08twe8m6.js +0 -218
- package/dist/chunk-2b5qtban.js.map +0 -14
- package/dist/chunk-2xns679x.js.map +0 -11
- package/dist/chunk-37wk412q.js +0 -1370
- package/dist/chunk-37wk412q.js.map +0 -23
- package/dist/chunk-3fqt22c4.js.map +0 -14
- package/dist/chunk-3kv70xwp.js.map +0 -10
- package/dist/chunk-407j3msh.js +0 -60
- package/dist/chunk-64sr682n.js.map +0 -12
- package/dist/chunk-6ed5bwnd.js.map +0 -57
- package/dist/chunk-7ds9620f.js.map +0 -10
- package/dist/chunk-7y0f6rf1.js.map +0 -10
- package/dist/chunk-atmkaf60.js.map +0 -11
- package/dist/chunk-c15dr03f.js +0 -43
- package/dist/chunk-d8qkxt2v.js.map +0 -10
- package/dist/chunk-dqn23610.js +0 -72
- package/dist/chunk-dqn23610.js.map +0 -11
- package/dist/chunk-e4rvtvpw.js.map +0 -34
- package/dist/chunk-gbrpsx4m.js.map +0 -11
- package/dist/chunk-h0knpbz5.js +0 -2486
- package/dist/chunk-h0knpbz5.js.map +0 -38
- package/dist/chunk-hdz94br2.js.map +0 -10
- package/dist/chunk-jq43kdvk.js +0 -50
- package/dist/chunk-n2arzn6e.js +0 -1745
- package/dist/chunk-n2arzn6e.js.map +0 -20
- package/dist/chunk-p03r0h5s.js.map +0 -16
- package/dist/chunk-qjzp9xyb.js.map +0 -12
- package/dist/chunk-tn7xcs2n.js.map +0 -13
- package/dist/chunk-wjgm6jjt.js.map +0 -13
- package/dist/chunk-xc7hq65b.js.map +0 -10
- package/dist/chunk-y35ma3mj.js +0 -551
- package/dist/chunk-y35ma3mj.js.map +0 -15
- package/dist/chunk-y64skrwp.js +0 -19
- package/dist/chunk-z2sery1b.js.map +0 -11
- package/dist/chunk-zcnhxkvd.js +0 -7
- package/dist/logging/types.js +0 -27
- package/dist/logging/types.js.map +0 -9
- package/dist/storage/objects/in-memory.d.ts.map +0 -1
- package/src/storage/objects/in-memory.ts +0 -1241
- /package/dist/{chunk-zqqz8052.js → chunk-7n30ybym.js} +0 -0
- /package/dist/{chunk-zqqz8052.js.map → chunk-7n30ybym.js.map} +0 -0
- /package/dist/{chunk-4a849fr1.js.map → chunk-9tc8dxmn.js.map} +0 -0
|
@@ -0,0 +1,4006 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
import {
|
|
3
|
+
agentServiceAccountId2,
|
|
4
|
+
assertObjectReadOutputWithinLimit2,
|
|
5
|
+
createAgentRuntimeAuthorization,
|
|
6
|
+
resolveRuntimeAuthorizationForProject,
|
|
7
|
+
getAuthorizationRef,
|
|
8
|
+
resolveExecutionScopeAuthorization,
|
|
9
|
+
AuthorizationError2,
|
|
10
|
+
isAllowed2,
|
|
11
|
+
assertAuthorized2,
|
|
12
|
+
isRuntimeAllowed2,
|
|
13
|
+
assertCanManageConnector2,
|
|
14
|
+
assertPrivileged2,
|
|
15
|
+
assertProviderAccess2,
|
|
16
|
+
canViewEvent2,
|
|
17
|
+
canViewActionRun2,
|
|
18
|
+
canViewWorkflowRun2,
|
|
19
|
+
canViewWorkflowIntervention2,
|
|
20
|
+
canViewPipelineRun2,
|
|
21
|
+
canViewProjectionRun2,
|
|
22
|
+
canViewProjection2
|
|
23
|
+
} from "./chunk-dz5h08xv.js";
|
|
24
|
+
import {
|
|
25
|
+
captureSixbFailure2
|
|
26
|
+
} from "./chunk-f4w3yp4f.js";
|
|
27
|
+
import {
|
|
28
|
+
isRecord2,
|
|
29
|
+
normalizeSchemaValue2,
|
|
30
|
+
coerceSchemaValueToTyped2,
|
|
31
|
+
assertObjectTypeRegistered2
|
|
32
|
+
} from "./chunk-ms2tmn1k.js";
|
|
33
|
+
import {
|
|
34
|
+
isActionDefinition2,
|
|
35
|
+
SYSTEM_PRINCIPAL2,
|
|
36
|
+
principalsEqual2
|
|
37
|
+
} from "./chunk-g00bfdq6.js";
|
|
38
|
+
import {
|
|
39
|
+
isModelReasoning2,
|
|
40
|
+
modelReasoningSupportIssue2
|
|
41
|
+
} from "./chunk-pqajwytd.js";
|
|
42
|
+
import {
|
|
43
|
+
RuntimeError2,
|
|
44
|
+
ModelProviderError2,
|
|
45
|
+
ModelStreamError2,
|
|
46
|
+
UnsupportedModelFeatureError2,
|
|
47
|
+
StructuredOutputError2,
|
|
48
|
+
estimateModelCall,
|
|
49
|
+
rateModelCall2
|
|
50
|
+
} from "./chunk-e0d1rzef.js";
|
|
51
|
+
import {
|
|
52
|
+
AgentStorageError2,
|
|
53
|
+
AGENT_REASONING_LEVELS2
|
|
54
|
+
} from "./chunk-7bs40fe1.js";
|
|
55
|
+
import {
|
|
56
|
+
ObjectNotFoundError2
|
|
57
|
+
} from "./chunk-8vj0rjgs.js";
|
|
58
|
+
import {
|
|
59
|
+
ExecutionStorageError2
|
|
60
|
+
} from "./chunk-93csa55g.js";
|
|
61
|
+
import {
|
|
62
|
+
WORKFLOW_RUN_FAILURE_CODES2
|
|
63
|
+
} from "./chunk-mjbk2djy.js";
|
|
64
|
+
import {
|
|
65
|
+
WorkflowRunError2
|
|
66
|
+
} from "./chunk-pr2h4bv4.js";
|
|
67
|
+
import {
|
|
68
|
+
assertAuthorizedObjectReaderBinding,
|
|
69
|
+
getAuthorizedOntologyView,
|
|
70
|
+
canDelegationAccessActionRun,
|
|
71
|
+
requestAction3,
|
|
72
|
+
requestActionAndWait2
|
|
73
|
+
} from "./chunk-ypbtykv6.js";
|
|
74
|
+
import {
|
|
75
|
+
shareSixbErrorReporter2,
|
|
76
|
+
reportRunFailure2
|
|
77
|
+
} from "./chunk-7apz6hg4.js";
|
|
78
|
+
import {
|
|
79
|
+
aiLimitSubjectsFromAttribution2,
|
|
80
|
+
applicableAiLimitPolicyStatuses2,
|
|
81
|
+
aiUsageLimitExceededError2,
|
|
82
|
+
aiUsageLimitUnavailableError2
|
|
83
|
+
} from "./chunk-0y39rgsb.js";
|
|
84
|
+
import {
|
|
85
|
+
AgentRequestError2,
|
|
86
|
+
normalizeAgentContextEntries2
|
|
87
|
+
} from "./chunk-dmn70ztd.js";
|
|
88
|
+
import {
|
|
89
|
+
publishAgentRunActivity2
|
|
90
|
+
} from "./chunk-92vk7gta.js";
|
|
91
|
+
import {
|
|
92
|
+
registerConnectorConnectionsRuntime
|
|
93
|
+
} from "./chunk-5a4a52tq.js";
|
|
94
|
+
import {
|
|
95
|
+
createConnectorRuntime,
|
|
96
|
+
SyncValidationError2,
|
|
97
|
+
requestSyncRun2
|
|
98
|
+
} from "./chunk-emyyk7dx.js";
|
|
99
|
+
import {
|
|
100
|
+
writeDataset2
|
|
101
|
+
} from "./chunk-mrp7k0pw.js";
|
|
102
|
+
import {
|
|
103
|
+
shareOntologyMutationRuntime2
|
|
104
|
+
} from "./chunk-zcnq6105.js";
|
|
105
|
+
import {
|
|
106
|
+
compileShareAccessPlan
|
|
107
|
+
} from "./chunk-awbhdqyc.js";
|
|
108
|
+
import {
|
|
109
|
+
getTelemetryHistoryBatch2,
|
|
110
|
+
getLatestTelemetryPoint,
|
|
111
|
+
createObjectSet2,
|
|
112
|
+
upsertLink3,
|
|
113
|
+
upsertLinkBatch3,
|
|
114
|
+
removeLink3,
|
|
115
|
+
listObjects,
|
|
116
|
+
upsertObject3,
|
|
117
|
+
upsertObjectBatch3,
|
|
118
|
+
appendTelemetry
|
|
119
|
+
} from "./chunk-1enhpacz.js";
|
|
120
|
+
import {
|
|
121
|
+
schemaRecordToJsonSchema2
|
|
122
|
+
} from "./chunk-7zgecwy1.js";
|
|
123
|
+
import {
|
|
124
|
+
PipelineError2,
|
|
125
|
+
requestPipelineRun2
|
|
126
|
+
} from "./chunk-jjy0fhrn.js";
|
|
127
|
+
import {
|
|
128
|
+
requireAccountingCapabilities,
|
|
129
|
+
aiModelCallOutputTokenAllowance,
|
|
130
|
+
createAiModelCallLimitController2,
|
|
131
|
+
AiModelCallRecorder2,
|
|
132
|
+
enqueueAiModelCallRecovery2,
|
|
133
|
+
resolveLanguageModel2
|
|
134
|
+
} from "./chunk-h1gfhhbh.js";
|
|
135
|
+
import {
|
|
136
|
+
getDatasetPrimaryKeyColumns2
|
|
137
|
+
} from "./chunk-9qsh3p5y.js";
|
|
138
|
+
import {
|
|
139
|
+
executionRecordInputFromRuntime,
|
|
140
|
+
ensureExecutionRecord2,
|
|
141
|
+
createPrimitiveExecutionRecord
|
|
142
|
+
} from "./chunk-17kfctj6.js";
|
|
143
|
+
import {
|
|
144
|
+
ShareGrantStorageError2
|
|
145
|
+
} from "./chunk-br3k6qbf.js";
|
|
146
|
+
import {
|
|
147
|
+
isObjectRefSchema2,
|
|
148
|
+
validateSchemaOrRefValue2
|
|
149
|
+
} from "./chunk-f0rwz2vh.js";
|
|
150
|
+
import {
|
|
151
|
+
supportsDirectUpload2,
|
|
152
|
+
supportsRangeRead2
|
|
153
|
+
} from "./chunk-h3v76ams.js";
|
|
154
|
+
import {
|
|
155
|
+
isJsonValue2,
|
|
156
|
+
assertJsonValue2,
|
|
157
|
+
assertJsonObject2,
|
|
158
|
+
isPlainRecord
|
|
159
|
+
} from "./chunk-wy0qdqfm.js";
|
|
160
|
+
|
|
161
|
+
// src/actions/descriptor.ts
|
|
162
|
+
function snapshotActionDescriptor(action) {
|
|
163
|
+
const params = Object.fromEntries(Object.entries(action.params).map(([id, config]) => [id, structuredClone(config)]));
|
|
164
|
+
return deepFreeze({
|
|
165
|
+
id: action.id,
|
|
166
|
+
...action.description === undefined ? {} : { description: action.description },
|
|
167
|
+
binding: action.binding.kind === "global" ? { kind: "global" } : { kind: "object", objectTypeId: action.binding.objectType.id },
|
|
168
|
+
params,
|
|
169
|
+
phases: {
|
|
170
|
+
validate: action.phases.validate.length > 0,
|
|
171
|
+
writeback: action.phases.writeback !== undefined,
|
|
172
|
+
edits: action.phases.edits !== undefined,
|
|
173
|
+
effects: action.phases.effects !== undefined
|
|
174
|
+
}
|
|
175
|
+
});
|
|
176
|
+
}
|
|
177
|
+
function deepFreeze(value, seen = new Set) {
|
|
178
|
+
if (typeof value !== "object" || value === null || seen.has(value))
|
|
179
|
+
return value;
|
|
180
|
+
seen.add(value);
|
|
181
|
+
for (const key of Reflect.ownKeys(value)) {
|
|
182
|
+
const descriptor = Object.getOwnPropertyDescriptor(value, key);
|
|
183
|
+
if (descriptor && "value" in descriptor)
|
|
184
|
+
deepFreeze(descriptor.value, seen);
|
|
185
|
+
}
|
|
186
|
+
return Object.freeze(value);
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
// src/actions/execution.ts
|
|
190
|
+
function createActionsRuntime(runtime, execution) {
|
|
191
|
+
const projectId = runtime.projectId;
|
|
192
|
+
const runtimeAuthorization = runtime.runtimeAuthorization;
|
|
193
|
+
const objectReader = runtime.objectReader;
|
|
194
|
+
assertAuthorizedObjectReaderBinding({
|
|
195
|
+
reader: objectReader,
|
|
196
|
+
scope: { execution, authorization: runtimeAuthorization }
|
|
197
|
+
});
|
|
198
|
+
const authorization = resolveRuntimeAuthorizationForProject({
|
|
199
|
+
projectId,
|
|
200
|
+
runtimeAuthorization
|
|
201
|
+
});
|
|
202
|
+
const canList = (action) => {
|
|
203
|
+
if (authorization.type === "denied")
|
|
204
|
+
return false;
|
|
205
|
+
if (authorization.type === "delegated") {
|
|
206
|
+
const binding = action.binding;
|
|
207
|
+
return binding.kind === "object" && authorization.actionApply.some((target) => target.actionId === action.id && target.subject.objectTypeId === binding.objectType.id) && getAuthorizedOntologyView(objectReader).getObjectTypeById(binding.objectType.id) !== null;
|
|
208
|
+
}
|
|
209
|
+
if (authorization.type === "unrestricted")
|
|
210
|
+
return true;
|
|
211
|
+
return isAllowed2(authorization.context, { kind: "action.apply", actionId: action.id }) && (action.binding.kind === "global" || isAllowed2(authorization.context, {
|
|
212
|
+
kind: "object.view",
|
|
213
|
+
objectTypeId: action.binding.objectType.id
|
|
214
|
+
}));
|
|
215
|
+
};
|
|
216
|
+
const release = (value) => {
|
|
217
|
+
if (authorization.type === "delegated") {
|
|
218
|
+
assertObjectReadOutputWithinLimit2(value, authorization.objectRead.limits);
|
|
219
|
+
}
|
|
220
|
+
return value;
|
|
221
|
+
};
|
|
222
|
+
const describeAll = (actions) => release(actions.filter(canList).map(snapshotActionDescriptor));
|
|
223
|
+
return {
|
|
224
|
+
list: () => describeAll(runtime.actionRegistry.list()),
|
|
225
|
+
getById: (actionId) => {
|
|
226
|
+
const action = runtime.actionRegistry.getById(actionId);
|
|
227
|
+
return release(action && canList(action) ? snapshotActionDescriptor(action) : null);
|
|
228
|
+
},
|
|
229
|
+
listGlobal: () => describeAll(runtime.actionRegistry.listGlobal()),
|
|
230
|
+
listForType: (objectType) => describeAll(runtime.actionRegistry.listForType(objectType).filter((action) => authorization.type !== "delegated" || action.binding.kind === "object" && action.binding.objectType.id === objectType.id)),
|
|
231
|
+
request: (input) => requestAction3(runtime, execution, input),
|
|
232
|
+
requestAndWait: (input) => requestActionAndWait2(runtime, execution, input),
|
|
233
|
+
runs: {
|
|
234
|
+
getById: async (runId) => {
|
|
235
|
+
if (authorization.type === "denied" || authorization.type === "delegated" && (!authorization.delegation || authorization.actionApply.length === 0))
|
|
236
|
+
return null;
|
|
237
|
+
const run = await runtime.storage.actionRuns?.getById({
|
|
238
|
+
projectId,
|
|
239
|
+
id: runId
|
|
240
|
+
}) ?? null;
|
|
241
|
+
return run && (authorization.type === "unrestricted" || authorization.type === "principal" && canViewActionRun2(authorization.context, run) || authorization.type === "delegated" && await canDelegationAccessActionRun({
|
|
242
|
+
storage: runtime.storage,
|
|
243
|
+
projectId,
|
|
244
|
+
authority: authorization,
|
|
245
|
+
run
|
|
246
|
+
})) ? release(run) : null;
|
|
247
|
+
},
|
|
248
|
+
list: (input = {}) => {
|
|
249
|
+
if (authorization.type === "denied" || authorization.type === "delegated") {
|
|
250
|
+
return Promise.resolve({ runs: [], hasMore: false, total: 0 });
|
|
251
|
+
}
|
|
252
|
+
const storage = runtime.storage.actionRuns;
|
|
253
|
+
if (!storage)
|
|
254
|
+
return Promise.resolve({ runs: [], hasMore: false, total: 0 });
|
|
255
|
+
return storage.list({
|
|
256
|
+
...input,
|
|
257
|
+
projectId,
|
|
258
|
+
actionIds: authorization.type === "principal" ? [...authorization.context.grants["apply:action"]] : undefined,
|
|
259
|
+
objectTypeIds: authorization.type === "principal" ? [...authorization.context.grants["view:object"]] : undefined
|
|
260
|
+
});
|
|
261
|
+
}
|
|
262
|
+
}
|
|
263
|
+
};
|
|
264
|
+
}
|
|
265
|
+
|
|
266
|
+
// src/runtime/ai-cost.ts
|
|
267
|
+
async function resolveExecutionCosts(input) {
|
|
268
|
+
if (input.executionIds.length === 0)
|
|
269
|
+
return [];
|
|
270
|
+
if (!input.storage)
|
|
271
|
+
return input.executionIds.map(() => {
|
|
272
|
+
return;
|
|
273
|
+
});
|
|
274
|
+
return input.storage.summarizeExecutions({
|
|
275
|
+
projectId: input.projectId,
|
|
276
|
+
executionIds: input.executionIds
|
|
277
|
+
});
|
|
278
|
+
}
|
|
279
|
+
|
|
280
|
+
// src/runtime/ai-usage.ts
|
|
281
|
+
async function resolveExecutionUsage(input) {
|
|
282
|
+
if (input.executionIds.length === 0)
|
|
283
|
+
return [];
|
|
284
|
+
if (!input.storage)
|
|
285
|
+
return input.executionIds.map(() => {
|
|
286
|
+
return;
|
|
287
|
+
});
|
|
288
|
+
const summaries = await input.storage.summarizeExecutions({
|
|
289
|
+
projectId: input.projectId,
|
|
290
|
+
executionIds: input.executionIds
|
|
291
|
+
});
|
|
292
|
+
return summaries.map((summary) => summary.modelCallCount === 0 ? undefined : summary.usage);
|
|
293
|
+
}
|
|
294
|
+
|
|
295
|
+
// src/agents/ids.ts
|
|
296
|
+
import { createHash, randomUUID } from "crypto";
|
|
297
|
+
function createAgentThreadId2() {
|
|
298
|
+
return `agt_thr_${randomUUID()}`;
|
|
299
|
+
}
|
|
300
|
+
function createAgentRunId2() {
|
|
301
|
+
return `agt_run_${randomUUID()}`;
|
|
302
|
+
}
|
|
303
|
+
function createSubagentRunId2(parentRunId, spawnKey) {
|
|
304
|
+
const digest = createHash("sha256").update(parentRunId).update("\x00").update(spawnKey).digest("hex");
|
|
305
|
+
return `agt_run_child_${digest}`;
|
|
306
|
+
}
|
|
307
|
+
function createSubagentExecutionId2(runId) {
|
|
308
|
+
return `exec_${runId}`;
|
|
309
|
+
}
|
|
310
|
+
function createAgentMessageId2() {
|
|
311
|
+
return `agt_msg_${randomUUID()}`;
|
|
312
|
+
}
|
|
313
|
+
function agentContextCheckpointId2(runId) {
|
|
314
|
+
return `agt_ctx_${runId}`;
|
|
315
|
+
}
|
|
316
|
+
function createAgentRunExecutionToken2() {
|
|
317
|
+
return `agt_exec_${randomUUID()}`;
|
|
318
|
+
}
|
|
319
|
+
|
|
320
|
+
// src/agents/request.ts
|
|
321
|
+
import { randomUUID as randomUUID2 } from "crypto";
|
|
322
|
+
|
|
323
|
+
// src/agents/context-resolution.ts
|
|
324
|
+
async function resolveAgentContextParts2(runtime, input) {
|
|
325
|
+
const entries = normalizeAgentContextEntries2(input);
|
|
326
|
+
for (const entry of entries) {
|
|
327
|
+
if (entry.context.kind !== "object")
|
|
328
|
+
continue;
|
|
329
|
+
const { objectTypeId, primaryId } = entry.context.ref;
|
|
330
|
+
try {
|
|
331
|
+
runtime.ontology.resolveObjectType(objectTypeId);
|
|
332
|
+
} catch {
|
|
333
|
+
invalidContext(`context references an unknown object type '${objectTypeId}'`);
|
|
334
|
+
}
|
|
335
|
+
const object = await runtime.objectReader.getByPrimaryId({
|
|
336
|
+
objectTypeId,
|
|
337
|
+
primaryId
|
|
338
|
+
});
|
|
339
|
+
if (!object) {
|
|
340
|
+
invalidContext(`context references an unknown object '${objectTypeId}:${primaryId}'`);
|
|
341
|
+
}
|
|
342
|
+
}
|
|
343
|
+
return entries.map((entry) => ({ type: "context", ...entry }));
|
|
344
|
+
}
|
|
345
|
+
function invalidContext(message) {
|
|
346
|
+
throw new AgentRequestError2("invalid_context", `[Sixb] Invalid agent context: ${message}.`);
|
|
347
|
+
}
|
|
348
|
+
|
|
349
|
+
// src/agents/dispatch.ts
|
|
350
|
+
function agentRunQueueJobId2(runId) {
|
|
351
|
+
return `agt_job_${runId}`;
|
|
352
|
+
}
|
|
353
|
+
function subagentRunQueueJobId2(runId) {
|
|
354
|
+
return `agt_child_job_${runId}`;
|
|
355
|
+
}
|
|
356
|
+
function workflowAgentNodeQueueJobId2(nodeRunId) {
|
|
357
|
+
return `wfa_job_${nodeRunId}`;
|
|
358
|
+
}
|
|
359
|
+
async function dispatchQueuedAgentRuns2(input) {
|
|
360
|
+
const limit = normalizeLimit(input.limit);
|
|
361
|
+
const runs = input.runIds ? await input.storage.runs.getByIds({
|
|
362
|
+
projectId: input.projectId,
|
|
363
|
+
ids: [...new Set(input.runIds)].slice(0, limit)
|
|
364
|
+
}) : (await input.storage.runs.list({
|
|
365
|
+
projectId: input.projectId,
|
|
366
|
+
kinds: ["conversation"],
|
|
367
|
+
statuses: ["queued"],
|
|
368
|
+
order: "asc",
|
|
369
|
+
limit
|
|
370
|
+
})).runs;
|
|
371
|
+
const queued = runs.filter((run) => run.kind === "conversation" && run.status === "queued");
|
|
372
|
+
if (queued.length === 0) {
|
|
373
|
+
return { scanned: 0, dispatched: [], failures: [] };
|
|
374
|
+
}
|
|
375
|
+
try {
|
|
376
|
+
const jobs = await input.queue.enqueue({
|
|
377
|
+
projectId: input.projectId,
|
|
378
|
+
jobs: queued.map((run) => ({
|
|
379
|
+
id: agentRunQueueJobId2(run.id),
|
|
380
|
+
type: "agent.run.requested",
|
|
381
|
+
payload: { runId: run.id }
|
|
382
|
+
}))
|
|
383
|
+
});
|
|
384
|
+
const jobsById = new Map(jobs.map((job) => [job.id, job]));
|
|
385
|
+
const dispatched = queued.map((run) => {
|
|
386
|
+
const jobId = agentRunQueueJobId2(run.id);
|
|
387
|
+
if (!jobsById.has(jobId)) {
|
|
388
|
+
throw new Error(`[Sixb] Agent queue did not return job '${jobId}'.`);
|
|
389
|
+
}
|
|
390
|
+
return { runId: run.id, jobId };
|
|
391
|
+
});
|
|
392
|
+
return { scanned: queued.length, dispatched, failures: [] };
|
|
393
|
+
} catch (error) {
|
|
394
|
+
return {
|
|
395
|
+
scanned: queued.length,
|
|
396
|
+
dispatched: [],
|
|
397
|
+
failures: queued.map((run) => ({ runId: run.id, error }))
|
|
398
|
+
};
|
|
399
|
+
}
|
|
400
|
+
}
|
|
401
|
+
async function dispatchQueuedSubagentRuns2(input) {
|
|
402
|
+
const limit = normalizeLimit(input.limit);
|
|
403
|
+
const runs = input.runIds ? await input.storage.runs.getByIds({
|
|
404
|
+
projectId: input.projectId,
|
|
405
|
+
ids: [...new Set(input.runIds)].slice(0, limit)
|
|
406
|
+
}) : (await input.storage.runs.list({
|
|
407
|
+
projectId: input.projectId,
|
|
408
|
+
kinds: ["subagent"],
|
|
409
|
+
statuses: ["queued"],
|
|
410
|
+
order: "asc",
|
|
411
|
+
limit
|
|
412
|
+
})).runs;
|
|
413
|
+
const queued = runs.filter((run) => run.kind === "subagent" && run.status === "queued");
|
|
414
|
+
if (queued.length === 0)
|
|
415
|
+
return { scanned: 0, dispatched: [], failures: [] };
|
|
416
|
+
try {
|
|
417
|
+
const jobs = await input.queue.enqueue({
|
|
418
|
+
projectId: input.projectId,
|
|
419
|
+
jobs: queued.map((run) => ({
|
|
420
|
+
id: subagentRunQueueJobId2(run.id),
|
|
421
|
+
type: "agent.subagent-run.requested",
|
|
422
|
+
payload: { runId: run.id }
|
|
423
|
+
}))
|
|
424
|
+
});
|
|
425
|
+
const jobsById = new Set(jobs.map((job) => job.id));
|
|
426
|
+
const dispatched = queued.map((run) => {
|
|
427
|
+
const jobId = subagentRunQueueJobId2(run.id);
|
|
428
|
+
if (!jobsById.has(jobId)) {
|
|
429
|
+
throw new Error(`[Sixb] Subagent queue did not return job '${jobId}'.`);
|
|
430
|
+
}
|
|
431
|
+
return { runId: run.id, jobId };
|
|
432
|
+
});
|
|
433
|
+
return { scanned: queued.length, dispatched, failures: [] };
|
|
434
|
+
} catch (error) {
|
|
435
|
+
return {
|
|
436
|
+
scanned: queued.length,
|
|
437
|
+
dispatched: [],
|
|
438
|
+
failures: queued.map((run) => ({ runId: run.id, error }))
|
|
439
|
+
};
|
|
440
|
+
}
|
|
441
|
+
}
|
|
442
|
+
function normalizeLimit(value) {
|
|
443
|
+
if (value === undefined)
|
|
444
|
+
return 100;
|
|
445
|
+
if (!Number.isFinite(value) || value < 1) {
|
|
446
|
+
throw new Error("[Sixb] Agent dispatch limit must be at least 1.");
|
|
447
|
+
}
|
|
448
|
+
return Math.floor(value);
|
|
449
|
+
}
|
|
450
|
+
|
|
451
|
+
// src/agents/retired-config.ts
|
|
452
|
+
function assertNoAgentDefinitions(input) {
|
|
453
|
+
if ("agents" in input) {
|
|
454
|
+
throw new RuntimeError2("[Sixb] Agent definitions are no longer supported. Configure 'models' and 'tools' on createSixb() instead.");
|
|
455
|
+
}
|
|
456
|
+
}
|
|
457
|
+
function assertNoAgentSelector(input) {
|
|
458
|
+
if ("agentId" in input || "agentIds" in input) {
|
|
459
|
+
throw new AgentRequestError2("agent_selector_removed", "[Sixb] There is one project Agent. Remove the agentId selector and use sixb.agent.");
|
|
460
|
+
}
|
|
461
|
+
}
|
|
462
|
+
|
|
463
|
+
// src/agents/request.ts
|
|
464
|
+
async function requestAgentRun2(runtime, execution, models, input) {
|
|
465
|
+
const authority = resolveExecutionScopeAuthorization(runtime.projectId, {
|
|
466
|
+
execution,
|
|
467
|
+
authorization: runtime.runtimeAuthorization
|
|
468
|
+
});
|
|
469
|
+
assertNoAgentSelector(input);
|
|
470
|
+
assertAuthorized2(runtime, { kind: "agent.run" });
|
|
471
|
+
assertRequestAuthorityCanRunAgent(runtime);
|
|
472
|
+
const spec = resolveConversationRunSpec({ models, input });
|
|
473
|
+
const contextParts = await resolveAgentContextParts2(runtime, input.context);
|
|
474
|
+
const agents = requireAgentStorage(runtime);
|
|
475
|
+
const projectId = runtime.projectId;
|
|
476
|
+
const principal = authority.type === "principal" ? authority.context.principal : input.principal ?? SYSTEM_PRINCIPAL2;
|
|
477
|
+
const runId = createAgentRunId2();
|
|
478
|
+
const durableExecution = await prepareDurableAgentExecution(runtime, execution, runId);
|
|
479
|
+
await assertAiLimitPreflight(runtime, durableExecution);
|
|
480
|
+
const { thread, createdThread } = await resolveThread(agents, {
|
|
481
|
+
projectId,
|
|
482
|
+
threadId: input.threadId,
|
|
483
|
+
title: input.title,
|
|
484
|
+
principal
|
|
485
|
+
});
|
|
486
|
+
if (thread.activeRunId !== null) {
|
|
487
|
+
throw new AgentRequestError2("active_run_exists", `[Sixb] Agent thread '${thread.id}' already has an active run '${thread.activeRunId}'.`);
|
|
488
|
+
}
|
|
489
|
+
const triggerMessageId = input.messageId ?? createAgentMessageId2();
|
|
490
|
+
let run;
|
|
491
|
+
try {
|
|
492
|
+
run = await runtime.storage.transaction(async (tx) => {
|
|
493
|
+
const agents = tx.agents;
|
|
494
|
+
if (!agents) {
|
|
495
|
+
throw new AgentRequestError2("storage_unavailable", "[Sixb] Agent storage is not configured.");
|
|
496
|
+
}
|
|
497
|
+
await tx.executions.create(durableExecution);
|
|
498
|
+
await agents.messages.append({
|
|
499
|
+
id: triggerMessageId,
|
|
500
|
+
projectId,
|
|
501
|
+
threadId: thread.id,
|
|
502
|
+
runId: null,
|
|
503
|
+
role: "user",
|
|
504
|
+
parts: [
|
|
505
|
+
...contextParts,
|
|
506
|
+
{ type: "text", text: input.text },
|
|
507
|
+
...(input.attachments ?? []).map((fileRef) => ({ type: "file", fileRef }))
|
|
508
|
+
],
|
|
509
|
+
authorPrincipal: principal
|
|
510
|
+
});
|
|
511
|
+
return agents.runs.create({
|
|
512
|
+
id: runId,
|
|
513
|
+
projectId,
|
|
514
|
+
executionId: durableExecution.id,
|
|
515
|
+
threadId: thread.id,
|
|
516
|
+
triggerMessageId,
|
|
517
|
+
spec
|
|
518
|
+
});
|
|
519
|
+
});
|
|
520
|
+
} catch (error) {
|
|
521
|
+
if (error instanceof AgentStorageError2 && error.code === "active_run_exists") {
|
|
522
|
+
throw new AgentRequestError2("active_run_exists", error.message);
|
|
523
|
+
}
|
|
524
|
+
throw error;
|
|
525
|
+
}
|
|
526
|
+
await publishRunActivity(runtime, run);
|
|
527
|
+
const jobId = await dispatchAgentRun(runtime, agents, runId);
|
|
528
|
+
return {
|
|
529
|
+
run,
|
|
530
|
+
...jobId ? { jobId } : {},
|
|
531
|
+
createdThread
|
|
532
|
+
};
|
|
533
|
+
}
|
|
534
|
+
async function retryAgentRun2(runtime, execution, models, failedRun) {
|
|
535
|
+
resolveExecutionScopeAuthorization(runtime.projectId, {
|
|
536
|
+
execution,
|
|
537
|
+
authorization: runtime.runtimeAuthorization
|
|
538
|
+
});
|
|
539
|
+
assertAuthorized2(runtime, { kind: "agent.run" });
|
|
540
|
+
assertRequestAuthorityCanRunAgent(runtime);
|
|
541
|
+
if (failedRun.status !== "failed") {
|
|
542
|
+
throw new AgentRequestError2("run_not_retryable", `[Sixb] Only failed Agent runs can be retried.`);
|
|
543
|
+
}
|
|
544
|
+
const agents = requireAgentStorage(runtime);
|
|
545
|
+
const thread = await agents.threads.getById({
|
|
546
|
+
projectId: runtime.projectId,
|
|
547
|
+
id: failedRun.threadId
|
|
548
|
+
});
|
|
549
|
+
if (!thread) {
|
|
550
|
+
throw new AgentRequestError2("thread_not_found", `[Sixb] Agent thread '${failedRun.threadId}' was not found.`);
|
|
551
|
+
}
|
|
552
|
+
const runId = createAgentRunId2();
|
|
553
|
+
const durableExecution = await prepareDurableAgentExecution(runtime, execution, runId);
|
|
554
|
+
await assertAiLimitPreflight(runtime, durableExecution);
|
|
555
|
+
const run = await runtime.storage.transaction(async (tx) => {
|
|
556
|
+
const agents = tx.agents;
|
|
557
|
+
if (!agents) {
|
|
558
|
+
throw new AgentRequestError2("storage_unavailable", "[Sixb] Agent storage is not configured.");
|
|
559
|
+
}
|
|
560
|
+
await agents.messages.deleteByRunId({
|
|
561
|
+
projectId: runtime.projectId,
|
|
562
|
+
threadId: failedRun.threadId,
|
|
563
|
+
runId: failedRun.id
|
|
564
|
+
});
|
|
565
|
+
await tx.executions.create(durableExecution);
|
|
566
|
+
return agents.runs.create({
|
|
567
|
+
id: runId,
|
|
568
|
+
projectId: runtime.projectId,
|
|
569
|
+
executionId: durableExecution.id,
|
|
570
|
+
threadId: failedRun.threadId,
|
|
571
|
+
triggerMessageId: failedRun.triggerMessageId,
|
|
572
|
+
spec: failedRun.spec ?? resolveConversationRunSpec({
|
|
573
|
+
models,
|
|
574
|
+
input: {}
|
|
575
|
+
})
|
|
576
|
+
});
|
|
577
|
+
});
|
|
578
|
+
await publishRunActivity(runtime, run);
|
|
579
|
+
const jobId = await dispatchAgentRun(runtime, agents, runId);
|
|
580
|
+
return { run, ...jobId ? { jobId } : {}, createdThread: false };
|
|
581
|
+
}
|
|
582
|
+
async function assertAiLimitPreflight(runtime, execution) {
|
|
583
|
+
const limits = runtime.storage.aiLimits;
|
|
584
|
+
if (!limits)
|
|
585
|
+
throw aiUsageLimitUnavailableError2(["limitStorageUnavailable"]);
|
|
586
|
+
const subjects = aiLimitSubjectsFromAttribution2(execution.requestedBy, execution.requesterGroupIds);
|
|
587
|
+
let applicable;
|
|
588
|
+
try {
|
|
589
|
+
applicable = applicableAiLimitPolicyStatuses2(await limits.listPolicyStatuses({ projectId: runtime.projectId }), subjects);
|
|
590
|
+
} catch {
|
|
591
|
+
throw aiUsageLimitUnavailableError2(["limitStorageUnavailable"]);
|
|
592
|
+
}
|
|
593
|
+
const unavailable = applicable.filter((status) => status.accountingStatus === "unavailable");
|
|
594
|
+
if (unavailable.length > 0) {
|
|
595
|
+
throw aiUsageLimitUnavailableError2(["incompleteAccounting"]);
|
|
596
|
+
}
|
|
597
|
+
const exhausted = applicable.filter((status) => status.exhausted);
|
|
598
|
+
if (exhausted.length > 0) {
|
|
599
|
+
const resetAt = new Date(Math.min(...exhausted.map((status) => status.period.resetAt.getTime())));
|
|
600
|
+
throw aiUsageLimitExceededError2(resetAt);
|
|
601
|
+
}
|
|
602
|
+
}
|
|
603
|
+
function resolveConversationRunSpec(input) {
|
|
604
|
+
if (!input.models) {
|
|
605
|
+
throw new AgentRequestError2("model_not_found", "[Sixb] Configure models.language before starting the Agent.");
|
|
606
|
+
}
|
|
607
|
+
const selected = input.input.model ?? input.models.default;
|
|
608
|
+
const model = input.models.getByRef(selected);
|
|
609
|
+
if (model === null) {
|
|
610
|
+
throw new AgentRequestError2("model_not_found", `[Sixb] Language model '${selected.provider}/${selected.modelId}' is not in the project model catalog.`);
|
|
611
|
+
}
|
|
612
|
+
const reasoning = input.input.reasoning;
|
|
613
|
+
if (reasoning !== undefined && !isModelReasoning2(reasoning)) {
|
|
614
|
+
throw new AgentRequestError2("invalid_model_selection", `[Sixb] Agent reasoning must be one of: ${AGENT_REASONING_LEVELS2.join(", ")}, or a nonnegative budgetTokens object.`);
|
|
615
|
+
}
|
|
616
|
+
return Object.freeze({
|
|
617
|
+
model: Object.freeze({ provider: selected.provider, modelId: selected.modelId }),
|
|
618
|
+
...reasoning === undefined ? {} : { reasoning }
|
|
619
|
+
});
|
|
620
|
+
}
|
|
621
|
+
async function prepareDurableAgentExecution(runtime, execution, runId) {
|
|
622
|
+
const parent = await ensureExecutionRecord2(runtime.storage.executions, executionRecordInputFromRuntime({
|
|
623
|
+
execution,
|
|
624
|
+
runtimeAuthorization: runtime.runtimeAuthorization
|
|
625
|
+
}));
|
|
626
|
+
return createInheritedAgentExecutionRecord2({
|
|
627
|
+
id: `exec_${randomUUID2()}`,
|
|
628
|
+
parent,
|
|
629
|
+
runId
|
|
630
|
+
});
|
|
631
|
+
}
|
|
632
|
+
function assertRequestAuthorityCanRunAgent(runtime) {
|
|
633
|
+
if (!canInheritAgentRequestAuthorization2(runtime.runtimeAuthorization)) {
|
|
634
|
+
throw new AgentRequestError2("authority_not_inheritable", "[Sixb] The Agent requires an authenticated user request or disabled authorization.");
|
|
635
|
+
}
|
|
636
|
+
}
|
|
637
|
+
async function dispatchAgentRun(runtime, agents, runId) {
|
|
638
|
+
try {
|
|
639
|
+
const dispatch = await dispatchQueuedAgentRuns2({
|
|
640
|
+
projectId: runtime.projectId,
|
|
641
|
+
storage: agents,
|
|
642
|
+
queue: runtime.queues.agents,
|
|
643
|
+
runIds: [runId]
|
|
644
|
+
});
|
|
645
|
+
const failure = dispatch.failures[0];
|
|
646
|
+
if (failure) {
|
|
647
|
+
console.error(`[Sixb] Could not dispatch queued agent run '${runId}'; retrying later.`, failure.error);
|
|
648
|
+
}
|
|
649
|
+
return dispatch.dispatched[0]?.jobId;
|
|
650
|
+
} catch (error) {
|
|
651
|
+
console.error(`[Sixb] Could not dispatch queued agent run '${runId}'; retrying later.`, error);
|
|
652
|
+
return;
|
|
653
|
+
}
|
|
654
|
+
}
|
|
655
|
+
async function publishRunActivity(runtime, run) {
|
|
656
|
+
try {
|
|
657
|
+
await publishAgentRunActivity2(runtime.broker, run);
|
|
658
|
+
} catch (error) {
|
|
659
|
+
console.error(`[Sixb] Agent run '${run.id}' activity stream publish failed:`, error);
|
|
660
|
+
}
|
|
661
|
+
}
|
|
662
|
+
async function resolveThread(agents, params) {
|
|
663
|
+
if (params.threadId) {
|
|
664
|
+
const existing = await agents.threads.getById({
|
|
665
|
+
projectId: params.projectId,
|
|
666
|
+
id: params.threadId
|
|
667
|
+
});
|
|
668
|
+
if (existing) {
|
|
669
|
+
return { thread: existing, createdThread: false };
|
|
670
|
+
}
|
|
671
|
+
}
|
|
672
|
+
const thread = await agents.threads.create({
|
|
673
|
+
id: params.threadId ?? createAgentThreadId2(),
|
|
674
|
+
projectId: params.projectId,
|
|
675
|
+
ownerPrincipal: params.principal,
|
|
676
|
+
...params.title === undefined ? {} : { title: params.title }
|
|
677
|
+
});
|
|
678
|
+
return { thread, createdThread: true };
|
|
679
|
+
}
|
|
680
|
+
function requireAgentStorage(runtime) {
|
|
681
|
+
const agents = runtime.storage.agents;
|
|
682
|
+
if (!agents) {
|
|
683
|
+
throw new AgentRequestError2("storage_unavailable", "[Sixb] Agent storage is not configured.");
|
|
684
|
+
}
|
|
685
|
+
return agents;
|
|
686
|
+
}
|
|
687
|
+
|
|
688
|
+
// src/agents/execution.ts
|
|
689
|
+
function createAgentRuntime(runtime, execution, models) {
|
|
690
|
+
const authority = resolveRuntimeAuthorizationForProject(runtime);
|
|
691
|
+
const principal = authority.type === "principal" ? authority.context.principal : SYSTEM_PRINCIPAL2;
|
|
692
|
+
const allowed = () => isRuntimeAllowed2(runtime, { kind: "agent.run" });
|
|
693
|
+
const getVisibleThreadRecord = async (threadId) => {
|
|
694
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
695
|
+
return null;
|
|
696
|
+
const thread = await runtime.storage.agents?.threads.getById({
|
|
697
|
+
projectId: runtime.projectId,
|
|
698
|
+
id: threadId
|
|
699
|
+
}) ?? null;
|
|
700
|
+
if (!thread || !allowed())
|
|
701
|
+
return null;
|
|
702
|
+
return authority.type === "principal" && !principalsEqual2(principal, thread.ownerPrincipal) ? null : thread;
|
|
703
|
+
};
|
|
704
|
+
const getAgent = () => {
|
|
705
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
706
|
+
return null;
|
|
707
|
+
const model = models?.language.default;
|
|
708
|
+
if (!model || !allowed())
|
|
709
|
+
return null;
|
|
710
|
+
return {
|
|
711
|
+
name: "Sixb",
|
|
712
|
+
model: { provider: model.provider, modelId: model.modelId }
|
|
713
|
+
};
|
|
714
|
+
};
|
|
715
|
+
const getVisibleRunRecord = async (runId) => {
|
|
716
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
717
|
+
return null;
|
|
718
|
+
const run = await runtime.storage.agents?.runs.getById({
|
|
719
|
+
projectId: runtime.projectId,
|
|
720
|
+
id: runId
|
|
721
|
+
}) ?? null;
|
|
722
|
+
if (!run || run.kind !== "conversation")
|
|
723
|
+
return null;
|
|
724
|
+
const thread = await getVisibleThreadRecord(run.threadId);
|
|
725
|
+
return thread ? run : null;
|
|
726
|
+
};
|
|
727
|
+
const getRun = async (runId) => {
|
|
728
|
+
const run = await getVisibleRunRecord(runId);
|
|
729
|
+
return run ? attachRunView(runtime, run) : null;
|
|
730
|
+
};
|
|
731
|
+
return {
|
|
732
|
+
get: getAgent,
|
|
733
|
+
threads: {
|
|
734
|
+
create: async (input) => {
|
|
735
|
+
assertNoAgentSelector(input);
|
|
736
|
+
const agent = getAgent();
|
|
737
|
+
if (!agent) {
|
|
738
|
+
throw new AgentRequestError2("agent_not_found", "[Sixb] The project Agent is unavailable.");
|
|
739
|
+
}
|
|
740
|
+
const storage = runtime.storage.agents;
|
|
741
|
+
if (!storage) {
|
|
742
|
+
throw new AgentRequestError2("storage_unavailable", "[Sixb] Agent storage is not configured.");
|
|
743
|
+
}
|
|
744
|
+
return storage.threads.create({
|
|
745
|
+
id: input.id ?? createAgentThreadId2(),
|
|
746
|
+
projectId: runtime.projectId,
|
|
747
|
+
ownerPrincipal: principal,
|
|
748
|
+
...input.title === undefined ? {} : { title: input.title }
|
|
749
|
+
});
|
|
750
|
+
},
|
|
751
|
+
getById: getVisibleThreadRecord,
|
|
752
|
+
list: async (input = {}) => {
|
|
753
|
+
assertNoAgentSelector(input);
|
|
754
|
+
if (authority.type === "denied" || authority.type === "delegated") {
|
|
755
|
+
return { threads: [], hasMore: false, total: 0 };
|
|
756
|
+
}
|
|
757
|
+
const storage = runtime.storage.agents;
|
|
758
|
+
if (!storage || !allowed())
|
|
759
|
+
return { threads: [], hasMore: false, total: 0 };
|
|
760
|
+
return storage.threads.list({
|
|
761
|
+
...input,
|
|
762
|
+
projectId: runtime.projectId,
|
|
763
|
+
ownerPrincipal: authority.type === "principal" ? principal : undefined
|
|
764
|
+
});
|
|
765
|
+
}
|
|
766
|
+
},
|
|
767
|
+
runs: {
|
|
768
|
+
request: async (input) => {
|
|
769
|
+
assertNoAgentSelector(input);
|
|
770
|
+
const agent = getAgent();
|
|
771
|
+
if (!agent) {
|
|
772
|
+
throw new AgentRequestError2("agent_not_found", "[Sixb] The project Agent is unavailable.");
|
|
773
|
+
}
|
|
774
|
+
assertAuthorized2(runtime, { kind: "agent.run" });
|
|
775
|
+
if (input.threadId && !await getVisibleThreadRecord(input.threadId)) {
|
|
776
|
+
throw new AgentRequestError2("thread_not_found", `[Sixb] Agent thread '${input.threadId}' not found.`);
|
|
777
|
+
}
|
|
778
|
+
const result = await requestAgentRun2(runtime, execution, models?.language, {
|
|
779
|
+
...input,
|
|
780
|
+
principal
|
|
781
|
+
});
|
|
782
|
+
return { ...result, run: await attachRunView(runtime, result.run) };
|
|
783
|
+
},
|
|
784
|
+
retry: async (runId) => {
|
|
785
|
+
const failedRun = await getVisibleRunRecord(runId);
|
|
786
|
+
if (!failedRun) {
|
|
787
|
+
throw new AgentRequestError2("run_not_found", `[Sixb] Agent run '${runId}' was not found.`);
|
|
788
|
+
}
|
|
789
|
+
const agent = getAgent();
|
|
790
|
+
if (!agent) {
|
|
791
|
+
throw new AgentRequestError2("agent_not_found", "[Sixb] The project Agent is unavailable.");
|
|
792
|
+
}
|
|
793
|
+
const result = await retryAgentRun2(runtime, execution, models?.language, failedRun);
|
|
794
|
+
return { ...result, run: await attachRunView(runtime, result.run) };
|
|
795
|
+
},
|
|
796
|
+
getById: getRun,
|
|
797
|
+
listForThread: async (threadId, input = {}) => {
|
|
798
|
+
assertNoAgentSelector(input);
|
|
799
|
+
const storage = runtime.storage.agents;
|
|
800
|
+
if (!storage || !await getVisibleThreadRecord(threadId))
|
|
801
|
+
return null;
|
|
802
|
+
const result = await storage.runs.list({
|
|
803
|
+
...input,
|
|
804
|
+
projectId: runtime.projectId,
|
|
805
|
+
threadId
|
|
806
|
+
});
|
|
807
|
+
return {
|
|
808
|
+
...result,
|
|
809
|
+
runs: await attachRunViews(runtime, result.runs.filter((run) => run.kind === "conversation"))
|
|
810
|
+
};
|
|
811
|
+
}
|
|
812
|
+
}
|
|
813
|
+
};
|
|
814
|
+
}
|
|
815
|
+
async function attachRunView(runtime, run) {
|
|
816
|
+
const [view] = await attachRunViews(runtime, [run]);
|
|
817
|
+
if (!view)
|
|
818
|
+
throw new Error(`[Sixb] Could not build Agent run '${run.id}' view.`);
|
|
819
|
+
return view;
|
|
820
|
+
}
|
|
821
|
+
async function attachRunViews(runtime, runs) {
|
|
822
|
+
const executionIds = runs.map((run) => run.executionId);
|
|
823
|
+
const [executions, usages, costs] = await Promise.all([
|
|
824
|
+
Promise.all(runs.map((run) => runtime.storage.executions.getById({
|
|
825
|
+
projectId: runtime.projectId,
|
|
826
|
+
id: run.executionId
|
|
827
|
+
}))),
|
|
828
|
+
resolveExecutionUsage({
|
|
829
|
+
storage: runtime.storage.aiUsage,
|
|
830
|
+
projectId: runtime.projectId,
|
|
831
|
+
executionIds
|
|
832
|
+
}),
|
|
833
|
+
resolveExecutionCosts({
|
|
834
|
+
storage: runtime.storage.aiCosts,
|
|
835
|
+
projectId: runtime.projectId,
|
|
836
|
+
executionIds
|
|
837
|
+
})
|
|
838
|
+
]);
|
|
839
|
+
return runs.map((run, index) => {
|
|
840
|
+
const execution = executions[index];
|
|
841
|
+
if (!execution) {
|
|
842
|
+
throw new Error(`[Sixb] Agent run '${run.id}' references missing execution '${run.executionId}'.`);
|
|
843
|
+
}
|
|
844
|
+
const usage = usages[index];
|
|
845
|
+
const cost = usage === undefined ? undefined : costs[index];
|
|
846
|
+
return {
|
|
847
|
+
...run,
|
|
848
|
+
...execution.requestedBy === undefined ? {} : { requestedBy: structuredClone(execution.requestedBy) },
|
|
849
|
+
...usage === undefined ? {} : { usage },
|
|
850
|
+
...cost === undefined ? {} : { cost }
|
|
851
|
+
};
|
|
852
|
+
});
|
|
853
|
+
}
|
|
854
|
+
|
|
855
|
+
// src/ai-usage/execution.ts
|
|
856
|
+
import { randomUUID as randomUUID3 } from "crypto";
|
|
857
|
+
function createAiUsageRuntime(runtime, security) {
|
|
858
|
+
const assertObservable = () => assertAuthorized2(runtime, { kind: "aiUsage.observe" });
|
|
859
|
+
const assertManageable = () => assertAuthorized2(runtime, { kind: "aiUsage.manage" });
|
|
860
|
+
const assertPolicyReadable = () => {
|
|
861
|
+
if (!isRuntimeAllowed2(runtime, { kind: "aiUsage.observe" }) && !isRuntimeAllowed2(runtime, { kind: "aiUsage.manage" })) {
|
|
862
|
+
assertObservable();
|
|
863
|
+
}
|
|
864
|
+
};
|
|
865
|
+
const requireCosts = () => {
|
|
866
|
+
if (!runtime.storage.aiCosts) {
|
|
867
|
+
throw new Error("[Sixb] AI cost storage is not configured.");
|
|
868
|
+
}
|
|
869
|
+
return runtime.storage.aiCosts;
|
|
870
|
+
};
|
|
871
|
+
const requireLimits = () => {
|
|
872
|
+
if (!runtime.storage.aiLimits) {
|
|
873
|
+
throw new Error("[Sixb] AI limit storage is not configured.");
|
|
874
|
+
}
|
|
875
|
+
return runtime.storage.aiLimits;
|
|
876
|
+
};
|
|
877
|
+
return {
|
|
878
|
+
accountingConfigured: runtime.storage.aiCosts !== undefined,
|
|
879
|
+
limitsConfigured: runtime.storage.aiLimits !== undefined,
|
|
880
|
+
assertObservable,
|
|
881
|
+
assertManageable,
|
|
882
|
+
canManageLimits: () => isRuntimeAllowed2(runtime, { kind: "aiUsage.manage" }),
|
|
883
|
+
queryOverview: (input) => {
|
|
884
|
+
assertObservable();
|
|
885
|
+
return requireCosts().queryProjectOverview({ ...input, projectId: runtime.projectId });
|
|
886
|
+
},
|
|
887
|
+
listModelCalls: (input) => {
|
|
888
|
+
assertObservable();
|
|
889
|
+
return requireCosts().listModelCalls({ ...input, projectId: runtime.projectId });
|
|
890
|
+
},
|
|
891
|
+
listModelCallGroups: (input) => {
|
|
892
|
+
assertObservable();
|
|
893
|
+
return requireCosts().listModelCallGroups({ ...input, projectId: runtime.projectId });
|
|
894
|
+
},
|
|
895
|
+
listLimitPolicies: (input = {}) => {
|
|
896
|
+
assertPolicyReadable();
|
|
897
|
+
return requireLimits().listPolicies({ ...input, projectId: runtime.projectId });
|
|
898
|
+
},
|
|
899
|
+
listLimitStatuses: (input = {}) => {
|
|
900
|
+
assertObservable();
|
|
901
|
+
return requireLimits().listPolicyStatuses({
|
|
902
|
+
...input.includeDisabled === undefined ? {} : { includeDisabled: input.includeDisabled },
|
|
903
|
+
projectId: runtime.projectId,
|
|
904
|
+
existingGroupIds: security.listGroups().map((group) => group.id)
|
|
905
|
+
});
|
|
906
|
+
},
|
|
907
|
+
listLimitSubjectOptions: async () => {
|
|
908
|
+
assertManageable();
|
|
909
|
+
const groups = security.listGroups().map((group) => ({
|
|
910
|
+
id: group.id,
|
|
911
|
+
...group.label === undefined ? {} : { label: group.label },
|
|
912
|
+
...group.description === undefined ? {} : { description: group.description }
|
|
913
|
+
}));
|
|
914
|
+
const auth = runtime.storage.auth;
|
|
915
|
+
if (!auth)
|
|
916
|
+
return { groups, users: [], serviceAccounts: [] };
|
|
917
|
+
const [users, serviceAccounts] = await Promise.all([
|
|
918
|
+
auth.users.list({ projectId: runtime.projectId, order: "asc" }),
|
|
919
|
+
auth.serviceAccounts.list({ projectId: runtime.projectId, order: "asc" })
|
|
920
|
+
]);
|
|
921
|
+
return {
|
|
922
|
+
groups,
|
|
923
|
+
users: users.users.map((user) => ({
|
|
924
|
+
id: user.id,
|
|
925
|
+
email: user.email,
|
|
926
|
+
...user.displayName === undefined ? {} : { displayName: user.displayName },
|
|
927
|
+
status: user.status
|
|
928
|
+
})),
|
|
929
|
+
serviceAccounts: serviceAccounts.serviceAccounts.map((serviceAccount) => ({
|
|
930
|
+
id: serviceAccount.id,
|
|
931
|
+
name: serviceAccount.name,
|
|
932
|
+
...serviceAccount.description === undefined ? {} : { description: serviceAccount.description },
|
|
933
|
+
status: serviceAccount.status
|
|
934
|
+
}))
|
|
935
|
+
};
|
|
936
|
+
},
|
|
937
|
+
createLimitPolicy: (input) => {
|
|
938
|
+
assertManageable();
|
|
939
|
+
return requireLimits().createPolicy({
|
|
940
|
+
...input,
|
|
941
|
+
id: input.id ?? `ailim_${randomUUID3()}`,
|
|
942
|
+
projectId: runtime.projectId
|
|
943
|
+
});
|
|
944
|
+
},
|
|
945
|
+
updateLimitPolicy: (input) => {
|
|
946
|
+
assertManageable();
|
|
947
|
+
return requireLimits().updatePolicy({ ...input, projectId: runtime.projectId });
|
|
948
|
+
},
|
|
949
|
+
deleteLimitPolicy: (id) => {
|
|
950
|
+
assertManageable();
|
|
951
|
+
return requireLimits().deletePolicy({ id, projectId: runtime.projectId });
|
|
952
|
+
}
|
|
953
|
+
};
|
|
954
|
+
}
|
|
955
|
+
// src/blob-storage/execution.ts
|
|
956
|
+
function createBlobsRuntime(runtime, execution, blobStorage) {
|
|
957
|
+
const assertAccess = () => assertProviderAccess2(runtime, execution, "blobs.access");
|
|
958
|
+
const executionBlobs = {
|
|
959
|
+
put: (input) => {
|
|
960
|
+
assertAccess();
|
|
961
|
+
return blobStorage.put(input);
|
|
962
|
+
},
|
|
963
|
+
open: (blobId) => {
|
|
964
|
+
assertAccess();
|
|
965
|
+
return blobStorage.open(blobId);
|
|
966
|
+
},
|
|
967
|
+
stat: (blobId) => {
|
|
968
|
+
assertAccess();
|
|
969
|
+
return blobStorage.stat(blobId);
|
|
970
|
+
}
|
|
971
|
+
};
|
|
972
|
+
if (supportsRangeRead2(blobStorage)) {
|
|
973
|
+
executionBlobs.openRange = (blobId, range) => {
|
|
974
|
+
assertAccess();
|
|
975
|
+
return blobStorage.openRange(blobId, range);
|
|
976
|
+
};
|
|
977
|
+
}
|
|
978
|
+
if (supportsDirectUpload2(blobStorage)) {
|
|
979
|
+
executionBlobs.createUpload = (input) => {
|
|
980
|
+
assertAccess();
|
|
981
|
+
return blobStorage.createUpload(input);
|
|
982
|
+
};
|
|
983
|
+
executionBlobs.signUploadPart = (input) => {
|
|
984
|
+
assertAccess();
|
|
985
|
+
return blobStorage.signUploadPart(input);
|
|
986
|
+
};
|
|
987
|
+
executionBlobs.completeUpload = (input) => {
|
|
988
|
+
assertAccess();
|
|
989
|
+
return blobStorage.completeUpload(input);
|
|
990
|
+
};
|
|
991
|
+
executionBlobs.abortUpload = (input) => {
|
|
992
|
+
assertAccess();
|
|
993
|
+
return blobStorage.abortUpload(input);
|
|
994
|
+
};
|
|
995
|
+
}
|
|
996
|
+
return Object.freeze(executionBlobs);
|
|
997
|
+
}
|
|
998
|
+
|
|
999
|
+
// src/connectors/connections/execution.ts
|
|
1000
|
+
function createConnectorConnectionsRuntime(runtime, execution, process) {
|
|
1001
|
+
const contextFor = (connectorId) => commandContext(runtime, execution, connectorId);
|
|
1002
|
+
const connections = {
|
|
1003
|
+
listConnections: (connectorId) => process.listConnections(contextFor(connectorId), connectorId),
|
|
1004
|
+
startConnectionRun: (connectorId, input) => process.startConnectionRun(contextFor(connectorId), connectorId, input),
|
|
1005
|
+
addConnection: (connectorId, input) => process.addConnection(contextFor(connectorId), connectorId, input),
|
|
1006
|
+
getConnectionRun: (connectorId, runId) => process.getConnectionRun(contextFor(connectorId), connectorId, runId),
|
|
1007
|
+
selectConnectionRunAccount: (connectorId, input) => process.selectConnectionRunAccount(contextFor(connectorId), connectorId, input),
|
|
1008
|
+
startReauthorization: (connectorId, connectionId, input) => process.startReauthorization(contextFor(connectorId), connectorId, connectionId, input),
|
|
1009
|
+
revokeConnection: (connectorId, connectionId) => process.revokeConnection(contextFor(connectorId), connectorId, connectionId),
|
|
1010
|
+
startAuthorization: (connectorId, input) => process.startAuthorization(contextFor(connectorId), connectorId, input),
|
|
1011
|
+
completeAuthorization: (connectorId, input) => process.completeAuthorization(contextFor(connectorId), connectorId, input),
|
|
1012
|
+
selectAccount: (connectorId, input) => process.selectAccount(contextFor(connectorId), connectorId, input),
|
|
1013
|
+
disconnect: (connectorId, connectionId) => process.disconnect(contextFor(connectorId), connectorId, connectionId),
|
|
1014
|
+
revokeAuthorization: (connectorId, authorizationId) => process.revokeAuthorization(contextFor(connectorId), connectorId, authorizationId)
|
|
1015
|
+
};
|
|
1016
|
+
return Object.freeze(connections);
|
|
1017
|
+
}
|
|
1018
|
+
function commandContext(runtime, execution, connectorId) {
|
|
1019
|
+
const resolved = resolveExecutionScopeAuthorization(runtime.projectId, {
|
|
1020
|
+
execution,
|
|
1021
|
+
authorization: runtime.runtimeAuthorization
|
|
1022
|
+
});
|
|
1023
|
+
if (execution.executor.type !== "request" || resolved.type !== "principal" || resolved.ref.type !== "principal") {
|
|
1024
|
+
throw new AuthorizationError2(`manage:connector:${connectorId}`, "[Sixb] Connector connections can only be managed by an authenticated request.");
|
|
1025
|
+
}
|
|
1026
|
+
if (!resolved.ref.credential) {
|
|
1027
|
+
throw new AuthorizationError2(`manage:connector:${connectorId}`, "[Sixb] Connector connection management requires a session or access token.");
|
|
1028
|
+
}
|
|
1029
|
+
assertCanManageConnector2(runtime, connectorId);
|
|
1030
|
+
return Object.freeze({
|
|
1031
|
+
execution: Object.freeze(executionRecordInputFromRuntime({
|
|
1032
|
+
execution,
|
|
1033
|
+
runtimeAuthorization: runtime.runtimeAuthorization
|
|
1034
|
+
}))
|
|
1035
|
+
});
|
|
1036
|
+
}
|
|
1037
|
+
|
|
1038
|
+
// src/datasets/execution.ts
|
|
1039
|
+
function createDatasetsRuntime(runtime, execution, source, lakeStorage, blobStorage) {
|
|
1040
|
+
const authority = resolveRuntimeAuthorizationForProject(runtime);
|
|
1041
|
+
const allowed = (datasetId) => isRuntimeAllowed2(runtime, { kind: "dataset.view", datasetId });
|
|
1042
|
+
return {
|
|
1043
|
+
list: () => authority.type === "denied" || authority.type === "delegated" ? [] : source.list().filter((dataset) => allowed(dataset.id)),
|
|
1044
|
+
getById: (datasetId) => {
|
|
1045
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
1046
|
+
return null;
|
|
1047
|
+
const dataset = source.getById(datasetId);
|
|
1048
|
+
return dataset && allowed(datasetId) ? dataset : null;
|
|
1049
|
+
},
|
|
1050
|
+
async ingest(dataset, input) {
|
|
1051
|
+
assertPrivileged2(runtime, "datasets.ingest");
|
|
1052
|
+
const registered = source.getById(dataset.id);
|
|
1053
|
+
if (!registered)
|
|
1054
|
+
throw new Error(`[Sixb] Dataset '${dataset.id}' is not registered.`);
|
|
1055
|
+
if (getDatasetPrimaryKeyColumns2(registered) === null) {
|
|
1056
|
+
throw new Error(`[Sixb] Dataset '${dataset.id}' must define a primaryKey before ingestion.`);
|
|
1057
|
+
}
|
|
1058
|
+
if (typeof lakeStorage.beginMerge !== "function") {
|
|
1059
|
+
throw new Error("[Sixb] Dataset ingestion requires a lake provider with merge support.");
|
|
1060
|
+
}
|
|
1061
|
+
const producer = { kind: "ingest", id: execution.id };
|
|
1062
|
+
const result = await writeDataset2({
|
|
1063
|
+
lakeStorage,
|
|
1064
|
+
blobStorage,
|
|
1065
|
+
dataset: registered,
|
|
1066
|
+
mode: "merge",
|
|
1067
|
+
signal: input.signal ?? new AbortController().signal,
|
|
1068
|
+
producer,
|
|
1069
|
+
readValues: async () => async function* () {
|
|
1070
|
+
for await (const value of input.changes)
|
|
1071
|
+
yield { value };
|
|
1072
|
+
}()
|
|
1073
|
+
});
|
|
1074
|
+
if (result.outcome === "created") {
|
|
1075
|
+
await runtime.events.emit({
|
|
1076
|
+
events: [
|
|
1077
|
+
{
|
|
1078
|
+
type: "dataset.version.committed",
|
|
1079
|
+
payload: {
|
|
1080
|
+
datasetId: registered.id,
|
|
1081
|
+
versionId: result.version.versionId,
|
|
1082
|
+
createdAt: result.version.createdAt.toISOString(),
|
|
1083
|
+
producer
|
|
1084
|
+
}
|
|
1085
|
+
}
|
|
1086
|
+
],
|
|
1087
|
+
correlationId: execution.correlationId
|
|
1088
|
+
}, { source: "SixbDatasets" });
|
|
1089
|
+
}
|
|
1090
|
+
return result;
|
|
1091
|
+
}
|
|
1092
|
+
};
|
|
1093
|
+
}
|
|
1094
|
+
|
|
1095
|
+
// src/events/execution.ts
|
|
1096
|
+
function createEventsRuntime(runtime) {
|
|
1097
|
+
const authority = resolveRuntimeAuthorizationForProject(runtime);
|
|
1098
|
+
const visibleEvents = (events) => {
|
|
1099
|
+
switch (authority.type) {
|
|
1100
|
+
case "denied":
|
|
1101
|
+
case "delegated":
|
|
1102
|
+
return [];
|
|
1103
|
+
case "principal":
|
|
1104
|
+
return events.filter((event) => canViewEvent2(authority.context, event));
|
|
1105
|
+
case "unrestricted":
|
|
1106
|
+
return [...events];
|
|
1107
|
+
}
|
|
1108
|
+
};
|
|
1109
|
+
return {
|
|
1110
|
+
canRead: (event) => {
|
|
1111
|
+
switch (authority.type) {
|
|
1112
|
+
case "denied":
|
|
1113
|
+
case "delegated":
|
|
1114
|
+
return false;
|
|
1115
|
+
case "principal":
|
|
1116
|
+
return canViewEvent2(authority.context, event);
|
|
1117
|
+
case "unrestricted":
|
|
1118
|
+
return true;
|
|
1119
|
+
}
|
|
1120
|
+
},
|
|
1121
|
+
append: (input) => {
|
|
1122
|
+
assertPrivileged2(runtime, "events.append");
|
|
1123
|
+
return runtime.events.append(input);
|
|
1124
|
+
},
|
|
1125
|
+
emit: (input, options) => {
|
|
1126
|
+
assertPrivileged2(runtime, "events.emit");
|
|
1127
|
+
return runtime.events.emit(input, options);
|
|
1128
|
+
},
|
|
1129
|
+
read: async (input) => {
|
|
1130
|
+
switch (authority.type) {
|
|
1131
|
+
case "denied":
|
|
1132
|
+
case "delegated":
|
|
1133
|
+
return [];
|
|
1134
|
+
case "principal":
|
|
1135
|
+
case "unrestricted":
|
|
1136
|
+
break;
|
|
1137
|
+
}
|
|
1138
|
+
const events = await runtime.events.read(input);
|
|
1139
|
+
return visibleEvents(events);
|
|
1140
|
+
},
|
|
1141
|
+
latestCursor: () => {
|
|
1142
|
+
switch (authority.type) {
|
|
1143
|
+
case "denied":
|
|
1144
|
+
case "delegated":
|
|
1145
|
+
return Promise.resolve(undefined);
|
|
1146
|
+
case "principal":
|
|
1147
|
+
case "unrestricted":
|
|
1148
|
+
return runtime.events.latestCursor();
|
|
1149
|
+
}
|
|
1150
|
+
},
|
|
1151
|
+
subscribe: (input, handler) => {
|
|
1152
|
+
switch (authority.type) {
|
|
1153
|
+
case "denied":
|
|
1154
|
+
case "delegated":
|
|
1155
|
+
return Promise.resolve(() => {});
|
|
1156
|
+
case "principal":
|
|
1157
|
+
case "unrestricted":
|
|
1158
|
+
break;
|
|
1159
|
+
}
|
|
1160
|
+
return runtime.events.subscribe(input, (events) => {
|
|
1161
|
+
const visible = visibleEvents(events);
|
|
1162
|
+
if (visible.length > 0)
|
|
1163
|
+
handler(visible);
|
|
1164
|
+
});
|
|
1165
|
+
}
|
|
1166
|
+
};
|
|
1167
|
+
}
|
|
1168
|
+
|
|
1169
|
+
// src/logging/execution.ts
|
|
1170
|
+
function createLogsRuntime(runtime, source) {
|
|
1171
|
+
const assertObservable = () => assertAuthorized2(runtime, { kind: "logs.observe" });
|
|
1172
|
+
return {
|
|
1173
|
+
assertObservable,
|
|
1174
|
+
read: (input) => {
|
|
1175
|
+
assertObservable();
|
|
1176
|
+
return source.read(input);
|
|
1177
|
+
},
|
|
1178
|
+
tail: (input) => {
|
|
1179
|
+
assertObservable();
|
|
1180
|
+
return source.tail(input);
|
|
1181
|
+
}
|
|
1182
|
+
};
|
|
1183
|
+
}
|
|
1184
|
+
|
|
1185
|
+
// src/agents/model-loop.ts
|
|
1186
|
+
import { randomUUID as randomUUID4 } from "crypto";
|
|
1187
|
+
var MAX_PROVIDER_DATA_BYTES = 256 * 1024;
|
|
1188
|
+
async function runModelLoop2(input) {
|
|
1189
|
+
assertLoopInput(input);
|
|
1190
|
+
const tools = indexTools(input.tools ?? []);
|
|
1191
|
+
const toolSpecifications = [...tools.values()].map((tool) => ({
|
|
1192
|
+
name: tool.name,
|
|
1193
|
+
description: tool.description,
|
|
1194
|
+
inputSchema: tool.inputSchema
|
|
1195
|
+
}));
|
|
1196
|
+
let messages = [...input.messages];
|
|
1197
|
+
const steps = [];
|
|
1198
|
+
const generateCallId = input.generateCallId ?? (() => `model_call_${randomUUID4()}`);
|
|
1199
|
+
const callIds = new Set;
|
|
1200
|
+
for (let stepIndex = 0;stepIndex < input.maxSteps; stepIndex += 1) {
|
|
1201
|
+
if (input.signal.aborted) {
|
|
1202
|
+
return { status: "aborted", steps, partialContent: [] };
|
|
1203
|
+
}
|
|
1204
|
+
await input.onEvent?.({ type: "start-step" });
|
|
1205
|
+
let requestMessages;
|
|
1206
|
+
try {
|
|
1207
|
+
const prepared = await input.prepareStep?.({
|
|
1208
|
+
stepIndex,
|
|
1209
|
+
messages,
|
|
1210
|
+
model: input.model,
|
|
1211
|
+
signal: input.signal
|
|
1212
|
+
});
|
|
1213
|
+
requestMessages = prepared?.messages ?? messages;
|
|
1214
|
+
} catch (error) {
|
|
1215
|
+
if (!input.signal.aborted && !isAbortError(error))
|
|
1216
|
+
throw error;
|
|
1217
|
+
return { status: "aborted", steps, partialContent: [] };
|
|
1218
|
+
}
|
|
1219
|
+
if (input.signal.aborted) {
|
|
1220
|
+
return { status: "aborted", steps, partialContent: [] };
|
|
1221
|
+
}
|
|
1222
|
+
let requestTools = toolSpecifications;
|
|
1223
|
+
if (input.finalStepInstruction !== undefined && stepIndex === input.maxSteps - 1) {
|
|
1224
|
+
requestMessages = [
|
|
1225
|
+
...requestMessages,
|
|
1226
|
+
{ role: "user", content: [{ type: "text", text: input.finalStepInstruction }] }
|
|
1227
|
+
];
|
|
1228
|
+
requestTools = [];
|
|
1229
|
+
}
|
|
1230
|
+
const callId = generateCallId();
|
|
1231
|
+
if (!callId || callIds.has(callId)) {
|
|
1232
|
+
throw new ModelStreamError2(`[SixbModels] Model call IDs must be nonempty and unique.`);
|
|
1233
|
+
}
|
|
1234
|
+
callIds.add(callId);
|
|
1235
|
+
const accumulator = new StreamAccumulator(input.onEvent);
|
|
1236
|
+
let accepted = false;
|
|
1237
|
+
let cost = { status: "unpriceable", reason: "missing-usage" };
|
|
1238
|
+
let terminalStreamError;
|
|
1239
|
+
try {
|
|
1240
|
+
const stream = await input.model.stream({
|
|
1241
|
+
callId,
|
|
1242
|
+
messages: requestMessages,
|
|
1243
|
+
tools: requestTools,
|
|
1244
|
+
...input.reasoning === undefined ? {} : { reasoning: input.reasoning },
|
|
1245
|
+
...input.maxOutputTokens === undefined ? {} : { maxOutputTokens: input.maxOutputTokens },
|
|
1246
|
+
...input.caching === undefined ? {} : { caching: input.caching },
|
|
1247
|
+
...input.output === undefined ? {} : {
|
|
1248
|
+
responseFormat: {
|
|
1249
|
+
type: "json",
|
|
1250
|
+
name: input.output.name,
|
|
1251
|
+
...input.output.description === undefined ? {} : { description: input.output.description },
|
|
1252
|
+
schema: input.output.schema
|
|
1253
|
+
}
|
|
1254
|
+
},
|
|
1255
|
+
signal: input.signal
|
|
1256
|
+
});
|
|
1257
|
+
accepted = true;
|
|
1258
|
+
for await (const event of stream.events) {
|
|
1259
|
+
await accumulator.accept(event);
|
|
1260
|
+
}
|
|
1261
|
+
} catch (error) {
|
|
1262
|
+
const aborted = input.signal.aborted || isAbortError(error);
|
|
1263
|
+
if (accumulator.isFinished()) {
|
|
1264
|
+
if (!aborted)
|
|
1265
|
+
terminalStreamError = { error };
|
|
1266
|
+
} else if (!aborted) {
|
|
1267
|
+
throw error;
|
|
1268
|
+
} else {
|
|
1269
|
+
return {
|
|
1270
|
+
status: "aborted",
|
|
1271
|
+
steps,
|
|
1272
|
+
partialContent: accumulator.partialContent()
|
|
1273
|
+
};
|
|
1274
|
+
}
|
|
1275
|
+
} finally {
|
|
1276
|
+
if (accepted) {
|
|
1277
|
+
const facts = accumulator.accounting();
|
|
1278
|
+
const estimate = accumulator.isFinished() ? estimateModelCall(input.model, facts) : cost;
|
|
1279
|
+
cost = facts.reportedCost ? rateModelCall2({ usage: facts.usage, reported: facts.reportedCost }) : estimate;
|
|
1280
|
+
await input.onModelCallEnd?.({
|
|
1281
|
+
callId,
|
|
1282
|
+
providerId: input.model.providerId,
|
|
1283
|
+
modelId: input.model.modelId,
|
|
1284
|
+
responseId: facts.responseId ?? `${callId}:response`,
|
|
1285
|
+
providerIds: facts.providerIds,
|
|
1286
|
+
responseModelId: facts.responseModelId,
|
|
1287
|
+
usage: facts.usage,
|
|
1288
|
+
cost,
|
|
1289
|
+
...facts.reportedCost === undefined ? {} : { estimate },
|
|
1290
|
+
...input.reasoning === undefined ? {} : { requestedReasoning: input.reasoning },
|
|
1291
|
+
...facts.route === undefined ? {} : { route: facts.route }
|
|
1292
|
+
});
|
|
1293
|
+
}
|
|
1294
|
+
}
|
|
1295
|
+
if (input.signal.aborted && !accumulator.isFinished()) {
|
|
1296
|
+
return { status: "aborted", steps, partialContent: accumulator.partialContent() };
|
|
1297
|
+
}
|
|
1298
|
+
const response = accumulator.complete();
|
|
1299
|
+
const responseId = response.responseId ?? `${callId}:response`;
|
|
1300
|
+
if (terminalStreamError)
|
|
1301
|
+
throw terminalStreamError.error;
|
|
1302
|
+
if (response.projectionError)
|
|
1303
|
+
throw response.projectionError;
|
|
1304
|
+
if (input.signal.aborted) {
|
|
1305
|
+
return { status: "aborted", steps, partialContent: response.content };
|
|
1306
|
+
}
|
|
1307
|
+
const localCalls = response.toolCalls.filter((call) => call.part.providerExecuted !== true);
|
|
1308
|
+
if (input.rejectLocalToolCalls && (localCalls.length > 0 || response.finishReason === "tool-calls")) {
|
|
1309
|
+
throw new ModelStreamError2("[SixbModels] Direct generation cannot continue local tool calls.");
|
|
1310
|
+
}
|
|
1311
|
+
if (response.finishReason === "pause" && localCalls.length === 0) {
|
|
1312
|
+
const step = modelStep(response, responseId, response.content, cost);
|
|
1313
|
+
steps.push(step);
|
|
1314
|
+
await input.onStepEnd?.(step);
|
|
1315
|
+
messages = [...requestMessages, { role: "assistant", content: response.content }];
|
|
1316
|
+
if (stepIndex + 1 === input.maxSteps) {
|
|
1317
|
+
throw new ModelStreamError2("[SixbModels] Model reached the step limit while a provider continuation was pending.");
|
|
1318
|
+
}
|
|
1319
|
+
continue;
|
|
1320
|
+
}
|
|
1321
|
+
if (localCalls.length === 0) {
|
|
1322
|
+
const step = modelStep(response, responseId, response.content, cost);
|
|
1323
|
+
steps.push(step);
|
|
1324
|
+
await input.onStepEnd?.(step);
|
|
1325
|
+
if (input.output) {
|
|
1326
|
+
const text = responseText(response);
|
|
1327
|
+
if (response.finishReason !== "stop") {
|
|
1328
|
+
throw new StructuredOutputError2(`[SixbModels] Structured output did not complete successfully (${response.finishReason}).`, structuredOutputErrorContext(input, response, responseId, cost, text));
|
|
1329
|
+
}
|
|
1330
|
+
let raw;
|
|
1331
|
+
try {
|
|
1332
|
+
raw = JSON.parse(text);
|
|
1333
|
+
} catch (error) {
|
|
1334
|
+
throw new StructuredOutputError2("[SixbModels] Model did not produce valid JSON output.", {
|
|
1335
|
+
cause: error,
|
|
1336
|
+
...structuredOutputErrorContext(input, response, responseId, cost, text)
|
|
1337
|
+
});
|
|
1338
|
+
}
|
|
1339
|
+
try {
|
|
1340
|
+
return {
|
|
1341
|
+
status: "completed",
|
|
1342
|
+
output: input.output.validate(raw),
|
|
1343
|
+
steps,
|
|
1344
|
+
finishReason: response.finishReason
|
|
1345
|
+
};
|
|
1346
|
+
} catch (error) {
|
|
1347
|
+
throw new StructuredOutputError2("[SixbModels] Structured output validation failed.", {
|
|
1348
|
+
cause: error,
|
|
1349
|
+
...structuredOutputErrorContext(input, response, responseId, cost, text)
|
|
1350
|
+
});
|
|
1351
|
+
}
|
|
1352
|
+
}
|
|
1353
|
+
const output = responseText(response);
|
|
1354
|
+
return { status: "completed", output, steps, finishReason: response.finishReason };
|
|
1355
|
+
}
|
|
1356
|
+
const toolResults = await Promise.all(localCalls.map((call) => executeToolCall(call, tools, callId, input.signal, input.onEvent)));
|
|
1357
|
+
const step = modelStep(response, responseId, [...response.content, ...toolResults], cost);
|
|
1358
|
+
steps.push(step);
|
|
1359
|
+
await input.onStepEnd?.(step);
|
|
1360
|
+
if (input.signal.aborted) {
|
|
1361
|
+
return {
|
|
1362
|
+
status: "aborted",
|
|
1363
|
+
steps,
|
|
1364
|
+
partialContent: []
|
|
1365
|
+
};
|
|
1366
|
+
}
|
|
1367
|
+
const assistantContent = response.content.filter((part) => part.type !== "tool-result" || part.providerExecuted === true);
|
|
1368
|
+
messages = [
|
|
1369
|
+
...requestMessages,
|
|
1370
|
+
{ role: "assistant", content: assistantContent },
|
|
1371
|
+
{ role: "tool", content: toolResults }
|
|
1372
|
+
];
|
|
1373
|
+
if (stepIndex + 1 === input.maxSteps) {
|
|
1374
|
+
if (input.output) {
|
|
1375
|
+
throw new StructuredOutputError2("[SixbModels] Model reached the step limit without structured output.", structuredOutputErrorContext(input, response, responseId, cost, responseText(response)));
|
|
1376
|
+
}
|
|
1377
|
+
const output = responseText(response);
|
|
1378
|
+
return { status: "completed", output, steps, finishReason: response.finishReason };
|
|
1379
|
+
}
|
|
1380
|
+
}
|
|
1381
|
+
throw new ModelStreamError2("[SixbModels] Model loop exited without a terminal result.");
|
|
1382
|
+
}
|
|
1383
|
+
function assertLoopInput(input) {
|
|
1384
|
+
if (input.maxOutputTokens !== undefined && (!Number.isSafeInteger(input.maxOutputTokens) || input.maxOutputTokens <= 0)) {
|
|
1385
|
+
throw new TypeError("[SixbModels] maxOutputTokens must be a positive safe integer.");
|
|
1386
|
+
}
|
|
1387
|
+
if (!Number.isInteger(input.maxSteps) || input.maxSteps <= 0) {
|
|
1388
|
+
throw new TypeError("[SixbModels] maxSteps must be a positive integer.");
|
|
1389
|
+
}
|
|
1390
|
+
if (!input.model.providerId.trim() || !input.model.modelId.trim()) {
|
|
1391
|
+
throw new TypeError("[SixbModels] Model providerId and modelId must not be empty.");
|
|
1392
|
+
}
|
|
1393
|
+
if (input.model.definition.providerId !== input.model.providerId || input.model.definition.modelId !== input.model.modelId) {
|
|
1394
|
+
throw new TypeError(`[SixbModels] Model definition for '${input.model.providerId}/${input.model.modelId}' has a different identity.`);
|
|
1395
|
+
}
|
|
1396
|
+
if (input.output) {
|
|
1397
|
+
if (!input.output.name.trim()) {
|
|
1398
|
+
throw new TypeError("[SixbModels] Structured output names must not be empty.");
|
|
1399
|
+
}
|
|
1400
|
+
assertJsonObject2(input.output.schema, "structured output schema");
|
|
1401
|
+
}
|
|
1402
|
+
}
|
|
1403
|
+
function indexTools(tools) {
|
|
1404
|
+
const result = new Map;
|
|
1405
|
+
for (const tool of tools) {
|
|
1406
|
+
if (!tool.name.trim())
|
|
1407
|
+
throw new TypeError("[SixbModels] Tool names must not be empty.");
|
|
1408
|
+
if (result.has(tool.name)) {
|
|
1409
|
+
throw new TypeError(`[SixbModels] Duplicate tool name '${tool.name}'.`);
|
|
1410
|
+
}
|
|
1411
|
+
assertJsonObject2(tool.inputSchema, `tool '${tool.name}' input schema`);
|
|
1412
|
+
result.set(tool.name, tool);
|
|
1413
|
+
}
|
|
1414
|
+
return result;
|
|
1415
|
+
}
|
|
1416
|
+
function responseText(response) {
|
|
1417
|
+
return response.content.filter((part) => part.type === "text").map((part) => part.text).join("");
|
|
1418
|
+
}
|
|
1419
|
+
function structuredOutputErrorContext(input, response, responseId, cost, text) {
|
|
1420
|
+
return {
|
|
1421
|
+
text,
|
|
1422
|
+
providerId: input.model.providerId,
|
|
1423
|
+
modelId: input.model.modelId,
|
|
1424
|
+
responseId,
|
|
1425
|
+
...response.responseModelId === undefined ? {} : { responseModelId: response.responseModelId },
|
|
1426
|
+
finishReason: response.finishReason,
|
|
1427
|
+
usage: response.usage,
|
|
1428
|
+
cost
|
|
1429
|
+
};
|
|
1430
|
+
}
|
|
1431
|
+
function modelStep(response, responseId, content, cost) {
|
|
1432
|
+
return {
|
|
1433
|
+
content,
|
|
1434
|
+
finishReason: response.finishReason,
|
|
1435
|
+
...response.rawFinishReason === undefined ? {} : { rawFinishReason: response.rawFinishReason },
|
|
1436
|
+
usage: response.usage,
|
|
1437
|
+
responseId,
|
|
1438
|
+
...response.responseModelId === undefined ? {} : { responseModelId: response.responseModelId },
|
|
1439
|
+
cost,
|
|
1440
|
+
...response.route === undefined ? {} : { route: response.route }
|
|
1441
|
+
};
|
|
1442
|
+
}
|
|
1443
|
+
async function executeToolCall(call, tools, callId, signal, onEvent) {
|
|
1444
|
+
const { part } = call;
|
|
1445
|
+
if (call.inputError) {
|
|
1446
|
+
const errorText = `Tool input is not valid JSON: ${call.inputError.message}`;
|
|
1447
|
+
await onEvent?.({
|
|
1448
|
+
type: "tool-input-error",
|
|
1449
|
+
toolCallId: part.toolCallId,
|
|
1450
|
+
toolName: part.toolName,
|
|
1451
|
+
input: part.input,
|
|
1452
|
+
errorText
|
|
1453
|
+
});
|
|
1454
|
+
return toolErrorResult(part, errorText);
|
|
1455
|
+
}
|
|
1456
|
+
const tool = tools.get(part.toolName);
|
|
1457
|
+
if (!tool) {
|
|
1458
|
+
const errorText = `Tool '${part.toolName}' is not available.`;
|
|
1459
|
+
await onEvent?.({
|
|
1460
|
+
type: "tool-output-error",
|
|
1461
|
+
toolCallId: part.toolCallId,
|
|
1462
|
+
toolName: part.toolName,
|
|
1463
|
+
errorText
|
|
1464
|
+
});
|
|
1465
|
+
return toolErrorResult(part, errorText);
|
|
1466
|
+
}
|
|
1467
|
+
let parsed;
|
|
1468
|
+
try {
|
|
1469
|
+
parsed = tool.parseInput(part.input);
|
|
1470
|
+
} catch (error) {
|
|
1471
|
+
const errorText = error instanceof Error ? error.message : "Tool input validation failed.";
|
|
1472
|
+
await onEvent?.({
|
|
1473
|
+
type: "tool-input-error",
|
|
1474
|
+
toolCallId: part.toolCallId,
|
|
1475
|
+
toolName: part.toolName,
|
|
1476
|
+
input: part.input,
|
|
1477
|
+
errorText
|
|
1478
|
+
});
|
|
1479
|
+
return toolErrorResult(part, errorText);
|
|
1480
|
+
}
|
|
1481
|
+
await onEvent?.({
|
|
1482
|
+
type: "tool-input-available",
|
|
1483
|
+
toolCallId: part.toolCallId,
|
|
1484
|
+
toolName: part.toolName,
|
|
1485
|
+
input: part.input
|
|
1486
|
+
});
|
|
1487
|
+
let output;
|
|
1488
|
+
let modelOutput;
|
|
1489
|
+
try {
|
|
1490
|
+
const context = { signal, callId, toolCallId: part.toolCallId };
|
|
1491
|
+
output = await tool.execute(parsed, context);
|
|
1492
|
+
assertJsonValue2(output, `tool '${part.toolName}' output`);
|
|
1493
|
+
modelOutput = tool.toModelOutput ? await tool.toModelOutput(output, context) : modelToolOutput(output);
|
|
1494
|
+
validateModelToolOutput(modelOutput, part.toolName);
|
|
1495
|
+
} catch (error) {
|
|
1496
|
+
const errorText = tool.errorText(error);
|
|
1497
|
+
await onEvent?.({
|
|
1498
|
+
type: "tool-output-error",
|
|
1499
|
+
toolCallId: part.toolCallId,
|
|
1500
|
+
toolName: part.toolName,
|
|
1501
|
+
errorText
|
|
1502
|
+
});
|
|
1503
|
+
return toolErrorResult(part, errorText);
|
|
1504
|
+
}
|
|
1505
|
+
await onEvent?.({
|
|
1506
|
+
type: "tool-output-available",
|
|
1507
|
+
toolCallId: part.toolCallId,
|
|
1508
|
+
toolName: part.toolName,
|
|
1509
|
+
output
|
|
1510
|
+
});
|
|
1511
|
+
return {
|
|
1512
|
+
type: "tool-result",
|
|
1513
|
+
toolCallId: part.toolCallId,
|
|
1514
|
+
toolName: part.toolName,
|
|
1515
|
+
output: modelOutput,
|
|
1516
|
+
...modelOutputMatchesOriginal(modelOutput, output) ? {} : { originalOutput: output }
|
|
1517
|
+
};
|
|
1518
|
+
}
|
|
1519
|
+
function validateModelToolOutput(output, toolName) {
|
|
1520
|
+
if (output.type === "text" || output.type === "error-text") {
|
|
1521
|
+
if (typeof output.value !== "string") {
|
|
1522
|
+
throw new TypeError(`[SixbModels] Tool '${toolName}' model output must contain text.`);
|
|
1523
|
+
}
|
|
1524
|
+
return;
|
|
1525
|
+
}
|
|
1526
|
+
if (output.type !== "json" && output.type !== "error-json") {
|
|
1527
|
+
throw new TypeError(`[SixbModels] Tool '${toolName}' returned an unsupported model output type.`);
|
|
1528
|
+
}
|
|
1529
|
+
assertJsonValue2(output.value, `tool '${toolName}' model output`);
|
|
1530
|
+
}
|
|
1531
|
+
function modelOutputMatchesOriginal(output, original) {
|
|
1532
|
+
if (output.type === "text")
|
|
1533
|
+
return typeof original === "string" && output.value === original;
|
|
1534
|
+
if (output.type === "json")
|
|
1535
|
+
return output.value === original;
|
|
1536
|
+
return false;
|
|
1537
|
+
}
|
|
1538
|
+
function modelToolOutput(value) {
|
|
1539
|
+
return typeof value === "string" ? { type: "text", value } : { type: "json", value };
|
|
1540
|
+
}
|
|
1541
|
+
function toolErrorResult(part, errorText) {
|
|
1542
|
+
if (typeof errorText !== "string") {
|
|
1543
|
+
throw new TypeError(`[SixbModels] Tool '${part.toolName}' error text must be a string.`);
|
|
1544
|
+
}
|
|
1545
|
+
return {
|
|
1546
|
+
type: "tool-result",
|
|
1547
|
+
toolCallId: part.toolCallId,
|
|
1548
|
+
toolName: part.toolName,
|
|
1549
|
+
output: { type: "error-text", value: errorText }
|
|
1550
|
+
};
|
|
1551
|
+
}
|
|
1552
|
+
|
|
1553
|
+
class StreamAccumulator {
|
|
1554
|
+
onEvent;
|
|
1555
|
+
parts = [];
|
|
1556
|
+
spans = new Map;
|
|
1557
|
+
toolCalls = new Map;
|
|
1558
|
+
started = false;
|
|
1559
|
+
finished = false;
|
|
1560
|
+
finishReason;
|
|
1561
|
+
rawFinishReason;
|
|
1562
|
+
usage = {};
|
|
1563
|
+
responseId;
|
|
1564
|
+
providerIds;
|
|
1565
|
+
responseModelId;
|
|
1566
|
+
projectionError;
|
|
1567
|
+
reportedCost;
|
|
1568
|
+
route;
|
|
1569
|
+
constructor(onEvent) {
|
|
1570
|
+
this.onEvent = onEvent;
|
|
1571
|
+
}
|
|
1572
|
+
isFinished() {
|
|
1573
|
+
return this.finished;
|
|
1574
|
+
}
|
|
1575
|
+
async accept(event) {
|
|
1576
|
+
if (this.finished) {
|
|
1577
|
+
throw new ModelStreamError2(`[SixbModels] Received '${event.type}' after stream finish.`);
|
|
1578
|
+
}
|
|
1579
|
+
switch (event.type) {
|
|
1580
|
+
case "stream-start":
|
|
1581
|
+
if (this.started)
|
|
1582
|
+
throw new ModelStreamError2("[SixbModels] Duplicate stream-start event.");
|
|
1583
|
+
this.started = true;
|
|
1584
|
+
return;
|
|
1585
|
+
case "response-metadata":
|
|
1586
|
+
this.requireStarted(event.type);
|
|
1587
|
+
this.responseId = event.id ?? this.responseId;
|
|
1588
|
+
if (event.providerIds)
|
|
1589
|
+
this.providerIds = { ...this.providerIds, ...event.providerIds };
|
|
1590
|
+
this.responseModelId = event.modelId ?? this.responseModelId;
|
|
1591
|
+
return;
|
|
1592
|
+
case "text-start":
|
|
1593
|
+
await this.startText(event);
|
|
1594
|
+
return;
|
|
1595
|
+
case "text-delta":
|
|
1596
|
+
await this.appendText(event, "text");
|
|
1597
|
+
return;
|
|
1598
|
+
case "text-end":
|
|
1599
|
+
await this.endText(event, "text");
|
|
1600
|
+
return;
|
|
1601
|
+
case "reasoning-start":
|
|
1602
|
+
await this.startReasoning(event);
|
|
1603
|
+
return;
|
|
1604
|
+
case "reasoning-delta":
|
|
1605
|
+
await this.appendText(event, "reasoning");
|
|
1606
|
+
return;
|
|
1607
|
+
case "reasoning-end":
|
|
1608
|
+
await this.endText(event, "reasoning");
|
|
1609
|
+
return;
|
|
1610
|
+
case "tool-input-start":
|
|
1611
|
+
await this.startTool(event);
|
|
1612
|
+
return;
|
|
1613
|
+
case "tool-input-delta":
|
|
1614
|
+
await this.appendTool(event);
|
|
1615
|
+
return;
|
|
1616
|
+
case "tool-input-end":
|
|
1617
|
+
this.endTool(event);
|
|
1618
|
+
return;
|
|
1619
|
+
case "tool-call":
|
|
1620
|
+
await this.completeTool(event);
|
|
1621
|
+
return;
|
|
1622
|
+
case "tool-result":
|
|
1623
|
+
this.addProviderToolResult(event);
|
|
1624
|
+
return;
|
|
1625
|
+
case "provider-state":
|
|
1626
|
+
if (typeof event.providerId !== "string" || event.providerId.length === 0) {
|
|
1627
|
+
this.captureProjectionError(new ModelStreamError2("[SixbModels] Provider state requires a nonempty provider ID."));
|
|
1628
|
+
return;
|
|
1629
|
+
}
|
|
1630
|
+
if (this.captureProviderState(event.data)) {
|
|
1631
|
+
this.parts.push({
|
|
1632
|
+
type: "provider-state",
|
|
1633
|
+
providerId: event.providerId,
|
|
1634
|
+
data: event.data
|
|
1635
|
+
});
|
|
1636
|
+
}
|
|
1637
|
+
return;
|
|
1638
|
+
case "finish":
|
|
1639
|
+
this.requireStarted(event.type);
|
|
1640
|
+
validateUsage(event.usage);
|
|
1641
|
+
this.captureProviderData(event.providerData);
|
|
1642
|
+
this.finished = true;
|
|
1643
|
+
this.finishReason = event.finishReason;
|
|
1644
|
+
this.rawFinishReason = event.rawFinishReason;
|
|
1645
|
+
this.usage = event.usage;
|
|
1646
|
+
this.reportedCost = event.reportedCost;
|
|
1647
|
+
this.route = event.route;
|
|
1648
|
+
return;
|
|
1649
|
+
case "error":
|
|
1650
|
+
throw event.error instanceof Error ? event.error : new ModelProviderError2("[SixbModels] Provider stream failed.", "unknown", "unknown", {
|
|
1651
|
+
cause: event.error
|
|
1652
|
+
});
|
|
1653
|
+
}
|
|
1654
|
+
}
|
|
1655
|
+
complete() {
|
|
1656
|
+
if (!this.started)
|
|
1657
|
+
throw new ModelStreamError2("[SixbModels] Stream did not start.");
|
|
1658
|
+
if (!this.finished || !this.finishReason) {
|
|
1659
|
+
throw new ModelStreamError2("[SixbModels] Stream ended without a finish event.");
|
|
1660
|
+
}
|
|
1661
|
+
for (const part of this.parts) {
|
|
1662
|
+
if ("complete" in part && !part.complete) {
|
|
1663
|
+
throw new ModelStreamError2(`[SixbModels] Stream finished with incomplete ${part.type} content.`);
|
|
1664
|
+
}
|
|
1665
|
+
}
|
|
1666
|
+
const parsed = this.parseParts(false);
|
|
1667
|
+
return {
|
|
1668
|
+
content: parsed.content,
|
|
1669
|
+
toolCalls: parsed.toolCalls,
|
|
1670
|
+
finishReason: this.finishReason,
|
|
1671
|
+
...this.rawFinishReason === undefined ? {} : { rawFinishReason: this.rawFinishReason },
|
|
1672
|
+
...this.accounting(),
|
|
1673
|
+
...this.projectionError === undefined ? {} : { projectionError: this.projectionError }
|
|
1674
|
+
};
|
|
1675
|
+
}
|
|
1676
|
+
accounting() {
|
|
1677
|
+
return {
|
|
1678
|
+
usage: this.usage,
|
|
1679
|
+
...this.responseId === undefined ? {} : { responseId: this.responseId },
|
|
1680
|
+
...this.providerIds === undefined ? {} : { providerIds: this.providerIds },
|
|
1681
|
+
...this.responseModelId === undefined ? {} : { responseModelId: this.responseModelId },
|
|
1682
|
+
...this.reportedCost === undefined ? {} : { reportedCost: this.reportedCost },
|
|
1683
|
+
...this.route === undefined ? {} : { route: this.route }
|
|
1684
|
+
};
|
|
1685
|
+
}
|
|
1686
|
+
partialContent() {
|
|
1687
|
+
return this.parseParts(true).content;
|
|
1688
|
+
}
|
|
1689
|
+
parseParts(partial) {
|
|
1690
|
+
const content = [];
|
|
1691
|
+
const toolCalls = [];
|
|
1692
|
+
for (const part of this.parts) {
|
|
1693
|
+
if (part.type === "text") {
|
|
1694
|
+
if ((!partial || part.text.length > 0) && (part.complete || partial)) {
|
|
1695
|
+
content.push({
|
|
1696
|
+
type: "text",
|
|
1697
|
+
text: part.text,
|
|
1698
|
+
...part.providerData === undefined ? {} : { providerData: part.providerData }
|
|
1699
|
+
});
|
|
1700
|
+
}
|
|
1701
|
+
} else if (part.type === "reasoning") {
|
|
1702
|
+
if (part.complete) {
|
|
1703
|
+
content.push({
|
|
1704
|
+
type: "reasoning",
|
|
1705
|
+
text: part.text,
|
|
1706
|
+
...part.providerData === undefined ? {} : { providerData: part.providerData }
|
|
1707
|
+
});
|
|
1708
|
+
}
|
|
1709
|
+
} else if (part.type === "tool-call") {
|
|
1710
|
+
if (!part.complete)
|
|
1711
|
+
continue;
|
|
1712
|
+
let value = null;
|
|
1713
|
+
let inputError;
|
|
1714
|
+
try {
|
|
1715
|
+
const parsed = JSON.parse(part.inputText);
|
|
1716
|
+
if (!isJsonValue2(parsed))
|
|
1717
|
+
throw new TypeError("input is not a JSON value");
|
|
1718
|
+
value = parsed;
|
|
1719
|
+
} catch (error) {
|
|
1720
|
+
inputError = error instanceof Error ? error : new Error(String(error));
|
|
1721
|
+
}
|
|
1722
|
+
const call = {
|
|
1723
|
+
type: "tool-call",
|
|
1724
|
+
toolCallId: part.toolCallId,
|
|
1725
|
+
toolName: part.toolName,
|
|
1726
|
+
input: value,
|
|
1727
|
+
...part.providerData === undefined ? {} : { providerData: part.providerData },
|
|
1728
|
+
...part.providerExecuted === undefined ? {} : { providerExecuted: part.providerExecuted },
|
|
1729
|
+
...part.dynamic === undefined ? {} : { dynamic: part.dynamic }
|
|
1730
|
+
};
|
|
1731
|
+
content.push(call);
|
|
1732
|
+
toolCalls.push({ part: call, ...inputError === undefined ? {} : { inputError } });
|
|
1733
|
+
} else {
|
|
1734
|
+
content.push(part);
|
|
1735
|
+
}
|
|
1736
|
+
}
|
|
1737
|
+
return { content, toolCalls };
|
|
1738
|
+
}
|
|
1739
|
+
async startText(event) {
|
|
1740
|
+
this.requireStarted(event.type);
|
|
1741
|
+
this.assertNewSpan(event.id);
|
|
1742
|
+
const providerData = this.captureProviderData(event.providerData);
|
|
1743
|
+
const part = {
|
|
1744
|
+
type: "text",
|
|
1745
|
+
text: "",
|
|
1746
|
+
complete: false,
|
|
1747
|
+
...providerData === undefined ? {} : { providerData }
|
|
1748
|
+
};
|
|
1749
|
+
this.spans.set(event.id, part);
|
|
1750
|
+
this.parts.push(part);
|
|
1751
|
+
await this.onEvent?.({ type: "text-start", id: event.id });
|
|
1752
|
+
}
|
|
1753
|
+
async startReasoning(event) {
|
|
1754
|
+
this.requireStarted(event.type);
|
|
1755
|
+
this.assertNewSpan(event.id);
|
|
1756
|
+
const providerData = this.captureProviderData(event.providerData);
|
|
1757
|
+
const part = {
|
|
1758
|
+
type: "reasoning",
|
|
1759
|
+
text: "",
|
|
1760
|
+
complete: false,
|
|
1761
|
+
...providerData === undefined ? {} : { providerData }
|
|
1762
|
+
};
|
|
1763
|
+
this.spans.set(event.id, part);
|
|
1764
|
+
this.parts.push(part);
|
|
1765
|
+
await this.onEvent?.({ type: "reasoning-start", id: event.id });
|
|
1766
|
+
}
|
|
1767
|
+
async appendText(event, expected) {
|
|
1768
|
+
const part = this.spans.get(event.id);
|
|
1769
|
+
if (!part || part.type !== expected || part.complete) {
|
|
1770
|
+
throw new ModelStreamError2(`[SixbModels] ${event.type} references unopened ${expected} span '${event.id}'.`);
|
|
1771
|
+
}
|
|
1772
|
+
part.text += event.delta;
|
|
1773
|
+
await this.onEvent?.({ type: event.type, id: event.id, delta: event.delta });
|
|
1774
|
+
}
|
|
1775
|
+
async endText(event, expected) {
|
|
1776
|
+
const part = this.spans.get(event.id);
|
|
1777
|
+
if (!part || part.type !== expected || part.complete) {
|
|
1778
|
+
throw new ModelStreamError2(`[SixbModels] ${event.type} references unopened ${expected} span '${event.id}'.`);
|
|
1779
|
+
}
|
|
1780
|
+
part.providerData = mergeProviderData(part.providerData, this.captureProviderData(event.providerData));
|
|
1781
|
+
part.complete = true;
|
|
1782
|
+
this.spans.delete(event.id);
|
|
1783
|
+
await this.onEvent?.({ type: event.type, id: event.id });
|
|
1784
|
+
}
|
|
1785
|
+
async startTool(event) {
|
|
1786
|
+
this.requireStarted(event.type);
|
|
1787
|
+
if (typeof event.id !== "string" || !event.id || typeof event.toolName !== "string" || !event.toolName) {
|
|
1788
|
+
throw new ModelStreamError2("[SixbModels] Tool calls require nonempty IDs and names.");
|
|
1789
|
+
}
|
|
1790
|
+
if (this.toolCalls.has(event.id)) {
|
|
1791
|
+
throw new ModelStreamError2(`[SixbModels] Duplicate tool call ID '${event.id}'.`);
|
|
1792
|
+
}
|
|
1793
|
+
const providerData = this.captureProviderData(event.providerData);
|
|
1794
|
+
const part = {
|
|
1795
|
+
type: "tool-call",
|
|
1796
|
+
toolCallId: event.id,
|
|
1797
|
+
toolName: event.toolName,
|
|
1798
|
+
inputText: "",
|
|
1799
|
+
complete: false,
|
|
1800
|
+
...providerData === undefined ? {} : { providerData },
|
|
1801
|
+
...event.providerExecuted === undefined ? {} : { providerExecuted: event.providerExecuted },
|
|
1802
|
+
...event.dynamic === undefined ? {} : { dynamic: event.dynamic }
|
|
1803
|
+
};
|
|
1804
|
+
this.toolCalls.set(event.id, part);
|
|
1805
|
+
this.parts.push(part);
|
|
1806
|
+
await this.onEvent?.({
|
|
1807
|
+
type: "tool-input-start",
|
|
1808
|
+
toolCallId: event.id,
|
|
1809
|
+
toolName: event.toolName
|
|
1810
|
+
});
|
|
1811
|
+
}
|
|
1812
|
+
async appendTool(event) {
|
|
1813
|
+
const part = this.toolCalls.get(event.id);
|
|
1814
|
+
if (!part || part.complete) {
|
|
1815
|
+
throw new ModelStreamError2(`[SixbModels] tool-input-delta references unopened tool call '${event.id}'.`);
|
|
1816
|
+
}
|
|
1817
|
+
part.inputText += event.delta;
|
|
1818
|
+
await this.onEvent?.({
|
|
1819
|
+
type: "tool-input-delta",
|
|
1820
|
+
toolCallId: event.id,
|
|
1821
|
+
toolName: part.toolName,
|
|
1822
|
+
inputTextDelta: event.delta
|
|
1823
|
+
});
|
|
1824
|
+
}
|
|
1825
|
+
endTool(event) {
|
|
1826
|
+
const part = this.toolCalls.get(event.id);
|
|
1827
|
+
if (!part || part.complete) {
|
|
1828
|
+
throw new ModelStreamError2(`[SixbModels] tool-input-end references unopened tool call '${event.id}'.`);
|
|
1829
|
+
}
|
|
1830
|
+
part.providerData = mergeProviderData(part.providerData, this.captureProviderData(event.providerData));
|
|
1831
|
+
part.complete = true;
|
|
1832
|
+
}
|
|
1833
|
+
async completeTool(event) {
|
|
1834
|
+
await this.startTool({
|
|
1835
|
+
type: "tool-input-start",
|
|
1836
|
+
id: event.toolCallId,
|
|
1837
|
+
toolName: event.toolName,
|
|
1838
|
+
...event.providerData === undefined ? {} : { providerData: event.providerData },
|
|
1839
|
+
...event.providerExecuted === undefined ? {} : { providerExecuted: event.providerExecuted },
|
|
1840
|
+
...event.dynamic === undefined ? {} : { dynamic: event.dynamic }
|
|
1841
|
+
});
|
|
1842
|
+
const part = this.toolCalls.get(event.toolCallId);
|
|
1843
|
+
if (!part)
|
|
1844
|
+
throw new ModelStreamError2("[SixbModels] Failed to index completed tool call.");
|
|
1845
|
+
part.inputText = event.input;
|
|
1846
|
+
part.complete = true;
|
|
1847
|
+
}
|
|
1848
|
+
addProviderToolResult(event) {
|
|
1849
|
+
if (!this.captureJsonValue(event.output, "provider tool result"))
|
|
1850
|
+
return;
|
|
1851
|
+
const providerData = this.captureProviderData(event.providerData);
|
|
1852
|
+
this.parts.push({
|
|
1853
|
+
type: "tool-result",
|
|
1854
|
+
toolCallId: event.toolCallId,
|
|
1855
|
+
toolName: event.toolName,
|
|
1856
|
+
output: event.isError ? { type: "error-json", value: event.output } : modelToolOutput(event.output),
|
|
1857
|
+
providerExecuted: event.providerExecuted ?? true,
|
|
1858
|
+
...event.dynamic === undefined ? {} : { dynamic: event.dynamic },
|
|
1859
|
+
...providerData === undefined ? {} : { providerData }
|
|
1860
|
+
});
|
|
1861
|
+
}
|
|
1862
|
+
captureProviderData(data) {
|
|
1863
|
+
if (data === undefined)
|
|
1864
|
+
return;
|
|
1865
|
+
try {
|
|
1866
|
+
return normalizeProviderData(data);
|
|
1867
|
+
} catch (error) {
|
|
1868
|
+
this.captureProjectionError(error);
|
|
1869
|
+
return;
|
|
1870
|
+
}
|
|
1871
|
+
}
|
|
1872
|
+
captureProviderState(value) {
|
|
1873
|
+
if (!this.captureJsonValue(value, "provider state"))
|
|
1874
|
+
return false;
|
|
1875
|
+
if (JSON.stringify(value).length > MAX_PROVIDER_DATA_BYTES) {
|
|
1876
|
+
this.captureProjectionError(new ModelStreamError2(`[SixbModels] Provider state exceeds the ${MAX_PROVIDER_DATA_BYTES}-byte response limit.`));
|
|
1877
|
+
return false;
|
|
1878
|
+
}
|
|
1879
|
+
return true;
|
|
1880
|
+
}
|
|
1881
|
+
captureJsonValue(value, label) {
|
|
1882
|
+
try {
|
|
1883
|
+
assertJsonValue2(value, label);
|
|
1884
|
+
return true;
|
|
1885
|
+
} catch (error) {
|
|
1886
|
+
this.captureProjectionError(error);
|
|
1887
|
+
return false;
|
|
1888
|
+
}
|
|
1889
|
+
}
|
|
1890
|
+
captureProjectionError(error) {
|
|
1891
|
+
this.projectionError ??= error instanceof Error ? error : new Error(String(error));
|
|
1892
|
+
}
|
|
1893
|
+
requireStarted(type) {
|
|
1894
|
+
if (!this.started) {
|
|
1895
|
+
throw new ModelStreamError2(`[SixbModels] Received '${type}' before stream-start.`);
|
|
1896
|
+
}
|
|
1897
|
+
}
|
|
1898
|
+
assertNewSpan(id) {
|
|
1899
|
+
if (!id)
|
|
1900
|
+
throw new ModelStreamError2("[SixbModels] Content span IDs must not be empty.");
|
|
1901
|
+
if (this.spans.has(id)) {
|
|
1902
|
+
throw new ModelStreamError2(`[SixbModels] Duplicate open content span '${id}'.`);
|
|
1903
|
+
}
|
|
1904
|
+
}
|
|
1905
|
+
}
|
|
1906
|
+
function validateUsage(usage) {
|
|
1907
|
+
for (const [key, value] of Object.entries(usage)) {
|
|
1908
|
+
if (key === "raw") {
|
|
1909
|
+
if (value !== undefined)
|
|
1910
|
+
assertJsonValue2(value, "raw model usage");
|
|
1911
|
+
continue;
|
|
1912
|
+
}
|
|
1913
|
+
if (value !== undefined && (!Number.isSafeInteger(value) || value < 0)) {
|
|
1914
|
+
throw new ModelStreamError2(`[SixbModels] Usage field '${key}' must be a nonnegative integer.`);
|
|
1915
|
+
}
|
|
1916
|
+
}
|
|
1917
|
+
}
|
|
1918
|
+
function normalizeProviderData(value) {
|
|
1919
|
+
const data = omitUndefinedObjectProperties(value);
|
|
1920
|
+
assertJsonValue2(data, "provider data");
|
|
1921
|
+
if (typeof data !== "object" || data === null || Array.isArray(data)) {
|
|
1922
|
+
throw new TypeError("[SixbModels] provider data must be a JSON object.");
|
|
1923
|
+
}
|
|
1924
|
+
if (JSON.stringify(data).length > MAX_PROVIDER_DATA_BYTES) {
|
|
1925
|
+
throw new ModelStreamError2(`[SixbModels] Provider data exceeds the ${MAX_PROVIDER_DATA_BYTES}-byte response limit.`);
|
|
1926
|
+
}
|
|
1927
|
+
return data;
|
|
1928
|
+
}
|
|
1929
|
+
function omitUndefinedObjectProperties(value, seen = new Set) {
|
|
1930
|
+
if (typeof value !== "object" || value === null || seen.has(value))
|
|
1931
|
+
return value;
|
|
1932
|
+
seen.add(value);
|
|
1933
|
+
try {
|
|
1934
|
+
if (Array.isArray(value)) {
|
|
1935
|
+
return value.map((entry) => omitUndefinedObjectProperties(entry, seen));
|
|
1936
|
+
}
|
|
1937
|
+
if (!isPlainRecord(value))
|
|
1938
|
+
return value;
|
|
1939
|
+
return Object.fromEntries(Reflect.ownKeys(value).filter((key) => Object.prototype.propertyIsEnumerable.call(value, key)).map((key) => [key, Reflect.get(value, key)]).filter(([, entry]) => entry !== undefined).map(([key, entry]) => [key, omitUndefinedObjectProperties(entry, seen)]));
|
|
1940
|
+
} finally {
|
|
1941
|
+
seen.delete(value);
|
|
1942
|
+
}
|
|
1943
|
+
}
|
|
1944
|
+
function mergeProviderData(first, second) {
|
|
1945
|
+
if (first === undefined)
|
|
1946
|
+
return second;
|
|
1947
|
+
if (second === undefined)
|
|
1948
|
+
return first;
|
|
1949
|
+
return { ...first, ...second };
|
|
1950
|
+
}
|
|
1951
|
+
function isAbortError(error) {
|
|
1952
|
+
return error instanceof DOMException && error.name === "AbortError" || error instanceof Error && error.name === "AbortError";
|
|
1953
|
+
}
|
|
1954
|
+
|
|
1955
|
+
// src/models/execution/binding.ts
|
|
1956
|
+
var bindings = new WeakMap;
|
|
1957
|
+
function registerModelExecutionBinding(models, bind) {
|
|
1958
|
+
bindings.set(models, bind);
|
|
1959
|
+
}
|
|
1960
|
+
function bindModelExecutionAttempt(models, input) {
|
|
1961
|
+
const bind = bindings.get(models);
|
|
1962
|
+
if (!bind)
|
|
1963
|
+
throw new Error("[SixbModels] Model runtime has no execution binding.");
|
|
1964
|
+
if (!Number.isSafeInteger(input.attempt) || input.attempt < 1) {
|
|
1965
|
+
throw new TypeError("[SixbModels] Execution attempt must be a positive safe integer.");
|
|
1966
|
+
}
|
|
1967
|
+
bind(input);
|
|
1968
|
+
bindings.delete(models);
|
|
1969
|
+
}
|
|
1970
|
+
|
|
1971
|
+
// src/models/output.ts
|
|
1972
|
+
function languageModelOutput(shape, valueTypesById) {
|
|
1973
|
+
if (!isRecord2(shape))
|
|
1974
|
+
throw new TypeError("[SixbModels] output must be a Sixb schema record.");
|
|
1975
|
+
const schema = schemaRecordToJsonSchema2({ shape, valueTypesById });
|
|
1976
|
+
assertJsonObject2(schema, "model output schema");
|
|
1977
|
+
return {
|
|
1978
|
+
name: "sixb_output",
|
|
1979
|
+
schema,
|
|
1980
|
+
validate(value) {
|
|
1981
|
+
if (!isRecord2(value))
|
|
1982
|
+
throw new TypeError("[SixbModels] Output must be an object.");
|
|
1983
|
+
for (const key of Object.keys(value)) {
|
|
1984
|
+
if (!Object.hasOwn(shape, key)) {
|
|
1985
|
+
throw new TypeError(`[SixbModels] Unknown output field '${key}'.`);
|
|
1986
|
+
}
|
|
1987
|
+
}
|
|
1988
|
+
return Object.fromEntries(Object.entries(shape).map(([key, field]) => {
|
|
1989
|
+
if (!Object.hasOwn(value, key)) {
|
|
1990
|
+
throw new TypeError(`[SixbModels] Missing output field '${key}'.`);
|
|
1991
|
+
}
|
|
1992
|
+
validateSchemaOrRefValue2(field, value[key], `output.${key}`, valueTypesById);
|
|
1993
|
+
const output = isObjectRefSchema2(field) ? value[key] : coerceSchemaValueToTyped2(field, normalizeSchemaValue2(field, value[key], `output.${key}`, valueTypesById), valueTypesById);
|
|
1994
|
+
return [key, output];
|
|
1995
|
+
}));
|
|
1996
|
+
}
|
|
1997
|
+
};
|
|
1998
|
+
}
|
|
1999
|
+
|
|
2000
|
+
// src/models/execution.ts
|
|
2001
|
+
function createModelsRuntime(runtime, execution, catalog) {
|
|
2002
|
+
let binding;
|
|
2003
|
+
let recorder;
|
|
2004
|
+
async function createRecorder() {
|
|
2005
|
+
const storage = {
|
|
2006
|
+
...requireAccountingCapabilities(runtime.storage),
|
|
2007
|
+
transaction: runtime.storage.transaction.bind(runtime.storage)
|
|
2008
|
+
};
|
|
2009
|
+
if (!binding) {
|
|
2010
|
+
throw new Error("[SixbModels] Generation requires a bound request or worker execution attempt.");
|
|
2011
|
+
}
|
|
2012
|
+
const { requesterGroupIds } = await ensureExecutionRecord2(runtime.storage.executions, executionRecordInputFromRuntime({
|
|
2013
|
+
execution,
|
|
2014
|
+
runtimeAuthorization: runtime.runtimeAuthorization
|
|
2015
|
+
}));
|
|
2016
|
+
return new AiModelCallRecorder2({
|
|
2017
|
+
storage,
|
|
2018
|
+
projectId: runtime.projectId,
|
|
2019
|
+
executionId: execution.id,
|
|
2020
|
+
attempt: binding.attempt,
|
|
2021
|
+
requesterGroupIds,
|
|
2022
|
+
limits: createAiModelCallLimitController2({
|
|
2023
|
+
storage,
|
|
2024
|
+
projectId: runtime.projectId,
|
|
2025
|
+
requestedBy: execution.requestedBy,
|
|
2026
|
+
requesterGroupIds
|
|
2027
|
+
}),
|
|
2028
|
+
recoverAiModelCall: (input) => enqueueAiModelCallRecovery2(runtime.queues.agents, input)
|
|
2029
|
+
});
|
|
2030
|
+
}
|
|
2031
|
+
async function generate(input) {
|
|
2032
|
+
assertProviderAccess2(runtime, execution, "models.language.generate");
|
|
2033
|
+
const messages = generationMessages(input);
|
|
2034
|
+
if (!binding) {
|
|
2035
|
+
throw new Error("[SixbModels] Generation requires a bound request or worker execution attempt.");
|
|
2036
|
+
}
|
|
2037
|
+
const signal = input.signal ? AbortSignal.any([binding.signal, input.signal]) : binding.signal;
|
|
2038
|
+
signal.throwIfAborted();
|
|
2039
|
+
const selected = input.model ? catalog ? catalog.language.getByRef({
|
|
2040
|
+
provider: input.model.providerId,
|
|
2041
|
+
modelId: input.model.modelId
|
|
2042
|
+
})?.model : input.model : catalog?.language.default.model;
|
|
2043
|
+
if (!selected) {
|
|
2044
|
+
throw new Error(input.model ? `[SixbModels] Model '${input.model.providerId}/${input.model.modelId}' is not configured in models.language.` : "[SixbModels] Configure models.language in createSixb() or supply a model to generate().");
|
|
2045
|
+
}
|
|
2046
|
+
const output = input.output === undefined ? undefined : languageModelOutput(input.output, runtime.ontology.getValueTypesById());
|
|
2047
|
+
const model = await resolveLanguageModel2(selected);
|
|
2048
|
+
const reasoningIssue = modelReasoningSupportIssue2(model.definition.capabilities.reasoning, input.reasoning);
|
|
2049
|
+
if (reasoningIssue)
|
|
2050
|
+
throw new UnsupportedModelFeatureError2(`[SixbModels] ${reasoningIssue}.`);
|
|
2051
|
+
if (output && model.definition.capabilities.nativeStructuredOutput === false) {
|
|
2052
|
+
throw new UnsupportedModelFeatureError2("[SixbModels] Model does not support native structured output.");
|
|
2053
|
+
}
|
|
2054
|
+
const maxOutputTokens = Math.min(aiModelCallOutputTokenAllowance(input.maxOutputTokens ?? model.definition.maxOutputTokens), model.definition.maxOutputTokens ?? Infinity);
|
|
2055
|
+
if (typeof input.reasoning === "object" && input.reasoning.budgetTokens >= maxOutputTokens) {
|
|
2056
|
+
throw new TypeError("[SixbModels] Output allowance must exceed the reasoning token budget.");
|
|
2057
|
+
}
|
|
2058
|
+
recorder ??= createRecorder();
|
|
2059
|
+
const accounting = await recorder;
|
|
2060
|
+
accounting.assertHealthy();
|
|
2061
|
+
signal.throwIfAborted();
|
|
2062
|
+
let event;
|
|
2063
|
+
const options = {
|
|
2064
|
+
model: accounting.wrapModel(model),
|
|
2065
|
+
messages,
|
|
2066
|
+
maxSteps: 1,
|
|
2067
|
+
rejectLocalToolCalls: true,
|
|
2068
|
+
maxOutputTokens,
|
|
2069
|
+
reasoning: input.reasoning,
|
|
2070
|
+
caching: input.caching,
|
|
2071
|
+
signal,
|
|
2072
|
+
onModelCallEnd: async (completed) => {
|
|
2073
|
+
await accounting.onModelCallEnd(completed);
|
|
2074
|
+
event = completed;
|
|
2075
|
+
}
|
|
2076
|
+
};
|
|
2077
|
+
const result = output ? await runModelLoop2({ ...options, output }) : await runModelLoop2(options);
|
|
2078
|
+
if (result.status === "aborted") {
|
|
2079
|
+
signal.throwIfAborted();
|
|
2080
|
+
throw new DOMException("Model generation aborted", "AbortError");
|
|
2081
|
+
}
|
|
2082
|
+
if (result.finishReason === "error" || result.finishReason === "content-filter") {
|
|
2083
|
+
throw new ModelProviderError2(`[SixbModels] Generation ended with '${result.finishReason}'.`, model.providerId, model.modelId);
|
|
2084
|
+
}
|
|
2085
|
+
if (!event)
|
|
2086
|
+
throw new ModelStreamError2("[SixbModels] Generation completed without accounting metadata.");
|
|
2087
|
+
return {
|
|
2088
|
+
output: result.output,
|
|
2089
|
+
usage: event.usage,
|
|
2090
|
+
cost: event.cost,
|
|
2091
|
+
callId: event.callId,
|
|
2092
|
+
finishReason: result.finishReason
|
|
2093
|
+
};
|
|
2094
|
+
}
|
|
2095
|
+
const models = {
|
|
2096
|
+
language: { generate }
|
|
2097
|
+
};
|
|
2098
|
+
registerModelExecutionBinding(models, (input) => {
|
|
2099
|
+
binding = { attempt: input.attempt, signal: input.signal };
|
|
2100
|
+
});
|
|
2101
|
+
return models;
|
|
2102
|
+
}
|
|
2103
|
+
function generationMessages(input) {
|
|
2104
|
+
if (input.prompt === undefined === (input.messages === undefined)) {
|
|
2105
|
+
throw new TypeError("[SixbModels] Supply exactly one of prompt or messages.");
|
|
2106
|
+
}
|
|
2107
|
+
if (input.prompt !== undefined && typeof input.prompt !== "string") {
|
|
2108
|
+
throw new TypeError("[SixbModels] prompt must be a string.");
|
|
2109
|
+
}
|
|
2110
|
+
if (input.messages !== undefined && !Array.isArray(input.messages)) {
|
|
2111
|
+
throw new TypeError("[SixbModels] messages must be an array.");
|
|
2112
|
+
}
|
|
2113
|
+
if (input.instructions !== undefined && typeof input.instructions !== "string") {
|
|
2114
|
+
throw new TypeError("[SixbModels] instructions must be a string.");
|
|
2115
|
+
}
|
|
2116
|
+
if (input.maxOutputTokens !== undefined && (!Number.isSafeInteger(input.maxOutputTokens) || input.maxOutputTokens <= 0)) {
|
|
2117
|
+
throw new TypeError("[SixbModels] maxOutputTokens must be a positive safe integer.");
|
|
2118
|
+
}
|
|
2119
|
+
if (input.caching !== undefined && input.caching !== "auto" && input.caching !== "off") {
|
|
2120
|
+
throw new TypeError("[SixbModels] caching must be 'auto' or 'off'.");
|
|
2121
|
+
}
|
|
2122
|
+
return [
|
|
2123
|
+
...input.instructions === undefined ? [] : [{ role: "system", content: input.instructions }],
|
|
2124
|
+
...input.prompt !== undefined ? [{ role: "user", content: [{ type: "text", text: input.prompt }] }] : input.messages ?? []
|
|
2125
|
+
];
|
|
2126
|
+
}
|
|
2127
|
+
|
|
2128
|
+
// src/objects/execution.ts
|
|
2129
|
+
function createObjectsRuntime(runtime, execution) {
|
|
2130
|
+
const runtimeAuthorization = runtime.runtimeAuthorization;
|
|
2131
|
+
const objectReader = runtime.objectReader;
|
|
2132
|
+
assertAuthorizedObjectReaderBinding({
|
|
2133
|
+
reader: objectReader,
|
|
2134
|
+
scope: { execution, authorization: runtimeAuthorization }
|
|
2135
|
+
});
|
|
2136
|
+
const authorization = runtime.authorization;
|
|
2137
|
+
const capturedRuntime = {
|
|
2138
|
+
projectId: runtime.projectId,
|
|
2139
|
+
broker: runtime.broker,
|
|
2140
|
+
ontology: runtime.ontology,
|
|
2141
|
+
actionRegistry: runtime.actionRegistry,
|
|
2142
|
+
events: runtime.events,
|
|
2143
|
+
storage: runtime.storage,
|
|
2144
|
+
queues: runtime.queues,
|
|
2145
|
+
runtimeAuthorization,
|
|
2146
|
+
objectReader,
|
|
2147
|
+
...authorization === undefined ? {} : { authorization }
|
|
2148
|
+
};
|
|
2149
|
+
shareOntologyMutationRuntime2(runtime, capturedRuntime);
|
|
2150
|
+
shareSixbErrorReporter2(runtime, capturedRuntime);
|
|
2151
|
+
Object.freeze(capturedRuntime);
|
|
2152
|
+
const ontologyView = () => getAuthorizedOntologyView(objectReader);
|
|
2153
|
+
const objects = Object.assign((objectType) => {
|
|
2154
|
+
assertObjectTypeRegistered2(capturedRuntime.ontology.getObjectTypesById(), objectType);
|
|
2155
|
+
return createObjectSet2({ ...capturedRuntime, execution, objectType });
|
|
2156
|
+
}, {
|
|
2157
|
+
listTypes: () => ontologyView().listObjectTypes(),
|
|
2158
|
+
getTypeById: (objectTypeId) => ontologyView().getObjectTypeById(objectTypeId),
|
|
2159
|
+
resolveType: (objectTypeId) => ontologyView().resolveObjectType(objectTypeId),
|
|
2160
|
+
getValueTypesById: () => ontologyView().getValueTypesById(),
|
|
2161
|
+
listSubTypes: (objectTypeId) => ontologyView().listSubTypes(objectTypeId),
|
|
2162
|
+
isValidLinkTarget: (expected, actual) => ontologyView().isValidLinkTarget(expected, actual),
|
|
2163
|
+
executeQuery: (input) => objectReader.executeQuery(input),
|
|
2164
|
+
queryLinks: (input) => objectReader.queryLinks(input),
|
|
2165
|
+
count: (input) => objectReader.count(input),
|
|
2166
|
+
exists: (input) => objectReader.exists(input),
|
|
2167
|
+
facet: (input) => objectReader.facet(input),
|
|
2168
|
+
listLinks: async (input) => {
|
|
2169
|
+
return objectReader.listLinks(input);
|
|
2170
|
+
},
|
|
2171
|
+
getTelemetryHistoryBatch: (input) => {
|
|
2172
|
+
const timeseries = capturedRuntime.storage.timeseries;
|
|
2173
|
+
return getTelemetryHistoryBatch2(input, { storage: timeseries, objectReader });
|
|
2174
|
+
},
|
|
2175
|
+
getTelemetryHistory: async (input) => {
|
|
2176
|
+
const timeseries = capturedRuntime.storage.timeseries;
|
|
2177
|
+
const objectTypeId = input.objectTypeId;
|
|
2178
|
+
const objectId = input.objectId;
|
|
2179
|
+
const propertyId = input.propertyId;
|
|
2180
|
+
const from = input.from;
|
|
2181
|
+
const to = input.to;
|
|
2182
|
+
const limit = input.limit;
|
|
2183
|
+
const order = input.order;
|
|
2184
|
+
const [result] = await getTelemetryHistoryBatch2({
|
|
2185
|
+
series: [{ objectTypeId, objectId, propertyId }],
|
|
2186
|
+
...from === undefined ? {} : { from },
|
|
2187
|
+
...to === undefined ? {} : { to },
|
|
2188
|
+
...limit === undefined ? {} : { limitPerSeries: limit },
|
|
2189
|
+
...order === undefined ? {} : { order }
|
|
2190
|
+
}, { storage: timeseries, objectReader });
|
|
2191
|
+
return result?.points ?? [];
|
|
2192
|
+
},
|
|
2193
|
+
getLatestTelemetry: async (input) => {
|
|
2194
|
+
const timeseries = capturedRuntime.storage.timeseries;
|
|
2195
|
+
const objectTypeId = input.objectTypeId;
|
|
2196
|
+
const objectId = input.objectId;
|
|
2197
|
+
const propertyId = input.propertyId;
|
|
2198
|
+
return getLatestTelemetryPoint({ objectTypeId, objectId, propertyId }, { storage: timeseries, objectReader });
|
|
2199
|
+
},
|
|
2200
|
+
list: (params) => listObjects(capturedRuntime, params),
|
|
2201
|
+
get: (objectTypeId, primaryId) => objectReader.getByPrimaryId({ objectTypeId, primaryId }),
|
|
2202
|
+
getPrimaryPropertyId: (objectTypeId) => {
|
|
2203
|
+
return ontologyView().getPrimaryPropertyId(objectTypeId);
|
|
2204
|
+
},
|
|
2205
|
+
upsert: (objectTypeId, properties) => upsertObject3(capturedRuntime, objectTypeId, properties),
|
|
2206
|
+
upsertBatch: (objectTypeId, items) => upsertObjectBatch3(capturedRuntime, objectTypeId, items),
|
|
2207
|
+
upsertLink: (objectTypeId, sourceId, linkId, target) => upsertLink3(capturedRuntime, objectTypeId, sourceId, linkId, target),
|
|
2208
|
+
upsertLinkBatch: (items) => upsertLinkBatch3(capturedRuntime, items),
|
|
2209
|
+
removeLink: (objectTypeId, sourceId, linkId, target) => removeLink3(capturedRuntime, objectTypeId, sourceId, linkId, target),
|
|
2210
|
+
appendTelemetry: (objectTypeId, items) => appendTelemetry(capturedRuntime, objectTypeId, items)
|
|
2211
|
+
});
|
|
2212
|
+
return objects;
|
|
2213
|
+
}
|
|
2214
|
+
|
|
2215
|
+
// src/pipelines/execution.ts
|
|
2216
|
+
function createPipelinesRuntime(runtime, execution, source) {
|
|
2217
|
+
const authority = resolveRuntimeAuthorizationForProject(runtime);
|
|
2218
|
+
const allowed = (pipelineId) => isRuntimeAllowed2(runtime, { kind: "pipeline.run", pipelineId });
|
|
2219
|
+
const visibleIds = () => source.list().filter((pipeline) => allowed(pipeline.id)).map((pipeline) => pipeline.id);
|
|
2220
|
+
const historyFilterIds = () => authority.type === "unrestricted" ? undefined : authority.type === "principal" ? visibleIds() : [];
|
|
2221
|
+
const getRun = async (runId) => {
|
|
2222
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
2223
|
+
return null;
|
|
2224
|
+
const run = await runtime.storage.pipelineRuns?.getById({
|
|
2225
|
+
projectId: runtime.projectId,
|
|
2226
|
+
id: runId
|
|
2227
|
+
}) ?? null;
|
|
2228
|
+
if (!run)
|
|
2229
|
+
return null;
|
|
2230
|
+
return authority.type === "unrestricted" || canViewPipelineRun2(authority.context, run) ? run : null;
|
|
2231
|
+
};
|
|
2232
|
+
return {
|
|
2233
|
+
list: () => authority.type === "denied" || authority.type === "delegated" ? [] : source.list().filter((pipeline) => allowed(pipeline.id)),
|
|
2234
|
+
getById: (pipelineId) => {
|
|
2235
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
2236
|
+
return null;
|
|
2237
|
+
const pipeline = source.getById(pipelineId);
|
|
2238
|
+
return pipeline && allowed(pipelineId) ? pipeline : null;
|
|
2239
|
+
},
|
|
2240
|
+
request: async (input) => {
|
|
2241
|
+
assertAuthorized2(runtime, { kind: "pipeline.run", pipelineId: input.pipelineId });
|
|
2242
|
+
const pipeline = source.getById(input.pipelineId);
|
|
2243
|
+
if (!pipeline)
|
|
2244
|
+
throw new PipelineError2(`[Sixb] Unknown pipeline '${input.pipelineId}'`);
|
|
2245
|
+
return requestPipelineRun2(runtime, execution, pipeline, input);
|
|
2246
|
+
},
|
|
2247
|
+
runs: {
|
|
2248
|
+
getById: getRun,
|
|
2249
|
+
list: (input = {}) => {
|
|
2250
|
+
if (authority.type === "denied" || authority.type === "delegated") {
|
|
2251
|
+
return Promise.resolve({ runs: [], hasMore: false, total: 0 });
|
|
2252
|
+
}
|
|
2253
|
+
const storage = runtime.storage.pipelineRuns;
|
|
2254
|
+
if (!storage)
|
|
2255
|
+
return Promise.resolve({ runs: [], hasMore: false, total: 0 });
|
|
2256
|
+
return storage.list({
|
|
2257
|
+
...input,
|
|
2258
|
+
pipelineIds: historyFilterIds(),
|
|
2259
|
+
projectId: runtime.projectId
|
|
2260
|
+
});
|
|
2261
|
+
},
|
|
2262
|
+
listLatest: (pipelineIds) => {
|
|
2263
|
+
if (authority.type === "denied" || authority.type === "delegated") {
|
|
2264
|
+
return Promise.resolve({ runs: [] });
|
|
2265
|
+
}
|
|
2266
|
+
const storage = runtime.storage.pipelineRuns;
|
|
2267
|
+
if (!storage || pipelineIds.length === 0)
|
|
2268
|
+
return Promise.resolve({ runs: [] });
|
|
2269
|
+
const allowedIds = pipelineIds.filter(allowed);
|
|
2270
|
+
return allowedIds.length === 0 ? Promise.resolve({ runs: [] }) : storage.listLatestByPipelineIds({
|
|
2271
|
+
projectId: runtime.projectId,
|
|
2272
|
+
pipelineIds: allowedIds
|
|
2273
|
+
});
|
|
2274
|
+
},
|
|
2275
|
+
listSteps: async (runId, input = {}) => {
|
|
2276
|
+
const storage = runtime.storage.pipelineRuns;
|
|
2277
|
+
if (!storage || !await getRun(runId))
|
|
2278
|
+
return null;
|
|
2279
|
+
return storage.listSteps({
|
|
2280
|
+
...input,
|
|
2281
|
+
pipelineRunId: runId,
|
|
2282
|
+
projectId: runtime.projectId
|
|
2283
|
+
});
|
|
2284
|
+
}
|
|
2285
|
+
}
|
|
2286
|
+
};
|
|
2287
|
+
}
|
|
2288
|
+
|
|
2289
|
+
// src/projections/execution.ts
|
|
2290
|
+
function createProjectionsRuntime(runtime, source) {
|
|
2291
|
+
const authority = resolveRuntimeAuthorizationForProject(runtime);
|
|
2292
|
+
const listVisible = (list) => {
|
|
2293
|
+
switch (authority.type) {
|
|
2294
|
+
case "denied":
|
|
2295
|
+
case "delegated":
|
|
2296
|
+
return [];
|
|
2297
|
+
case "principal":
|
|
2298
|
+
return list().filter((projection) => canViewProjection2(authority.context, projection));
|
|
2299
|
+
case "unrestricted":
|
|
2300
|
+
return [...list()];
|
|
2301
|
+
}
|
|
2302
|
+
};
|
|
2303
|
+
const visible = (projection) => {
|
|
2304
|
+
switch (authority.type) {
|
|
2305
|
+
case "denied":
|
|
2306
|
+
case "delegated":
|
|
2307
|
+
return false;
|
|
2308
|
+
case "principal":
|
|
2309
|
+
return canViewProjection2(authority.context, projection);
|
|
2310
|
+
case "unrestricted":
|
|
2311
|
+
return true;
|
|
2312
|
+
}
|
|
2313
|
+
};
|
|
2314
|
+
const visibleIds = (projectionIds) => projectionIds.filter((projectionId) => {
|
|
2315
|
+
const projection = source.getById(projectionId);
|
|
2316
|
+
return projection !== null && visible(projection);
|
|
2317
|
+
});
|
|
2318
|
+
return {
|
|
2319
|
+
list: () => listVisible(() => source.list()),
|
|
2320
|
+
listObjects: () => listVisible(() => source.listObjects()),
|
|
2321
|
+
listLinks: () => listVisible(() => source.listLinks()),
|
|
2322
|
+
listTelemetry: () => listVisible(() => source.listTelemetry()),
|
|
2323
|
+
getById: (projectionId) => {
|
|
2324
|
+
switch (authority.type) {
|
|
2325
|
+
case "denied":
|
|
2326
|
+
case "delegated":
|
|
2327
|
+
return null;
|
|
2328
|
+
case "principal":
|
|
2329
|
+
case "unrestricted":
|
|
2330
|
+
break;
|
|
2331
|
+
}
|
|
2332
|
+
const projection = source.getById(projectionId);
|
|
2333
|
+
return projection && visible(projection) ? projection : null;
|
|
2334
|
+
},
|
|
2335
|
+
runs: {
|
|
2336
|
+
getById: async (runId) => {
|
|
2337
|
+
switch (authority.type) {
|
|
2338
|
+
case "denied":
|
|
2339
|
+
case "delegated":
|
|
2340
|
+
return null;
|
|
2341
|
+
case "principal":
|
|
2342
|
+
case "unrestricted":
|
|
2343
|
+
break;
|
|
2344
|
+
}
|
|
2345
|
+
const run = await runtime.storage.projectionRuns?.getById({
|
|
2346
|
+
projectId: runtime.projectId,
|
|
2347
|
+
id: runId
|
|
2348
|
+
}) ?? null;
|
|
2349
|
+
if (!run)
|
|
2350
|
+
return null;
|
|
2351
|
+
return authority.type === "unrestricted" || canViewProjectionRun2(authority.context, run.target) ? run : null;
|
|
2352
|
+
},
|
|
2353
|
+
list: (input = {}) => {
|
|
2354
|
+
switch (authority.type) {
|
|
2355
|
+
case "denied":
|
|
2356
|
+
case "delegated":
|
|
2357
|
+
return Promise.resolve({ runs: [], hasMore: false, total: 0 });
|
|
2358
|
+
case "principal":
|
|
2359
|
+
case "unrestricted":
|
|
2360
|
+
break;
|
|
2361
|
+
}
|
|
2362
|
+
const storage = runtime.storage.projectionRuns;
|
|
2363
|
+
if (!storage)
|
|
2364
|
+
return Promise.resolve({ runs: [], hasMore: false, total: 0 });
|
|
2365
|
+
return storage.list({
|
|
2366
|
+
...input,
|
|
2367
|
+
objectTypeIds: authority.type === "principal" ? [...authority.context.grants["view:object"]] : undefined,
|
|
2368
|
+
projectId: runtime.projectId
|
|
2369
|
+
});
|
|
2370
|
+
},
|
|
2371
|
+
listLatest: (projectionIds) => {
|
|
2372
|
+
switch (authority.type) {
|
|
2373
|
+
case "denied":
|
|
2374
|
+
case "delegated":
|
|
2375
|
+
return Promise.resolve({ runs: [] });
|
|
2376
|
+
case "principal":
|
|
2377
|
+
case "unrestricted":
|
|
2378
|
+
break;
|
|
2379
|
+
}
|
|
2380
|
+
const storage = runtime.storage.projectionRuns;
|
|
2381
|
+
if (!storage || projectionIds.length === 0)
|
|
2382
|
+
return Promise.resolve({ runs: [] });
|
|
2383
|
+
const ids = visibleIds(projectionIds);
|
|
2384
|
+
return ids.length === 0 ? Promise.resolve({ runs: [] }) : storage.listLatestByProjectionIds({ projectId: runtime.projectId, projectionIds: ids });
|
|
2385
|
+
}
|
|
2386
|
+
}
|
|
2387
|
+
};
|
|
2388
|
+
}
|
|
2389
|
+
|
|
2390
|
+
// src/rules/execution.ts
|
|
2391
|
+
function createRulesRuntime(runtime, source) {
|
|
2392
|
+
const authority = resolveRuntimeAuthorizationForProject(runtime);
|
|
2393
|
+
const visible = (rule) => {
|
|
2394
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
2395
|
+
return false;
|
|
2396
|
+
return isRuntimeAllowed2(runtime, {
|
|
2397
|
+
kind: "object.view",
|
|
2398
|
+
objectTypeId: rule.subject.objectTypeId
|
|
2399
|
+
});
|
|
2400
|
+
};
|
|
2401
|
+
return {
|
|
2402
|
+
list: () => authority.type === "denied" || authority.type === "delegated" ? [] : source.list().filter(visible),
|
|
2403
|
+
getById: (ruleId) => {
|
|
2404
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
2405
|
+
return null;
|
|
2406
|
+
const rule = source.getById(ruleId);
|
|
2407
|
+
return rule && visible(rule) ? rule : null;
|
|
2408
|
+
},
|
|
2409
|
+
states: {
|
|
2410
|
+
list: (input = {}) => {
|
|
2411
|
+
if (authority.type === "denied" || authority.type === "delegated") {
|
|
2412
|
+
return Promise.resolve({ states: [], hasMore: false, total: 0 });
|
|
2413
|
+
}
|
|
2414
|
+
const storage = runtime.storage.rules;
|
|
2415
|
+
if (!storage)
|
|
2416
|
+
return Promise.resolve({ states: [], hasMore: false, total: 0 });
|
|
2417
|
+
return storage.listActive({
|
|
2418
|
+
...input,
|
|
2419
|
+
objectTypeIds: authority.type === "principal" ? [...authority.context.grants["view:object"]] : undefined,
|
|
2420
|
+
projectId: runtime.projectId
|
|
2421
|
+
});
|
|
2422
|
+
}
|
|
2423
|
+
}
|
|
2424
|
+
};
|
|
2425
|
+
}
|
|
2426
|
+
|
|
2427
|
+
// src/schedules/execution.ts
|
|
2428
|
+
function createSchedulesRuntime(runtime, schedules) {
|
|
2429
|
+
const authority = resolveRuntimeAuthorizationForProject(runtime);
|
|
2430
|
+
return {
|
|
2431
|
+
list: () => {
|
|
2432
|
+
switch (authority.type) {
|
|
2433
|
+
case "denied":
|
|
2434
|
+
case "delegated":
|
|
2435
|
+
return [];
|
|
2436
|
+
case "principal":
|
|
2437
|
+
case "unrestricted":
|
|
2438
|
+
return schedules.list();
|
|
2439
|
+
}
|
|
2440
|
+
},
|
|
2441
|
+
getById: (scheduleId) => {
|
|
2442
|
+
switch (authority.type) {
|
|
2443
|
+
case "denied":
|
|
2444
|
+
case "delegated":
|
|
2445
|
+
return null;
|
|
2446
|
+
case "principal":
|
|
2447
|
+
case "unrestricted":
|
|
2448
|
+
return schedules.getById(scheduleId);
|
|
2449
|
+
}
|
|
2450
|
+
}
|
|
2451
|
+
};
|
|
2452
|
+
}
|
|
2453
|
+
|
|
2454
|
+
// src/shares/execution.ts
|
|
2455
|
+
import { createHash as createHash2, randomBytes, randomUUID as randomUUID5 } from "crypto";
|
|
2456
|
+
var MAX_CREATE_ATTEMPTS = 5;
|
|
2457
|
+
|
|
2458
|
+
class ShareError2 extends Error {
|
|
2459
|
+
reason;
|
|
2460
|
+
name = "ShareError";
|
|
2461
|
+
constructor(reason, message, options) {
|
|
2462
|
+
super(message, options);
|
|
2463
|
+
this.reason = reason;
|
|
2464
|
+
}
|
|
2465
|
+
}
|
|
2466
|
+
function createSharesRuntime(runtime, execution, definitions) {
|
|
2467
|
+
const managementPrincipal = () => {
|
|
2468
|
+
const authority = resolveExecutionScopeAuthorization(runtime.projectId, {
|
|
2469
|
+
execution,
|
|
2470
|
+
authorization: runtime.runtimeAuthorization
|
|
2471
|
+
});
|
|
2472
|
+
if (authority.type !== "principal" || authority.context.principal.type === "system") {
|
|
2473
|
+
throw new ShareError2("unauthenticated", "[Sixb] Shared access grants require user or service-account authority.");
|
|
2474
|
+
}
|
|
2475
|
+
return {
|
|
2476
|
+
type: authority.context.principal.type,
|
|
2477
|
+
id: authority.context.principal.id
|
|
2478
|
+
};
|
|
2479
|
+
};
|
|
2480
|
+
const canManage = (shareId) => {
|
|
2481
|
+
try {
|
|
2482
|
+
managementPrincipal();
|
|
2483
|
+
return isRuntimeAllowed2(runtime, { kind: "share.manage", shareId });
|
|
2484
|
+
} catch {
|
|
2485
|
+
return false;
|
|
2486
|
+
}
|
|
2487
|
+
};
|
|
2488
|
+
const resolveManageableDefinition = (definitionId) => {
|
|
2489
|
+
const id = validDefinitionId(definitionId);
|
|
2490
|
+
managementPrincipal();
|
|
2491
|
+
assertCanManage(runtime, id);
|
|
2492
|
+
return resolveDefinition(definitions, id);
|
|
2493
|
+
};
|
|
2494
|
+
const issueByDefinition = async (definition, input) => {
|
|
2495
|
+
assertInputObject(input, "Shared access issue input");
|
|
2496
|
+
const issuer = managementPrincipal();
|
|
2497
|
+
assertCanManage(runtime, definition.id);
|
|
2498
|
+
const storage = requireShareStorage(runtime);
|
|
2499
|
+
const createdAt = new Date;
|
|
2500
|
+
const expiresAt = validFutureDate(input.expiresAt, createdAt);
|
|
2501
|
+
const target = exactTarget(definition, input.target);
|
|
2502
|
+
const object = await runtime.objectReader.getByPrimaryId({
|
|
2503
|
+
objectTypeId: target.objectTypeId,
|
|
2504
|
+
primaryId: target.primaryId
|
|
2505
|
+
});
|
|
2506
|
+
if (!object) {
|
|
2507
|
+
throw new ObjectNotFoundError2(target.objectTypeId, target.primaryId, "Share target not found");
|
|
2508
|
+
}
|
|
2509
|
+
const authoritySnapshot = {
|
|
2510
|
+
version: 1,
|
|
2511
|
+
access: compileShareAccessPlan({
|
|
2512
|
+
share: definition,
|
|
2513
|
+
target,
|
|
2514
|
+
ontology: runtime.ontology,
|
|
2515
|
+
actions: runtime.actionRegistry
|
|
2516
|
+
})
|
|
2517
|
+
};
|
|
2518
|
+
for (let attempt = 0;attempt < MAX_CREATE_ATTEMPTS; attempt += 1) {
|
|
2519
|
+
const secret = randomBytes(32).toString("base64url");
|
|
2520
|
+
try {
|
|
2521
|
+
const grant = await storage.create({
|
|
2522
|
+
id: `shr_${randomUUID5()}`,
|
|
2523
|
+
projectId: runtime.projectId,
|
|
2524
|
+
definitionId: definition.id,
|
|
2525
|
+
target,
|
|
2526
|
+
issuedBy: issuer,
|
|
2527
|
+
authoritySnapshot,
|
|
2528
|
+
tokenHash: sha256(secret),
|
|
2529
|
+
destinationPath: input.destinationPath,
|
|
2530
|
+
createdAt,
|
|
2531
|
+
expiresAt
|
|
2532
|
+
});
|
|
2533
|
+
return { grant: publicGrant(grant), secret };
|
|
2534
|
+
} catch (error) {
|
|
2535
|
+
if (error instanceof ShareGrantStorageError2 && error.code === "invalid_input") {
|
|
2536
|
+
throw new ShareError2("invalid_input", error.message, { cause: error });
|
|
2537
|
+
}
|
|
2538
|
+
if (!(error instanceof ShareGrantStorageError2) || error.code !== "duplicate" || attempt === MAX_CREATE_ATTEMPTS - 1) {
|
|
2539
|
+
throw storageFailure("issue", error);
|
|
2540
|
+
}
|
|
2541
|
+
}
|
|
2542
|
+
}
|
|
2543
|
+
throw storageFailure("issue");
|
|
2544
|
+
};
|
|
2545
|
+
const listByDefinition = async (definition, input = {}) => {
|
|
2546
|
+
assertInputObject(input, "Shared access list input");
|
|
2547
|
+
managementPrincipal();
|
|
2548
|
+
assertCanManage(runtime, definition.id);
|
|
2549
|
+
const storage = requireShareStorage(runtime);
|
|
2550
|
+
const target = input.target === undefined ? undefined : exactTarget(definition, input.target);
|
|
2551
|
+
try {
|
|
2552
|
+
const result = await storage.list({
|
|
2553
|
+
projectId: runtime.projectId,
|
|
2554
|
+
definitionId: definition.id,
|
|
2555
|
+
...target === undefined ? {} : { target },
|
|
2556
|
+
includeRevoked: input.includeRevoked,
|
|
2557
|
+
includeExpired: input.includeExpired,
|
|
2558
|
+
now: new Date,
|
|
2559
|
+
limit: input.limit,
|
|
2560
|
+
offset: input.offset
|
|
2561
|
+
});
|
|
2562
|
+
return { ...result, grants: result.grants.map(publicGrant) };
|
|
2563
|
+
} catch (error) {
|
|
2564
|
+
if (error instanceof ShareGrantStorageError2 && error.code === "invalid_input") {
|
|
2565
|
+
throw new ShareError2("invalid_input", error.message, { cause: error });
|
|
2566
|
+
}
|
|
2567
|
+
throw storageFailure("list", error);
|
|
2568
|
+
}
|
|
2569
|
+
};
|
|
2570
|
+
return {
|
|
2571
|
+
listDefinitions: () => definitions.list().filter((definition) => canManage(definition.id)),
|
|
2572
|
+
getDefinitionById: (definitionId) => {
|
|
2573
|
+
const definition = definitions.getById(definitionId);
|
|
2574
|
+
return definition && canManage(definition.id) ? definition : null;
|
|
2575
|
+
},
|
|
2576
|
+
async issue(definition, input) {
|
|
2577
|
+
return issueByDefinition(resolveManageableDefinition(definitionIdFromReference(definition)), input);
|
|
2578
|
+
},
|
|
2579
|
+
async issueById(input) {
|
|
2580
|
+
assertInputObject(input, "Shared access issue input");
|
|
2581
|
+
return issueByDefinition(resolveManageableDefinition(input.definitionId), input);
|
|
2582
|
+
},
|
|
2583
|
+
async list(definition, input) {
|
|
2584
|
+
return listByDefinition(resolveManageableDefinition(definitionIdFromReference(definition)), input);
|
|
2585
|
+
},
|
|
2586
|
+
async listById(input) {
|
|
2587
|
+
assertInputObject(input, "Shared access list input");
|
|
2588
|
+
const definition = resolveManageableDefinition(input.definitionId);
|
|
2589
|
+
const { primaryId, includeRevoked, includeExpired, limit, offset } = input;
|
|
2590
|
+
return listByDefinition(definition, {
|
|
2591
|
+
...primaryId === undefined ? {} : {
|
|
2592
|
+
target: {
|
|
2593
|
+
objectTypeId: definition.target.objectTypeId,
|
|
2594
|
+
primaryId
|
|
2595
|
+
}
|
|
2596
|
+
},
|
|
2597
|
+
includeRevoked,
|
|
2598
|
+
includeExpired,
|
|
2599
|
+
limit,
|
|
2600
|
+
offset
|
|
2601
|
+
});
|
|
2602
|
+
},
|
|
2603
|
+
revoke: async (grantId) => {
|
|
2604
|
+
const actor = managementPrincipal();
|
|
2605
|
+
const storage = requireShareStorage(runtime);
|
|
2606
|
+
if (typeof grantId !== "string" || !grantId.trim()) {
|
|
2607
|
+
throw new ShareError2("invalid_input", "[Sixb] Shared access grant id must not be empty.");
|
|
2608
|
+
}
|
|
2609
|
+
let current;
|
|
2610
|
+
try {
|
|
2611
|
+
current = await storage.getById({ projectId: runtime.projectId, id: grantId });
|
|
2612
|
+
} catch (error) {
|
|
2613
|
+
throw storageFailure("load for revocation", error);
|
|
2614
|
+
}
|
|
2615
|
+
if (!current)
|
|
2616
|
+
return null;
|
|
2617
|
+
if (!definitions.getById(current.definitionId) || !canManage(current.definitionId)) {
|
|
2618
|
+
return null;
|
|
2619
|
+
}
|
|
2620
|
+
try {
|
|
2621
|
+
const revoked = await storage.revoke({
|
|
2622
|
+
projectId: runtime.projectId,
|
|
2623
|
+
id: grantId,
|
|
2624
|
+
revokedAt: new Date,
|
|
2625
|
+
revokedBy: actor
|
|
2626
|
+
});
|
|
2627
|
+
return revoked ? publicGrant(revoked) : null;
|
|
2628
|
+
} catch (error) {
|
|
2629
|
+
throw storageFailure("revoke", error);
|
|
2630
|
+
}
|
|
2631
|
+
}
|
|
2632
|
+
};
|
|
2633
|
+
}
|
|
2634
|
+
function definitionIdFromReference(value) {
|
|
2635
|
+
return typeof value === "object" && value !== null ? value.id : undefined;
|
|
2636
|
+
}
|
|
2637
|
+
function assertInputObject(value, label) {
|
|
2638
|
+
if (typeof value !== "object" || value === null || Array.isArray(value)) {
|
|
2639
|
+
throw new ShareError2("invalid_input", `[Sixb] ${label} must be an object.`);
|
|
2640
|
+
}
|
|
2641
|
+
}
|
|
2642
|
+
function resolveDefinition(definitions, definitionId) {
|
|
2643
|
+
const id = validDefinitionId(definitionId);
|
|
2644
|
+
const definition = definitions.getById(id);
|
|
2645
|
+
if (!definition) {
|
|
2646
|
+
throw new ShareError2("not_found", `[Sixb] Unknown Share definition '${id}'.`);
|
|
2647
|
+
}
|
|
2648
|
+
return definition;
|
|
2649
|
+
}
|
|
2650
|
+
function validDefinitionId(value) {
|
|
2651
|
+
if (typeof value !== "string" || !value.trim()) {
|
|
2652
|
+
throw new ShareError2("invalid_input", "[Sixb] Share definition id must not be empty.");
|
|
2653
|
+
}
|
|
2654
|
+
return value;
|
|
2655
|
+
}
|
|
2656
|
+
function assertCanManage(runtime, shareId) {
|
|
2657
|
+
assertAuthorized2(runtime, { kind: "share.manage", shareId });
|
|
2658
|
+
}
|
|
2659
|
+
function requireShareStorage(runtime) {
|
|
2660
|
+
const storage = runtime.storage.shareGrants;
|
|
2661
|
+
if (!storage) {
|
|
2662
|
+
throw new ShareError2("storage_unavailable", "[Sixb] Share grant storage is not configured on this runtime.");
|
|
2663
|
+
}
|
|
2664
|
+
return storage;
|
|
2665
|
+
}
|
|
2666
|
+
function exactTarget(definition, value) {
|
|
2667
|
+
if (typeof value !== "object" || value === null || Array.isArray(value)) {
|
|
2668
|
+
throw new ShareError2("invalid_input", "[Sixb] Share target must be an exact object reference.");
|
|
2669
|
+
}
|
|
2670
|
+
const objectTypeId = value.objectTypeId;
|
|
2671
|
+
const primaryId = value.primaryId;
|
|
2672
|
+
if (typeof objectTypeId !== "string" || typeof primaryId !== "string" || !primaryId.trim()) {
|
|
2673
|
+
throw new ShareError2("invalid_input", "[Sixb] Share target must be an exact object reference.");
|
|
2674
|
+
}
|
|
2675
|
+
if (objectTypeId !== definition.target.objectTypeId) {
|
|
2676
|
+
throw new ShareError2("invalid_input", `[Sixb] Share '${definition.id}' targets '${definition.target.objectTypeId}', not '${objectTypeId}'.`);
|
|
2677
|
+
}
|
|
2678
|
+
return Object.freeze({ objectTypeId, primaryId });
|
|
2679
|
+
}
|
|
2680
|
+
function validFutureDate(value, now) {
|
|
2681
|
+
if (!(value instanceof Date) || !Number.isFinite(value.getTime()) || value <= now) {
|
|
2682
|
+
throw new ShareError2("invalid_input", "[Sixb] Shared access expiry must be a valid future date.");
|
|
2683
|
+
}
|
|
2684
|
+
return new Date(value);
|
|
2685
|
+
}
|
|
2686
|
+
function sha256(value) {
|
|
2687
|
+
return createHash2("sha256").update(value).digest("hex");
|
|
2688
|
+
}
|
|
2689
|
+
function publicGrant(record) {
|
|
2690
|
+
const {
|
|
2691
|
+
projectId: _projectId,
|
|
2692
|
+
authoritySnapshot: _authoritySnapshot,
|
|
2693
|
+
authorityDigest: _authorityDigest,
|
|
2694
|
+
tokenHash: _tokenHash,
|
|
2695
|
+
...grant
|
|
2696
|
+
} = record;
|
|
2697
|
+
return structuredClone(grant);
|
|
2698
|
+
}
|
|
2699
|
+
function storageFailure(operation, cause) {
|
|
2700
|
+
return new ShareError2("storage_failure", `[Sixb] Share grant storage failed to ${operation}.`, {
|
|
2701
|
+
cause
|
|
2702
|
+
});
|
|
2703
|
+
}
|
|
2704
|
+
|
|
2705
|
+
// src/syncs/execution.ts
|
|
2706
|
+
function createSyncsRuntime(runtime, execution, source) {
|
|
2707
|
+
const authority = resolveRuntimeAuthorizationForProject(runtime);
|
|
2708
|
+
const allowed = (syncId) => isRuntimeAllowed2(runtime, { kind: "sync.run", syncId });
|
|
2709
|
+
const visibleIds = () => source.list().filter((sync) => allowed(sync.id)).map((sync) => sync.id);
|
|
2710
|
+
const historyFilterIds = () => authority.type === "unrestricted" ? undefined : authority.type === "principal" ? visibleIds() : [];
|
|
2711
|
+
return {
|
|
2712
|
+
list: () => authority.type === "denied" || authority.type === "delegated" ? [] : source.list().filter((sync) => allowed(sync.id)),
|
|
2713
|
+
getById: (syncId) => {
|
|
2714
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
2715
|
+
return null;
|
|
2716
|
+
const sync = source.getById(syncId);
|
|
2717
|
+
return sync && allowed(syncId) ? sync : null;
|
|
2718
|
+
},
|
|
2719
|
+
request: async (input) => {
|
|
2720
|
+
assertAuthorized2(runtime, { kind: "sync.run", syncId: input.syncId });
|
|
2721
|
+
const sync = source.getById(input.syncId);
|
|
2722
|
+
if (!sync)
|
|
2723
|
+
throw new SyncValidationError2(`[Sixb] Unknown sync '${input.syncId}'`);
|
|
2724
|
+
return requestSyncRun2(runtime, execution, sync, input);
|
|
2725
|
+
},
|
|
2726
|
+
runs: {
|
|
2727
|
+
getById: async (runId) => {
|
|
2728
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
2729
|
+
return null;
|
|
2730
|
+
const run = await runtime.storage.syncRuns?.getById({
|
|
2731
|
+
projectId: runtime.projectId,
|
|
2732
|
+
id: runId
|
|
2733
|
+
}) ?? null;
|
|
2734
|
+
return run && allowed(run.syncId) ? run : null;
|
|
2735
|
+
},
|
|
2736
|
+
list: (input = {}) => {
|
|
2737
|
+
if (authority.type === "denied" || authority.type === "delegated") {
|
|
2738
|
+
return Promise.resolve({ runs: [], hasMore: false, total: 0 });
|
|
2739
|
+
}
|
|
2740
|
+
const storage = runtime.storage.syncRuns;
|
|
2741
|
+
if (!storage)
|
|
2742
|
+
return Promise.resolve({ runs: [], hasMore: false, total: 0 });
|
|
2743
|
+
return storage.list({
|
|
2744
|
+
...input,
|
|
2745
|
+
syncIds: historyFilterIds(),
|
|
2746
|
+
projectId: runtime.projectId
|
|
2747
|
+
});
|
|
2748
|
+
},
|
|
2749
|
+
listLatest: (syncIds) => {
|
|
2750
|
+
if (authority.type === "denied" || authority.type === "delegated") {
|
|
2751
|
+
return Promise.resolve({ runs: [] });
|
|
2752
|
+
}
|
|
2753
|
+
const storage = runtime.storage.syncRuns;
|
|
2754
|
+
if (!storage || syncIds.length === 0)
|
|
2755
|
+
return Promise.resolve({ runs: [] });
|
|
2756
|
+
const allowedIds = syncIds.filter(allowed);
|
|
2757
|
+
return allowedIds.length === 0 ? Promise.resolve({ runs: [] }) : storage.listLatestBySyncIds({ projectId: runtime.projectId, syncIds: allowedIds });
|
|
2758
|
+
}
|
|
2759
|
+
}
|
|
2760
|
+
};
|
|
2761
|
+
}
|
|
2762
|
+
|
|
2763
|
+
// src/workflows/errors.ts
|
|
2764
|
+
class WorkflowDefinitionError2 extends Error {
|
|
2765
|
+
name = "WorkflowDefinitionError";
|
|
2766
|
+
}
|
|
2767
|
+
|
|
2768
|
+
class WorkflowValidationError2 extends Error {
|
|
2769
|
+
name = "WorkflowValidationError";
|
|
2770
|
+
cause;
|
|
2771
|
+
constructor(message, options) {
|
|
2772
|
+
super(message);
|
|
2773
|
+
this.cause = options?.cause;
|
|
2774
|
+
}
|
|
2775
|
+
}
|
|
2776
|
+
|
|
2777
|
+
// src/workflows/run-dispatch.ts
|
|
2778
|
+
import { randomUUID as randomUUID6 } from "crypto";
|
|
2779
|
+
import { isDeepStrictEqual } from "util";
|
|
2780
|
+
|
|
2781
|
+
// src/workflows/validation.ts
|
|
2782
|
+
function assertNonEmpty(value, subject, field) {
|
|
2783
|
+
if (!value.trim()) {
|
|
2784
|
+
throw new WorkflowDefinitionError2(`${subject} ${field} must not be empty.`);
|
|
2785
|
+
}
|
|
2786
|
+
}
|
|
2787
|
+
function isStepDefinition2(value) {
|
|
2788
|
+
return isRecord(value) && value.kind === "step" && typeof value.id === "string" && isRecord(value.input) && isRecord(value.output) && typeof value.handler === "function";
|
|
2789
|
+
}
|
|
2790
|
+
function isAgentStepDefinition2(value) {
|
|
2791
|
+
return isRecord(value) && value.kind === "agentStep" && typeof value.id === "string" && (value.model === undefined || isLanguageModel(value.model)) && (value.reasoning === undefined || isModelReasoning2(value.reasoning)) && typeof value.instructions === "string" && isStringArray(value.groupIds) && isStringArray(value.toolNames) && isRecord(value.input) && isRecord(value.output) && typeof value.prompt === "function";
|
|
2792
|
+
}
|
|
2793
|
+
function isInterventionDefinition2(value) {
|
|
2794
|
+
return isRecord(value) && value.kind === "intervention" && typeof value.id === "string" && isRecord(value.input) && isRecord(value.response) && (value.defaults === undefined || typeof value.defaults === "function");
|
|
2795
|
+
}
|
|
2796
|
+
function isWorkflowDefinition2(value) {
|
|
2797
|
+
return isRecord(value) && value.kind === "workflow" && typeof value.id === "string" && isRecord(value.input) && Array.isArray(value.triggers) && Array.isArray(value.nodes);
|
|
2798
|
+
}
|
|
2799
|
+
function validateWorkflowDefinition2(value) {
|
|
2800
|
+
if (!isWorkflowDefinition2(value)) {
|
|
2801
|
+
throw new WorkflowDefinitionError2("Invalid workflow definition.");
|
|
2802
|
+
}
|
|
2803
|
+
assertNonEmpty(value.id, "Workflow", "id");
|
|
2804
|
+
if (value.nodes.length === 0) {
|
|
2805
|
+
throw new WorkflowDefinitionError2(`Workflow "${value.id}" must contain at least one node.`);
|
|
2806
|
+
}
|
|
2807
|
+
const nodeIds = new Set;
|
|
2808
|
+
const nodeKeys = new Set;
|
|
2809
|
+
for (const node of value.nodes) {
|
|
2810
|
+
validateWorkflowNodeDefinition(value.id, node);
|
|
2811
|
+
if (nodeIds.has(node.id)) {
|
|
2812
|
+
throw new WorkflowDefinitionError2(`Duplicate workflow node id "${node.id}" in workflow "${value.id}".`);
|
|
2813
|
+
}
|
|
2814
|
+
nodeIds.add(node.id);
|
|
2815
|
+
if (nodeKeys.has(node.key)) {
|
|
2816
|
+
throw new WorkflowDefinitionError2(`Duplicate workflow node key "${node.key}" in workflow "${value.id}".`);
|
|
2817
|
+
}
|
|
2818
|
+
nodeKeys.add(node.key);
|
|
2819
|
+
}
|
|
2820
|
+
}
|
|
2821
|
+
function validateWorkflowsAtStartup2(options) {
|
|
2822
|
+
for (const workflow of options.workflows) {
|
|
2823
|
+
validateWorkflowDefinition2(workflow);
|
|
2824
|
+
for (const trigger of workflow.triggers) {
|
|
2825
|
+
validateWorkflowTriggerAtStartup(workflow.id, trigger, options.registeredSchedules, Object.keys(workflow.input));
|
|
2826
|
+
}
|
|
2827
|
+
for (const node of workflow.nodes) {
|
|
2828
|
+
if (node.type === "action" && !options.registeredActionIds.has(node.action.id)) {
|
|
2829
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflow.id}" references unknown action "${node.action.id}". Add it to 'actions' in createSixb() or export it from 'actions/'.`);
|
|
2830
|
+
}
|
|
2831
|
+
if (node.type === "agent") {
|
|
2832
|
+
validateWorkflowAgentStepRuntimeReferences(workflow.id, node.agentStep, options);
|
|
2833
|
+
}
|
|
2834
|
+
}
|
|
2835
|
+
}
|
|
2836
|
+
return options.workflows;
|
|
2837
|
+
}
|
|
2838
|
+
function validateWorkflowAgentStepGroupReferences2(workflows, security) {
|
|
2839
|
+
for (const workflow of workflows) {
|
|
2840
|
+
for (const node of workflow.nodes) {
|
|
2841
|
+
if (node.type !== "agent")
|
|
2842
|
+
continue;
|
|
2843
|
+
for (const groupId of node.agentStep.groupIds) {
|
|
2844
|
+
if (!security.getGroupById(groupId)) {
|
|
2845
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflow.id}" agent step "${node.id}" references unknown group "${groupId}". Add it to 'security/groups/' or pass it to createSixb({ groups }).`);
|
|
2846
|
+
}
|
|
2847
|
+
}
|
|
2848
|
+
}
|
|
2849
|
+
}
|
|
2850
|
+
}
|
|
2851
|
+
function validateWorkflowAgentStepRuntimeReferences(workflowId, step, options) {
|
|
2852
|
+
if (step.model === undefined && options.models === undefined) {
|
|
2853
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" agent step "${step.id}" needs a model. Configure 'models.language' or pass 'model' to defineAgentStep().`);
|
|
2854
|
+
}
|
|
2855
|
+
if (step.model !== undefined && options.models !== undefined) {
|
|
2856
|
+
const ref = { provider: step.model.providerId, modelId: step.model.modelId };
|
|
2857
|
+
if (options.models.language.getByRef(ref) === null) {
|
|
2858
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" agent step "${step.id}" uses unknown language model "${ref.provider}/${ref.modelId}". Add it to 'models.language' in createSixb().`);
|
|
2859
|
+
}
|
|
2860
|
+
}
|
|
2861
|
+
for (const toolName of step.toolNames) {
|
|
2862
|
+
if (options.tools.getByName(toolName) === null) {
|
|
2863
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" agent step "${step.id}" uses unknown project tool "${toolName}". Add it to 'tools' in createSixb().`);
|
|
2864
|
+
}
|
|
2865
|
+
}
|
|
2866
|
+
}
|
|
2867
|
+
function validateWorkflowInput2(params) {
|
|
2868
|
+
return validateWorkflowContractRecord({
|
|
2869
|
+
shape: params.workflow.input,
|
|
2870
|
+
value: params.value,
|
|
2871
|
+
path: `Workflow "${params.workflow.id}" input`,
|
|
2872
|
+
valueTypesById: params.valueTypesById
|
|
2873
|
+
});
|
|
2874
|
+
}
|
|
2875
|
+
function validateWorkflowStepInput2(params) {
|
|
2876
|
+
return validateWorkflowContractRecord({
|
|
2877
|
+
shape: params.step.input,
|
|
2878
|
+
value: params.value,
|
|
2879
|
+
path: `Workflow "${params.workflowId}" step "${params.step.id}" input`,
|
|
2880
|
+
valueTypesById: params.valueTypesById
|
|
2881
|
+
});
|
|
2882
|
+
}
|
|
2883
|
+
function validateWorkflowStepOutput2(params) {
|
|
2884
|
+
return validateWorkflowContractRecord({
|
|
2885
|
+
shape: params.step.output,
|
|
2886
|
+
value: params.value,
|
|
2887
|
+
path: `Workflow "${params.workflowId}" step "${params.step.id}" output`,
|
|
2888
|
+
valueTypesById: params.valueTypesById
|
|
2889
|
+
});
|
|
2890
|
+
}
|
|
2891
|
+
function validateWorkflowInterventionInput2(params) {
|
|
2892
|
+
return validateWorkflowContractRecord({
|
|
2893
|
+
shape: params.intervention.input,
|
|
2894
|
+
value: params.value,
|
|
2895
|
+
path: `Workflow "${params.workflowId}" intervention "${params.intervention.id}" input`,
|
|
2896
|
+
valueTypesById: params.valueTypesById
|
|
2897
|
+
});
|
|
2898
|
+
}
|
|
2899
|
+
function validateWorkflowInterventionResponse2(params) {
|
|
2900
|
+
return validateWorkflowInterventionResponseRecord({
|
|
2901
|
+
response: params.intervention.response,
|
|
2902
|
+
value: params.value,
|
|
2903
|
+
path: `Workflow "${params.workflowId}" intervention "${params.intervention.id}" response`,
|
|
2904
|
+
partial: false,
|
|
2905
|
+
valueTypesById: params.valueTypesById
|
|
2906
|
+
});
|
|
2907
|
+
}
|
|
2908
|
+
function validateWorkflowInterventionDefaultResponse2(params) {
|
|
2909
|
+
return validateWorkflowInterventionResponseRecord({
|
|
2910
|
+
response: params.intervention.response,
|
|
2911
|
+
value: params.value,
|
|
2912
|
+
path: `Workflow "${params.workflowId}" intervention "${params.intervention.id}" defaultResponse`,
|
|
2913
|
+
partial: true,
|
|
2914
|
+
valueTypesById: params.valueTypesById
|
|
2915
|
+
});
|
|
2916
|
+
}
|
|
2917
|
+
function validateWorkflowTriggerAtStartup(workflowId, trigger, registeredSchedules, inputFields) {
|
|
2918
|
+
if (!isRecord(trigger) || trigger.type !== "schedule") {
|
|
2919
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an unsupported trigger.`);
|
|
2920
|
+
}
|
|
2921
|
+
validateScheduleWorkflowTrigger(workflowId, trigger, registeredSchedules, inputFields);
|
|
2922
|
+
}
|
|
2923
|
+
function validateScheduleWorkflowTrigger(workflowId, trigger, registeredSchedules, inputFields) {
|
|
2924
|
+
if (typeof trigger.scheduleId !== "string" || !trigger.scheduleId.trim()) {
|
|
2925
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains a schedule trigger with an empty schedule id.`);
|
|
2926
|
+
}
|
|
2927
|
+
const schedule = registeredSchedules.get(trigger.scheduleId);
|
|
2928
|
+
if (!schedule) {
|
|
2929
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" references unknown schedule "${trigger.scheduleId}". Add it to 'schedules' in createSixb() or export it from 'schedules/'.`);
|
|
2930
|
+
}
|
|
2931
|
+
if (trigger.mapper !== undefined && typeof trigger.mapper !== "function") {
|
|
2932
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" schedule "${trigger.scheduleId}" mapper must be a function.`);
|
|
2933
|
+
}
|
|
2934
|
+
if (trigger.mapper !== undefined && schedule.trigger.type !== "event") {
|
|
2935
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" cron schedule "${trigger.scheduleId}" does not accept a mapper.`);
|
|
2936
|
+
}
|
|
2937
|
+
if (trigger.mapper === undefined && inputFields.length > 0) {
|
|
2938
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" schedule "${trigger.scheduleId}" requires a mapper because workflow input is not empty: ${inputFields.join(", ")}.`);
|
|
2939
|
+
}
|
|
2940
|
+
}
|
|
2941
|
+
function validateWorkflowNodeDefinition(workflowId, node) {
|
|
2942
|
+
if (!isRecord(node)) {
|
|
2943
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an invalid node.`);
|
|
2944
|
+
}
|
|
2945
|
+
if (node.type === "step") {
|
|
2946
|
+
validateStepNodeDefinition(workflowId, node);
|
|
2947
|
+
return;
|
|
2948
|
+
}
|
|
2949
|
+
if (node.type === "agent") {
|
|
2950
|
+
validateAgentNodeDefinition(workflowId, node);
|
|
2951
|
+
return;
|
|
2952
|
+
}
|
|
2953
|
+
if (node.type === "intervention") {
|
|
2954
|
+
validateInterventionNodeDefinition(workflowId, node);
|
|
2955
|
+
return;
|
|
2956
|
+
}
|
|
2957
|
+
if (node.type === "action") {
|
|
2958
|
+
validateActionNodeDefinition(workflowId, node);
|
|
2959
|
+
return;
|
|
2960
|
+
}
|
|
2961
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an unsupported node type.`);
|
|
2962
|
+
}
|
|
2963
|
+
function validateAgentNodeDefinition(workflowId, node) {
|
|
2964
|
+
if (typeof node.id !== "string" || !node.id.trim()) {
|
|
2965
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an agent step with an empty id.`);
|
|
2966
|
+
}
|
|
2967
|
+
if (typeof node.key !== "string" || !node.key.trim()) {
|
|
2968
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains agent step "${node.id}" with an empty derived key.`);
|
|
2969
|
+
}
|
|
2970
|
+
if (!isAgentStepDefinition2(node.agentStep)) {
|
|
2971
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an invalid agent node "${node.id}".`);
|
|
2972
|
+
}
|
|
2973
|
+
if (node.id !== node.agentStep.id) {
|
|
2974
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" agent node id "${node.id}" does not match agent step definition id "${node.agentStep.id}".`);
|
|
2975
|
+
}
|
|
2976
|
+
if (!node.agentStep.instructions.trim()) {
|
|
2977
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" agent step "${node.id}" instructions must not be empty.`);
|
|
2978
|
+
}
|
|
2979
|
+
assertUniqueNonEmptyAgentStepValues(workflowId, node.id, "group", node.agentStep.groupIds);
|
|
2980
|
+
assertUniqueNonEmptyAgentStepValues(workflowId, node.id, "tool", node.agentStep.toolNames);
|
|
2981
|
+
if (node.mapper !== undefined && typeof node.mapper !== "function") {
|
|
2982
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" agent node "${node.id}" mapper must be a function.`);
|
|
2983
|
+
}
|
|
2984
|
+
}
|
|
2985
|
+
function assertUniqueNonEmptyAgentStepValues(workflowId, stepId, kind, values) {
|
|
2986
|
+
const seen = new Set;
|
|
2987
|
+
for (const value of values) {
|
|
2988
|
+
if (!value.trim()) {
|
|
2989
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" agent step "${stepId}" has an empty ${kind} id.`);
|
|
2990
|
+
}
|
|
2991
|
+
if (seen.has(value)) {
|
|
2992
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" agent step "${stepId}" has duplicate ${kind} '${value}'.`);
|
|
2993
|
+
}
|
|
2994
|
+
seen.add(value);
|
|
2995
|
+
}
|
|
2996
|
+
}
|
|
2997
|
+
function isLanguageModel(value) {
|
|
2998
|
+
return (typeof value === "object" || typeof value === "function") && value !== null;
|
|
2999
|
+
}
|
|
3000
|
+
function isStringArray(value) {
|
|
3001
|
+
if (!Array.isArray(value))
|
|
3002
|
+
return false;
|
|
3003
|
+
for (let index = 0;index < value.length; index += 1) {
|
|
3004
|
+
if (!Object.hasOwn(value, index) || typeof value[index] !== "string")
|
|
3005
|
+
return false;
|
|
3006
|
+
}
|
|
3007
|
+
return true;
|
|
3008
|
+
}
|
|
3009
|
+
function validateWorkflowAgentStepInput2(params) {
|
|
3010
|
+
return validateWorkflowContractRecord({
|
|
3011
|
+
shape: params.agentStep.input,
|
|
3012
|
+
value: params.value,
|
|
3013
|
+
path: `Workflow "${params.workflowId}" agent step "${params.agentStep.id}" input`,
|
|
3014
|
+
valueTypesById: params.valueTypesById
|
|
3015
|
+
});
|
|
3016
|
+
}
|
|
3017
|
+
function validateWorkflowAgentStepOutput2(params) {
|
|
3018
|
+
return validateWorkflowContractRecord({
|
|
3019
|
+
shape: params.agentStep.output,
|
|
3020
|
+
value: params.value,
|
|
3021
|
+
path: `Workflow "${params.workflowId}" agent step "${params.agentStep.id}" output`,
|
|
3022
|
+
valueTypesById: params.valueTypesById
|
|
3023
|
+
});
|
|
3024
|
+
}
|
|
3025
|
+
function validateStepNodeDefinition(workflowId, node) {
|
|
3026
|
+
if (typeof node.id !== "string" || !node.id.trim()) {
|
|
3027
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains a step with an empty id.`);
|
|
3028
|
+
}
|
|
3029
|
+
if (typeof node.key !== "string" || !node.key.trim()) {
|
|
3030
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains step "${node.id}" with an empty derived key.`);
|
|
3031
|
+
}
|
|
3032
|
+
if (!isStepDefinition2(node.step)) {
|
|
3033
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an invalid step node "${node.id}".`);
|
|
3034
|
+
}
|
|
3035
|
+
if (node.id !== node.step.id) {
|
|
3036
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" step node id "${node.id}" does not match step definition id "${node.step.id}".`);
|
|
3037
|
+
}
|
|
3038
|
+
if (node.mapper !== undefined && typeof node.mapper !== "function") {
|
|
3039
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" step node "${node.id}" mapper must be a function.`);
|
|
3040
|
+
}
|
|
3041
|
+
}
|
|
3042
|
+
function validateInterventionNodeDefinition(workflowId, node) {
|
|
3043
|
+
if (typeof node.id !== "string" || !node.id.trim()) {
|
|
3044
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an intervention with an empty id.`);
|
|
3045
|
+
}
|
|
3046
|
+
if (typeof node.key !== "string" || !node.key.trim()) {
|
|
3047
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains intervention "${node.id}" with an empty derived key.`);
|
|
3048
|
+
}
|
|
3049
|
+
if (!isInterventionDefinition2(node.intervention)) {
|
|
3050
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an invalid intervention node "${node.id}".`);
|
|
3051
|
+
}
|
|
3052
|
+
if (node.id !== node.intervention.id) {
|
|
3053
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" intervention node id "${node.id}" does not match intervention definition id "${node.intervention.id}".`);
|
|
3054
|
+
}
|
|
3055
|
+
if (node.mapper !== undefined && typeof node.mapper !== "function") {
|
|
3056
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" intervention node "${node.id}" mapper must be a function.`);
|
|
3057
|
+
}
|
|
3058
|
+
}
|
|
3059
|
+
function validateActionNodeDefinition(workflowId, node) {
|
|
3060
|
+
if (typeof node.id !== "string" || !node.id.trim()) {
|
|
3061
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an action with an empty id.`);
|
|
3062
|
+
}
|
|
3063
|
+
if (typeof node.key !== "string" || !node.key.trim()) {
|
|
3064
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains action "${node.id}" with an empty derived key.`);
|
|
3065
|
+
}
|
|
3066
|
+
if (!isActionDefinition2(node.action)) {
|
|
3067
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" contains an invalid action node "${node.id}".`);
|
|
3068
|
+
}
|
|
3069
|
+
if (node.id !== node.action.id) {
|
|
3070
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" action node id "${node.id}" does not match action definition id "${node.action.id}".`);
|
|
3071
|
+
}
|
|
3072
|
+
if (node.mapper !== undefined && typeof node.mapper !== "function") {
|
|
3073
|
+
throw new WorkflowDefinitionError2(`Workflow "${workflowId}" action node "${node.id}" mapper must be a function.`);
|
|
3074
|
+
}
|
|
3075
|
+
}
|
|
3076
|
+
function validateWorkflowContractRecord(params) {
|
|
3077
|
+
if (!isRecord(params.value)) {
|
|
3078
|
+
throw new WorkflowValidationError2(`[Sixb] ${params.path} must be an object`);
|
|
3079
|
+
}
|
|
3080
|
+
const fieldIds = new Set(Object.keys(params.shape));
|
|
3081
|
+
for (const fieldId of Object.keys(params.value)) {
|
|
3082
|
+
if (!fieldIds.has(fieldId)) {
|
|
3083
|
+
throw new WorkflowValidationError2(`[Sixb] Unknown field '${params.path}.${fieldId}'`);
|
|
3084
|
+
}
|
|
3085
|
+
}
|
|
3086
|
+
for (const [fieldId, schema] of Object.entries(params.shape)) {
|
|
3087
|
+
const fieldValue = params.value[fieldId];
|
|
3088
|
+
if (fieldValue === undefined) {
|
|
3089
|
+
throw new WorkflowValidationError2(`[Sixb] Missing required field '${params.path}.${fieldId}'`);
|
|
3090
|
+
}
|
|
3091
|
+
try {
|
|
3092
|
+
validateSchemaOrRefValue2(schema, fieldValue, `${params.path}.${fieldId}`, params.valueTypesById);
|
|
3093
|
+
} catch (error) {
|
|
3094
|
+
throw toWorkflowValidationError(error);
|
|
3095
|
+
}
|
|
3096
|
+
}
|
|
3097
|
+
return params.value;
|
|
3098
|
+
}
|
|
3099
|
+
function validateWorkflowInterventionResponseRecord(params) {
|
|
3100
|
+
if (!isRecord(params.value)) {
|
|
3101
|
+
throw new WorkflowValidationError2(`[Sixb] ${params.path} must be an object`);
|
|
3102
|
+
}
|
|
3103
|
+
const fieldIds = new Set(Object.keys(params.response));
|
|
3104
|
+
for (const fieldId of Object.keys(params.value)) {
|
|
3105
|
+
if (!fieldIds.has(fieldId)) {
|
|
3106
|
+
throw new WorkflowValidationError2(`[Sixb] Unknown field '${params.path}.${fieldId}'`);
|
|
3107
|
+
}
|
|
3108
|
+
}
|
|
3109
|
+
for (const [fieldId, field] of Object.entries(params.response)) {
|
|
3110
|
+
const fieldValue = params.value[fieldId];
|
|
3111
|
+
if (fieldValue === undefined) {
|
|
3112
|
+
if (!params.partial && isInterventionResponseFieldRequired(field)) {
|
|
3113
|
+
throw new WorkflowValidationError2(`[Sixb] Missing required field '${params.path}.${fieldId}'`);
|
|
3114
|
+
}
|
|
3115
|
+
continue;
|
|
3116
|
+
}
|
|
3117
|
+
try {
|
|
3118
|
+
validateSchemaOrRefValue2(interventionResponseFieldSchema(field), fieldValue, `${params.path}.${fieldId}`, params.valueTypesById);
|
|
3119
|
+
} catch (error) {
|
|
3120
|
+
throw toWorkflowValidationError(error);
|
|
3121
|
+
}
|
|
3122
|
+
}
|
|
3123
|
+
return params.value;
|
|
3124
|
+
}
|
|
3125
|
+
function isInterventionFieldConfig(value) {
|
|
3126
|
+
return isRecord(value) && "schema" in value;
|
|
3127
|
+
}
|
|
3128
|
+
function interventionResponseFieldSchema(field) {
|
|
3129
|
+
return isInterventionFieldConfig(field) ? field.schema : field;
|
|
3130
|
+
}
|
|
3131
|
+
function isInterventionResponseFieldRequired(field) {
|
|
3132
|
+
return !isInterventionFieldConfig(field) || field.required !== false;
|
|
3133
|
+
}
|
|
3134
|
+
function toWorkflowValidationError(error) {
|
|
3135
|
+
if (error instanceof WorkflowValidationError2) {
|
|
3136
|
+
return error;
|
|
3137
|
+
}
|
|
3138
|
+
if (error instanceof Error) {
|
|
3139
|
+
return new WorkflowValidationError2(error.message, { cause: error });
|
|
3140
|
+
}
|
|
3141
|
+
return new WorkflowValidationError2(String(error), { cause: error });
|
|
3142
|
+
}
|
|
3143
|
+
function isRecord(value) {
|
|
3144
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
3145
|
+
}
|
|
3146
|
+
|
|
3147
|
+
// src/workflows/snapshot.ts
|
|
3148
|
+
function snapshotWorkflowAgentStepInput2(params) {
|
|
3149
|
+
const value = validateWorkflowAgentStepInput2(params);
|
|
3150
|
+
return snapshotWorkflowContractRecord({
|
|
3151
|
+
shape: params.agentStep.input,
|
|
3152
|
+
value,
|
|
3153
|
+
path: `Workflow "${params.workflowId}" agent step "${params.agentStep.id}" input`,
|
|
3154
|
+
valueTypesById: params.valueTypesById
|
|
3155
|
+
});
|
|
3156
|
+
}
|
|
3157
|
+
function snapshotWorkflowAgentStepOutput2(params) {
|
|
3158
|
+
const value = validateWorkflowAgentStepOutput2(params);
|
|
3159
|
+
return snapshotWorkflowContractRecord({
|
|
3160
|
+
shape: params.agentStep.output,
|
|
3161
|
+
value,
|
|
3162
|
+
path: `Workflow "${params.workflowId}" agent step "${params.agentStep.id}" output`,
|
|
3163
|
+
valueTypesById: params.valueTypesById
|
|
3164
|
+
});
|
|
3165
|
+
}
|
|
3166
|
+
function snapshotWorkflowInput2(params) {
|
|
3167
|
+
const value = validateWorkflowInput2(params);
|
|
3168
|
+
return snapshotWorkflowContractRecord({
|
|
3169
|
+
shape: params.workflow.input,
|
|
3170
|
+
value,
|
|
3171
|
+
path: `Workflow "${params.workflow.id}" input`,
|
|
3172
|
+
valueTypesById: params.valueTypesById
|
|
3173
|
+
});
|
|
3174
|
+
}
|
|
3175
|
+
function snapshotWorkflowStepInput2(params) {
|
|
3176
|
+
const value = validateWorkflowStepInput2(params);
|
|
3177
|
+
return snapshotWorkflowContractRecord({
|
|
3178
|
+
shape: params.step.input,
|
|
3179
|
+
value,
|
|
3180
|
+
path: `Workflow "${params.workflowId}" step "${params.step.id}" input`,
|
|
3181
|
+
valueTypesById: params.valueTypesById
|
|
3182
|
+
});
|
|
3183
|
+
}
|
|
3184
|
+
function snapshotWorkflowStepOutput2(params) {
|
|
3185
|
+
const value = validateWorkflowStepOutput2(params);
|
|
3186
|
+
return snapshotWorkflowContractRecord({
|
|
3187
|
+
shape: params.step.output,
|
|
3188
|
+
value,
|
|
3189
|
+
path: `Workflow "${params.workflowId}" step "${params.step.id}" output`,
|
|
3190
|
+
valueTypesById: params.valueTypesById
|
|
3191
|
+
});
|
|
3192
|
+
}
|
|
3193
|
+
function snapshotWorkflowInterventionInput2(params) {
|
|
3194
|
+
const value = validateWorkflowInterventionInput2(params);
|
|
3195
|
+
return snapshotWorkflowContractRecord({
|
|
3196
|
+
shape: params.intervention.input,
|
|
3197
|
+
value,
|
|
3198
|
+
path: `Workflow "${params.workflowId}" intervention "${params.intervention.id}" input`,
|
|
3199
|
+
valueTypesById: params.valueTypesById
|
|
3200
|
+
});
|
|
3201
|
+
}
|
|
3202
|
+
function snapshotWorkflowInterventionResponse2(params) {
|
|
3203
|
+
const value = validateWorkflowInterventionResponse2(params);
|
|
3204
|
+
return snapshotWorkflowInterventionResponseRecord({
|
|
3205
|
+
response: params.intervention.response,
|
|
3206
|
+
value,
|
|
3207
|
+
path: `Workflow "${params.workflowId}" intervention "${params.intervention.id}" response`,
|
|
3208
|
+
valueTypesById: params.valueTypesById
|
|
3209
|
+
});
|
|
3210
|
+
}
|
|
3211
|
+
function snapshotWorkflowInterventionDefaultResponse2(params) {
|
|
3212
|
+
const value = validateWorkflowInterventionDefaultResponse2(params);
|
|
3213
|
+
return snapshotWorkflowInterventionResponseRecord({
|
|
3214
|
+
response: params.intervention.response,
|
|
3215
|
+
value,
|
|
3216
|
+
path: `Workflow "${params.workflowId}" intervention "${params.intervention.id}" defaultResponse`,
|
|
3217
|
+
valueTypesById: params.valueTypesById
|
|
3218
|
+
});
|
|
3219
|
+
}
|
|
3220
|
+
function snapshotWorkflowActionInput2(params) {
|
|
3221
|
+
const snapshot = {
|
|
3222
|
+
params: snapshotJsonValue(params.params, "Workflow action params")
|
|
3223
|
+
};
|
|
3224
|
+
if (params.subject && params.subject.kind !== "none") {
|
|
3225
|
+
snapshot.subject = snapshotJsonValue(params.subject, "Workflow action subject");
|
|
3226
|
+
}
|
|
3227
|
+
return snapshot;
|
|
3228
|
+
}
|
|
3229
|
+
function snapshotWorkflowContractRecord(params) {
|
|
3230
|
+
const snapshot = {};
|
|
3231
|
+
for (const [fieldId, schema] of Object.entries(params.shape)) {
|
|
3232
|
+
snapshot[fieldId] = snapshotSchemaOrRefValue({
|
|
3233
|
+
schema,
|
|
3234
|
+
value: params.value[fieldId],
|
|
3235
|
+
path: `${params.path}.${fieldId}`,
|
|
3236
|
+
valueTypesById: params.valueTypesById
|
|
3237
|
+
});
|
|
3238
|
+
}
|
|
3239
|
+
return snapshot;
|
|
3240
|
+
}
|
|
3241
|
+
function snapshotWorkflowInterventionResponseRecord(params) {
|
|
3242
|
+
const snapshot = {};
|
|
3243
|
+
for (const [fieldId, value] of Object.entries(params.value)) {
|
|
3244
|
+
if (value === undefined) {
|
|
3245
|
+
continue;
|
|
3246
|
+
}
|
|
3247
|
+
snapshot[fieldId] = snapshotSchemaOrRefValue({
|
|
3248
|
+
schema: interventionResponseFieldSchema(params.response[fieldId]),
|
|
3249
|
+
value,
|
|
3250
|
+
path: `${params.path}.${fieldId}`,
|
|
3251
|
+
valueTypesById: params.valueTypesById
|
|
3252
|
+
});
|
|
3253
|
+
}
|
|
3254
|
+
return snapshot;
|
|
3255
|
+
}
|
|
3256
|
+
function snapshotSchemaOrRefValue(params) {
|
|
3257
|
+
if (isObjectRefSchema2(params.schema)) {
|
|
3258
|
+
if (!isRecord3(params.value)) {
|
|
3259
|
+
throw cannotSerialize(params.path);
|
|
3260
|
+
}
|
|
3261
|
+
return {
|
|
3262
|
+
objectTypeId: String(params.value.objectTypeId),
|
|
3263
|
+
primaryId: String(params.value.primaryId)
|
|
3264
|
+
};
|
|
3265
|
+
}
|
|
3266
|
+
return snapshotSchemaValue({
|
|
3267
|
+
schema: params.schema,
|
|
3268
|
+
value: params.value,
|
|
3269
|
+
path: params.path,
|
|
3270
|
+
valueTypesById: params.valueTypesById
|
|
3271
|
+
});
|
|
3272
|
+
}
|
|
3273
|
+
function snapshotSchemaValue(params) {
|
|
3274
|
+
const { schema, value, path, valueTypesById } = params;
|
|
3275
|
+
if (typeof schema === "string") {
|
|
3276
|
+
if (schema === "date" || schema === "timestamp") {
|
|
3277
|
+
if (value instanceof Date) {
|
|
3278
|
+
return snapshotDate(value, path);
|
|
3279
|
+
}
|
|
3280
|
+
return snapshotJsonValue(value, path);
|
|
3281
|
+
}
|
|
3282
|
+
return snapshotJsonValue(value, path);
|
|
3283
|
+
}
|
|
3284
|
+
if (schema.type === "enum") {
|
|
3285
|
+
return snapshotJsonValue(value, path);
|
|
3286
|
+
}
|
|
3287
|
+
if (schema.type === "array") {
|
|
3288
|
+
if (!Array.isArray(value)) {
|
|
3289
|
+
throw cannotSerialize(path);
|
|
3290
|
+
}
|
|
3291
|
+
return value.map((item, index) => snapshotSchemaValue({
|
|
3292
|
+
schema: schema.items,
|
|
3293
|
+
value: item,
|
|
3294
|
+
path: `${path}[${index}]`,
|
|
3295
|
+
valueTypesById
|
|
3296
|
+
}));
|
|
3297
|
+
}
|
|
3298
|
+
if (schema.type === "map") {
|
|
3299
|
+
if (!isRecord3(value)) {
|
|
3300
|
+
throw cannotSerialize(path);
|
|
3301
|
+
}
|
|
3302
|
+
const snapshot = {};
|
|
3303
|
+
for (const [key, entry] of Object.entries(value)) {
|
|
3304
|
+
snapshot[key] = snapshotSchemaValue({
|
|
3305
|
+
schema: schema.valueSchema,
|
|
3306
|
+
value: entry,
|
|
3307
|
+
path: `${path}.${key}`,
|
|
3308
|
+
valueTypesById
|
|
3309
|
+
});
|
|
3310
|
+
}
|
|
3311
|
+
return snapshot;
|
|
3312
|
+
}
|
|
3313
|
+
if (schema.type === "object") {
|
|
3314
|
+
if (!isRecord3(value)) {
|
|
3315
|
+
throw cannotSerialize(path);
|
|
3316
|
+
}
|
|
3317
|
+
const snapshot = {};
|
|
3318
|
+
for (const [fieldId, field] of Object.entries(schema.properties)) {
|
|
3319
|
+
const fieldValue = value[fieldId];
|
|
3320
|
+
if (fieldValue === undefined) {
|
|
3321
|
+
continue;
|
|
3322
|
+
}
|
|
3323
|
+
if (fieldValue === null) {
|
|
3324
|
+
snapshot[fieldId] = null;
|
|
3325
|
+
continue;
|
|
3326
|
+
}
|
|
3327
|
+
snapshot[fieldId] = snapshotSchemaValue({
|
|
3328
|
+
schema: field.schema,
|
|
3329
|
+
value: fieldValue,
|
|
3330
|
+
path: `${path}.${fieldId}`,
|
|
3331
|
+
valueTypesById
|
|
3332
|
+
});
|
|
3333
|
+
}
|
|
3334
|
+
return snapshot;
|
|
3335
|
+
}
|
|
3336
|
+
if (schema.type === "valueTypeRef") {
|
|
3337
|
+
const valueType = valueTypesById.get(schema.valueTypeId);
|
|
3338
|
+
if (!valueType) {
|
|
3339
|
+
throw new WorkflowValidationError2(`[Sixb] Unknown valueTypeRef '${schema.valueTypeId}' at ${path}`);
|
|
3340
|
+
}
|
|
3341
|
+
return snapshotSchemaValue({
|
|
3342
|
+
schema: valueType.schema,
|
|
3343
|
+
value,
|
|
3344
|
+
path,
|
|
3345
|
+
valueTypesById
|
|
3346
|
+
});
|
|
3347
|
+
}
|
|
3348
|
+
return snapshotJsonValue(value, path);
|
|
3349
|
+
}
|
|
3350
|
+
function snapshotJsonValue(value, path) {
|
|
3351
|
+
if (value === null || typeof value === "string" || typeof value === "boolean") {
|
|
3352
|
+
return value;
|
|
3353
|
+
}
|
|
3354
|
+
if (typeof value === "number") {
|
|
3355
|
+
if (!Number.isFinite(value)) {
|
|
3356
|
+
throw cannotSerialize(path);
|
|
3357
|
+
}
|
|
3358
|
+
return value;
|
|
3359
|
+
}
|
|
3360
|
+
if (value instanceof Date) {
|
|
3361
|
+
return snapshotDate(value, path);
|
|
3362
|
+
}
|
|
3363
|
+
if (Array.isArray(value)) {
|
|
3364
|
+
return value.map((item, index) => snapshotJsonValue(item, `${path}[${index}]`));
|
|
3365
|
+
}
|
|
3366
|
+
if (isPlainRecord(value)) {
|
|
3367
|
+
const snapshot = {};
|
|
3368
|
+
for (const [key, entry] of Object.entries(value)) {
|
|
3369
|
+
snapshot[key] = snapshotJsonValue(entry, `${path}.${key}`);
|
|
3370
|
+
}
|
|
3371
|
+
return snapshot;
|
|
3372
|
+
}
|
|
3373
|
+
throw cannotSerialize(path);
|
|
3374
|
+
}
|
|
3375
|
+
function snapshotDate(value, path) {
|
|
3376
|
+
if (Number.isNaN(value.getTime())) {
|
|
3377
|
+
throw cannotSerialize(path);
|
|
3378
|
+
}
|
|
3379
|
+
return value.toISOString();
|
|
3380
|
+
}
|
|
3381
|
+
function cannotSerialize(path) {
|
|
3382
|
+
return new WorkflowValidationError2(`[Sixb] ${path} cannot be serialized as workflow IO`);
|
|
3383
|
+
}
|
|
3384
|
+
function isRecord3(value) {
|
|
3385
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
3386
|
+
}
|
|
3387
|
+
|
|
3388
|
+
// src/workflows/run-dispatch.ts
|
|
3389
|
+
class WorkflowRunDispatcher2 {
|
|
3390
|
+
dependencies;
|
|
3391
|
+
constructor(dependencies) {
|
|
3392
|
+
this.dependencies = dependencies;
|
|
3393
|
+
}
|
|
3394
|
+
async dispatch(input) {
|
|
3395
|
+
assertAutomaticDispatchInput(input);
|
|
3396
|
+
const workflow = this.dependencies.definitions.workflows.getById(input.workflowId);
|
|
3397
|
+
if (!workflow) {
|
|
3398
|
+
throw new WorkflowValidationError2(`[Sixb] Unknown workflow '${input.workflowId}'`);
|
|
3399
|
+
}
|
|
3400
|
+
const result = await dispatchWorkflowRun({
|
|
3401
|
+
errorReporterHost: this.dependencies,
|
|
3402
|
+
projectId: this.dependencies.id,
|
|
3403
|
+
workflow,
|
|
3404
|
+
valueTypesById: this.dependencies.definitions.ontology.getValueTypesById(),
|
|
3405
|
+
storage: this.dependencies.storage,
|
|
3406
|
+
queue: this.dependencies.queues.workflows,
|
|
3407
|
+
events: this.dependencies.events,
|
|
3408
|
+
runId: input.runId,
|
|
3409
|
+
input: input.input,
|
|
3410
|
+
source: {
|
|
3411
|
+
type: "schedule",
|
|
3412
|
+
scheduleId: input.scheduleId,
|
|
3413
|
+
eventId: input.source.eventId,
|
|
3414
|
+
principal: SYSTEM_PRINCIPAL2
|
|
3415
|
+
},
|
|
3416
|
+
metadata: input.metadata,
|
|
3417
|
+
queueJobId: input.runId,
|
|
3418
|
+
createExecution: async (executionId, runId) => createPrimitiveExecutionRecord({
|
|
3419
|
+
id: executionId,
|
|
3420
|
+
primitive: { kind: "workflow", id: workflow.id, runId },
|
|
3421
|
+
origin: {
|
|
3422
|
+
type: "automatic",
|
|
3423
|
+
projectId: this.dependencies.id,
|
|
3424
|
+
source: input.source,
|
|
3425
|
+
correlationId: input.correlationId
|
|
3426
|
+
}
|
|
3427
|
+
})
|
|
3428
|
+
});
|
|
3429
|
+
if (!result.created) {
|
|
3430
|
+
await assertAutomaticExecutionIdentity(this.dependencies, input, result.runId);
|
|
3431
|
+
}
|
|
3432
|
+
return result;
|
|
3433
|
+
}
|
|
3434
|
+
}
|
|
3435
|
+
async function dispatchWorkflowRun(input) {
|
|
3436
|
+
const request = prepareWorkflowRun(input);
|
|
3437
|
+
const persisted = await persistWorkflowRun(input, request);
|
|
3438
|
+
if (!persisted.created)
|
|
3439
|
+
return existingWorkflowRunResult(persisted.run);
|
|
3440
|
+
return publishWorkflowRun(input, persisted);
|
|
3441
|
+
}
|
|
3442
|
+
function prepareWorkflowRun(input) {
|
|
3443
|
+
const value = input.input ?? {};
|
|
3444
|
+
return {
|
|
3445
|
+
runId: resolveWorkflowRunId(input.runId),
|
|
3446
|
+
snapshot: snapshotWorkflowInput2({
|
|
3447
|
+
workflow: input.workflow,
|
|
3448
|
+
value,
|
|
3449
|
+
valueTypesById: input.valueTypesById
|
|
3450
|
+
})
|
|
3451
|
+
};
|
|
3452
|
+
}
|
|
3453
|
+
async function persistWorkflowRun(input, request) {
|
|
3454
|
+
const workflowRuns = input.storage.workflowRuns;
|
|
3455
|
+
if (!workflowRuns) {
|
|
3456
|
+
throw new WorkflowValidationError2("[Sixb] Workflow run storage is not configured.");
|
|
3457
|
+
}
|
|
3458
|
+
const existing = await workflowRuns.getById({
|
|
3459
|
+
projectId: input.projectId,
|
|
3460
|
+
id: request.runId
|
|
3461
|
+
});
|
|
3462
|
+
if (existing) {
|
|
3463
|
+
assertExistingWorkflowRun(existing, input.workflow.id, request.snapshot);
|
|
3464
|
+
return { run: existing, created: false };
|
|
3465
|
+
}
|
|
3466
|
+
const execution = await input.createExecution(`exec_${randomUUID6()}`, request.runId);
|
|
3467
|
+
const queuedAt = new Date;
|
|
3468
|
+
try {
|
|
3469
|
+
return await input.storage.transaction(async (tx) => {
|
|
3470
|
+
const raced = await tx.workflowRuns?.getById({
|
|
3471
|
+
projectId: input.projectId,
|
|
3472
|
+
id: request.runId
|
|
3473
|
+
});
|
|
3474
|
+
if (raced) {
|
|
3475
|
+
assertExistingWorkflowRun(raced, input.workflow.id, request.snapshot);
|
|
3476
|
+
return { run: raced, created: false };
|
|
3477
|
+
}
|
|
3478
|
+
if (!tx.workflowRuns) {
|
|
3479
|
+
throw new WorkflowValidationError2("[Sixb] Workflow run storage is not configured.");
|
|
3480
|
+
}
|
|
3481
|
+
await tx.executions.create(execution);
|
|
3482
|
+
const run = await tx.workflowRuns.queue({
|
|
3483
|
+
projectId: input.projectId,
|
|
3484
|
+
id: request.runId,
|
|
3485
|
+
executionId: execution.id,
|
|
3486
|
+
workflowId: input.workflow.id,
|
|
3487
|
+
input: request.snapshot,
|
|
3488
|
+
queuedAt
|
|
3489
|
+
});
|
|
3490
|
+
return { run, execution, queuedAt, created: true };
|
|
3491
|
+
}, { isolation: "serializable" });
|
|
3492
|
+
} catch (error) {
|
|
3493
|
+
if (!(error instanceof WorkflowRunError2))
|
|
3494
|
+
throw error;
|
|
3495
|
+
const raced = await workflowRuns.getById({
|
|
3496
|
+
projectId: input.projectId,
|
|
3497
|
+
id: request.runId
|
|
3498
|
+
});
|
|
3499
|
+
if (!raced)
|
|
3500
|
+
throw error;
|
|
3501
|
+
assertExistingWorkflowRun(raced, input.workflow.id, request.snapshot);
|
|
3502
|
+
return { run: raced, created: false };
|
|
3503
|
+
}
|
|
3504
|
+
}
|
|
3505
|
+
async function publishWorkflowRun(input, persisted) {
|
|
3506
|
+
let job;
|
|
3507
|
+
try {
|
|
3508
|
+
const jobs = await input.queue.enqueue({
|
|
3509
|
+
projectId: input.projectId,
|
|
3510
|
+
jobs: [
|
|
3511
|
+
{
|
|
3512
|
+
...input.queueJobId === undefined ? {} : { id: input.queueJobId },
|
|
3513
|
+
type: "workflow.run.requested",
|
|
3514
|
+
payload: { runId: persisted.run.id },
|
|
3515
|
+
...input.metadata === undefined ? {} : { metadata: input.metadata }
|
|
3516
|
+
}
|
|
3517
|
+
]
|
|
3518
|
+
});
|
|
3519
|
+
job = jobs[0];
|
|
3520
|
+
} catch (error) {
|
|
3521
|
+
await failWorkflowRunPublication(input, persisted.run, error);
|
|
3522
|
+
throw error;
|
|
3523
|
+
}
|
|
3524
|
+
await input.events.emit({
|
|
3525
|
+
events: [
|
|
3526
|
+
{
|
|
3527
|
+
type: "workflow.run.queued",
|
|
3528
|
+
payload: {
|
|
3529
|
+
workflowId: persisted.run.workflowId,
|
|
3530
|
+
runId: persisted.run.id,
|
|
3531
|
+
queuedAt: persisted.queuedAt.toISOString(),
|
|
3532
|
+
...job?.id ? { jobId: job.id } : {},
|
|
3533
|
+
...input.source === undefined ? {} : { source: input.source }
|
|
3534
|
+
}
|
|
3535
|
+
}
|
|
3536
|
+
],
|
|
3537
|
+
correlationId: persisted.execution.correlationId
|
|
3538
|
+
}, { source: "Sixb" });
|
|
3539
|
+
return {
|
|
3540
|
+
workflowId: persisted.run.workflowId,
|
|
3541
|
+
runId: persisted.run.id,
|
|
3542
|
+
queuedAt: persisted.queuedAt.toISOString(),
|
|
3543
|
+
jobId: job?.id,
|
|
3544
|
+
created: true
|
|
3545
|
+
};
|
|
3546
|
+
}
|
|
3547
|
+
async function failWorkflowRunPublication(input, run, error) {
|
|
3548
|
+
const workflowRuns = input.storage.workflowRuns;
|
|
3549
|
+
if (!workflowRuns) {
|
|
3550
|
+
throw new WorkflowValidationError2("[Sixb] Workflow run storage is not configured.");
|
|
3551
|
+
}
|
|
3552
|
+
const failure = captureSixbFailure2(error, {
|
|
3553
|
+
allowedCodes: WORKFLOW_RUN_FAILURE_CODES2,
|
|
3554
|
+
defaultCode: "internal.unexpected",
|
|
3555
|
+
details: { workflowId: run.workflowId, runId: run.id }
|
|
3556
|
+
});
|
|
3557
|
+
await workflowRuns.finish({
|
|
3558
|
+
projectId: input.projectId,
|
|
3559
|
+
id: run.id,
|
|
3560
|
+
status: "failed",
|
|
3561
|
+
error: failure
|
|
3562
|
+
});
|
|
3563
|
+
reportRunFailure2(input.errorReporterHost, error, {
|
|
3564
|
+
projectId: input.projectId,
|
|
3565
|
+
runKind: "workflow",
|
|
3566
|
+
run: { runId: run.id, workflowId: run.workflowId },
|
|
3567
|
+
failure
|
|
3568
|
+
});
|
|
3569
|
+
}
|
|
3570
|
+
function resolveWorkflowRunId(runId) {
|
|
3571
|
+
if (runId === undefined)
|
|
3572
|
+
return `run_${randomUUID6()}`;
|
|
3573
|
+
if (!runId.trim()) {
|
|
3574
|
+
throw new WorkflowValidationError2("[Sixb] Workflow run id must not be empty");
|
|
3575
|
+
}
|
|
3576
|
+
return runId;
|
|
3577
|
+
}
|
|
3578
|
+
function assertExistingWorkflowRun(existing, workflowId, input) {
|
|
3579
|
+
if (existing.workflowId !== workflowId || !isDeepStrictEqual(existing.input, input)) {
|
|
3580
|
+
throw new WorkflowValidationError2(`[Sixb] Workflow run '${existing.id}' already exists with a different request payload.`);
|
|
3581
|
+
}
|
|
3582
|
+
}
|
|
3583
|
+
function existingWorkflowRunResult(existing) {
|
|
3584
|
+
return {
|
|
3585
|
+
workflowId: existing.workflowId,
|
|
3586
|
+
runId: existing.id,
|
|
3587
|
+
queuedAt: (existing.queuedAt ?? existing.startedAt).toISOString(),
|
|
3588
|
+
created: false
|
|
3589
|
+
};
|
|
3590
|
+
}
|
|
3591
|
+
function assertAutomaticDispatchInput(input) {
|
|
3592
|
+
assertNonBlank(input.workflowId, "Workflow id");
|
|
3593
|
+
assertNonBlank(input.runId, "Workflow run id");
|
|
3594
|
+
assertNonBlank(input.scheduleId, "Workflow schedule id");
|
|
3595
|
+
assertNonBlank(input.source.eventId, "Workflow source event id");
|
|
3596
|
+
assertNonBlank(input.correlationId, "Workflow correlation id");
|
|
3597
|
+
}
|
|
3598
|
+
async function assertAutomaticExecutionIdentity(dependencies, input, runId) {
|
|
3599
|
+
const run = await dependencies.storage.workflowRuns?.getById({
|
|
3600
|
+
projectId: dependencies.id,
|
|
3601
|
+
id: runId
|
|
3602
|
+
});
|
|
3603
|
+
const execution = run ? await dependencies.storage.executions.getById({
|
|
3604
|
+
projectId: dependencies.id,
|
|
3605
|
+
id: run.executionId
|
|
3606
|
+
}) : null;
|
|
3607
|
+
if (!execution || execution.source.type !== input.source.type || execution.source.eventId !== input.source.eventId || execution.correlationId !== input.correlationId || execution.requestedBy !== undefined) {
|
|
3608
|
+
throw new WorkflowValidationError2(`[Sixb] Workflow run '${runId}' already exists with different automatic provenance.`);
|
|
3609
|
+
}
|
|
3610
|
+
}
|
|
3611
|
+
function assertNonBlank(value, label) {
|
|
3612
|
+
if (!value.trim())
|
|
3613
|
+
throw new WorkflowValidationError2(`[Sixb] ${label} must not be empty.`);
|
|
3614
|
+
}
|
|
3615
|
+
|
|
3616
|
+
// src/workflows/request.ts
|
|
3617
|
+
async function requestWorkflowRun2(runtime, execution, workflow, options = {}) {
|
|
3618
|
+
resolveExecutionScopeAuthorization(runtime.projectId, {
|
|
3619
|
+
execution,
|
|
3620
|
+
authorization: runtime.runtimeAuthorization
|
|
3621
|
+
});
|
|
3622
|
+
assertAuthorized2(runtime, { kind: "workflow.run", workflowId: workflow.id });
|
|
3623
|
+
return dispatchWorkflowRun({
|
|
3624
|
+
errorReporterHost: runtime,
|
|
3625
|
+
projectId: runtime.projectId,
|
|
3626
|
+
workflow,
|
|
3627
|
+
valueTypesById: runtime.ontology.getValueTypesById(),
|
|
3628
|
+
storage: runtime.storage,
|
|
3629
|
+
queue: runtime.queues.workflows,
|
|
3630
|
+
events: runtime.events,
|
|
3631
|
+
runId: options.runId,
|
|
3632
|
+
input: options.input,
|
|
3633
|
+
source: options.source,
|
|
3634
|
+
createExecution: async (executionId, runId) => {
|
|
3635
|
+
const caller = await ensureExecutionRecord2(runtime.storage.executions, executionRecordInputFromRuntime({
|
|
3636
|
+
execution,
|
|
3637
|
+
runtimeAuthorization: runtime.runtimeAuthorization
|
|
3638
|
+
}));
|
|
3639
|
+
return createPrimitiveExecutionRecord({
|
|
3640
|
+
id: executionId,
|
|
3641
|
+
primitive: { kind: "workflow", id: workflow.id, runId },
|
|
3642
|
+
origin: { type: "execution", parent: caller }
|
|
3643
|
+
});
|
|
3644
|
+
}
|
|
3645
|
+
});
|
|
3646
|
+
}
|
|
3647
|
+
|
|
3648
|
+
// src/workflows/execution.ts
|
|
3649
|
+
function createWorkflowsRuntime(runtime, execution, source) {
|
|
3650
|
+
const authority = resolveRuntimeAuthorizationForProject(runtime);
|
|
3651
|
+
const allowed = (workflowId) => isRuntimeAllowed2(runtime, { kind: "workflow.run", workflowId });
|
|
3652
|
+
const canAccessHistory = (workflowId) => {
|
|
3653
|
+
switch (authority.type) {
|
|
3654
|
+
case "denied":
|
|
3655
|
+
case "delegated":
|
|
3656
|
+
return false;
|
|
3657
|
+
case "unrestricted":
|
|
3658
|
+
return true;
|
|
3659
|
+
case "principal":
|
|
3660
|
+
return allowed(workflowId) && source.getById(workflowId) !== null;
|
|
3661
|
+
}
|
|
3662
|
+
};
|
|
3663
|
+
const visibleIds = () => source.list().filter((workflow) => allowed(workflow.id)).map((workflow) => workflow.id);
|
|
3664
|
+
const historyFilterIds = () => authority.type === "unrestricted" ? undefined : authority.type === "principal" ? visibleIds() : [];
|
|
3665
|
+
const getVisibleRunRecord = async (runId) => {
|
|
3666
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
3667
|
+
return null;
|
|
3668
|
+
const run = await runtime.storage.workflowRuns?.getById({
|
|
3669
|
+
projectId: runtime.projectId,
|
|
3670
|
+
id: runId
|
|
3671
|
+
}) ?? null;
|
|
3672
|
+
if (!run || !canAccessHistory(run.workflowId))
|
|
3673
|
+
return null;
|
|
3674
|
+
return authority.type === "unrestricted" || canViewWorkflowRun2(authority.context, run) ? run : null;
|
|
3675
|
+
};
|
|
3676
|
+
const getRun = async (runId) => {
|
|
3677
|
+
const run = await getVisibleRunRecord(runId);
|
|
3678
|
+
return run ? attachRequestedBy(runtime, run) : null;
|
|
3679
|
+
};
|
|
3680
|
+
const listNodes = async (runId, input = {}) => {
|
|
3681
|
+
const storage = runtime.storage.workflowRuns;
|
|
3682
|
+
if (!storage || !await getVisibleRunRecord(runId))
|
|
3683
|
+
return null;
|
|
3684
|
+
const result = await storage.nodes.list({
|
|
3685
|
+
...input,
|
|
3686
|
+
workflowRunId: runId,
|
|
3687
|
+
projectId: runtime.projectId
|
|
3688
|
+
});
|
|
3689
|
+
return {
|
|
3690
|
+
...result,
|
|
3691
|
+
nodes: await attachWorkflowNodeViews(runtime, storage, result.nodes)
|
|
3692
|
+
};
|
|
3693
|
+
};
|
|
3694
|
+
return {
|
|
3695
|
+
list: () => authority.type === "denied" || authority.type === "delegated" ? [] : source.list().filter((workflow) => allowed(workflow.id)),
|
|
3696
|
+
getById: (workflowId) => {
|
|
3697
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
3698
|
+
return null;
|
|
3699
|
+
const workflow = source.getById(workflowId);
|
|
3700
|
+
return workflow && allowed(workflowId) ? workflow : null;
|
|
3701
|
+
},
|
|
3702
|
+
request: (workflow, options) => requestWorkflowRun2(runtime, execution, workflow, options),
|
|
3703
|
+
requestById: async (input) => {
|
|
3704
|
+
assertAuthorized2(runtime, { kind: "workflow.run", workflowId: input.workflowId });
|
|
3705
|
+
const workflow = source.getById(input.workflowId);
|
|
3706
|
+
if (!workflow) {
|
|
3707
|
+
throw new WorkflowValidationError2(`[Sixb] Unknown workflow '${input.workflowId}'`);
|
|
3708
|
+
}
|
|
3709
|
+
return requestWorkflowRun2(runtime, execution, workflow, input);
|
|
3710
|
+
},
|
|
3711
|
+
runs: {
|
|
3712
|
+
getById: getRun,
|
|
3713
|
+
list: async (input = {}) => {
|
|
3714
|
+
if (authority.type === "denied" || authority.type === "delegated") {
|
|
3715
|
+
return { runs: [], hasMore: false, total: 0 };
|
|
3716
|
+
}
|
|
3717
|
+
const storage = runtime.storage.workflowRuns;
|
|
3718
|
+
if (!storage)
|
|
3719
|
+
return { runs: [], hasMore: false, total: 0 };
|
|
3720
|
+
const result = await storage.list({
|
|
3721
|
+
...input,
|
|
3722
|
+
workflowIds: historyFilterIds(),
|
|
3723
|
+
projectId: runtime.projectId
|
|
3724
|
+
});
|
|
3725
|
+
return {
|
|
3726
|
+
...result,
|
|
3727
|
+
runs: await Promise.all(result.runs.map((run) => attachRequestedBy(runtime, run)))
|
|
3728
|
+
};
|
|
3729
|
+
},
|
|
3730
|
+
listLatest: async (workflowIds) => {
|
|
3731
|
+
if (authority.type === "denied" || authority.type === "delegated") {
|
|
3732
|
+
return { runs: [] };
|
|
3733
|
+
}
|
|
3734
|
+
const storage = runtime.storage.workflowRuns;
|
|
3735
|
+
if (!storage || workflowIds.length === 0)
|
|
3736
|
+
return { runs: [] };
|
|
3737
|
+
const allowedIds = workflowIds.filter(canAccessHistory);
|
|
3738
|
+
if (allowedIds.length === 0)
|
|
3739
|
+
return { runs: [] };
|
|
3740
|
+
const result = await storage.listLatestByWorkflowIds({
|
|
3741
|
+
projectId: runtime.projectId,
|
|
3742
|
+
workflowIds: allowedIds
|
|
3743
|
+
});
|
|
3744
|
+
return {
|
|
3745
|
+
runs: await Promise.all(result.runs.map((run) => attachRequestedBy(runtime, run)))
|
|
3746
|
+
};
|
|
3747
|
+
},
|
|
3748
|
+
listNodes
|
|
3749
|
+
},
|
|
3750
|
+
interventions: {
|
|
3751
|
+
getById: async (interventionId) => {
|
|
3752
|
+
if (authority.type === "denied" || authority.type === "delegated")
|
|
3753
|
+
return null;
|
|
3754
|
+
const intervention = await runtime.storage.workflowInterventions?.getById({
|
|
3755
|
+
projectId: runtime.projectId,
|
|
3756
|
+
id: interventionId
|
|
3757
|
+
}) ?? null;
|
|
3758
|
+
if (!intervention || !canAccessHistory(intervention.workflowId))
|
|
3759
|
+
return null;
|
|
3760
|
+
return authority.type === "unrestricted" || canViewWorkflowIntervention2(authority.context, intervention) ? intervention : null;
|
|
3761
|
+
},
|
|
3762
|
+
list: (input = {}) => {
|
|
3763
|
+
if (authority.type === "denied" || authority.type === "delegated") {
|
|
3764
|
+
return Promise.resolve({ interventions: [], hasMore: false, total: 0 });
|
|
3765
|
+
}
|
|
3766
|
+
const storage = runtime.storage.workflowInterventions;
|
|
3767
|
+
if (!storage)
|
|
3768
|
+
return Promise.resolve({ interventions: [], hasMore: false, total: 0 });
|
|
3769
|
+
return storage.list({
|
|
3770
|
+
...input,
|
|
3771
|
+
workflowIds: historyFilterIds(),
|
|
3772
|
+
projectId: runtime.projectId
|
|
3773
|
+
});
|
|
3774
|
+
}
|
|
3775
|
+
}
|
|
3776
|
+
};
|
|
3777
|
+
}
|
|
3778
|
+
async function attachWorkflowNodeViews(runtime, storage, nodes) {
|
|
3779
|
+
const executions = await Promise.all(nodes.map((node) => node.nodeType === "agent" ? storage.agentNodes.getByNodeRunId({
|
|
3780
|
+
projectId: runtime.projectId,
|
|
3781
|
+
nodeRunId: node.id
|
|
3782
|
+
}) : null));
|
|
3783
|
+
const agentExecutions = executions.filter((execution) => execution !== null);
|
|
3784
|
+
if (agentExecutions.length === 0)
|
|
3785
|
+
return nodes;
|
|
3786
|
+
const executionIds = agentExecutions.map((execution) => execution.executionId);
|
|
3787
|
+
const [usages, costs] = await Promise.all([
|
|
3788
|
+
resolveExecutionUsage({
|
|
3789
|
+
storage: runtime.storage.aiUsage,
|
|
3790
|
+
projectId: runtime.projectId,
|
|
3791
|
+
executionIds
|
|
3792
|
+
}),
|
|
3793
|
+
resolveExecutionCosts({
|
|
3794
|
+
storage: runtime.storage.aiCosts,
|
|
3795
|
+
projectId: runtime.projectId,
|
|
3796
|
+
executionIds
|
|
3797
|
+
})
|
|
3798
|
+
]);
|
|
3799
|
+
const accountingByExecutionId = new Map(agentExecutions.map((execution, index) => [
|
|
3800
|
+
execution.executionId,
|
|
3801
|
+
{ usage: usages[index], cost: costs[index] }
|
|
3802
|
+
]));
|
|
3803
|
+
return nodes.map((node, index) => {
|
|
3804
|
+
const execution = executions[index];
|
|
3805
|
+
if (!execution)
|
|
3806
|
+
return node;
|
|
3807
|
+
const accounting = accountingByExecutionId.get(execution.executionId);
|
|
3808
|
+
return {
|
|
3809
|
+
...node,
|
|
3810
|
+
agentExecution: toWorkflowAgentNodeRunView(execution, accounting?.usage, accounting?.usage === undefined ? undefined : accounting.cost)
|
|
3811
|
+
};
|
|
3812
|
+
});
|
|
3813
|
+
}
|
|
3814
|
+
function toWorkflowAgentNodeRunView(execution, usage, cost) {
|
|
3815
|
+
return {
|
|
3816
|
+
projectId: execution.projectId,
|
|
3817
|
+
nodeRunId: execution.nodeRunId,
|
|
3818
|
+
executionId: execution.executionId,
|
|
3819
|
+
status: execution.status,
|
|
3820
|
+
prompt: execution.prompt,
|
|
3821
|
+
modelId: execution.modelId,
|
|
3822
|
+
finishReason: execution.finishReason,
|
|
3823
|
+
trace: execution.trace,
|
|
3824
|
+
diagnostics: execution.diagnostics,
|
|
3825
|
+
error: execution.error,
|
|
3826
|
+
attempt: execution.attempt,
|
|
3827
|
+
createdAt: execution.createdAt,
|
|
3828
|
+
startedAt: execution.startedAt,
|
|
3829
|
+
completedAt: execution.completedAt,
|
|
3830
|
+
...usage === undefined ? {} : { usage },
|
|
3831
|
+
...usage === undefined || cost === undefined ? {} : { cost }
|
|
3832
|
+
};
|
|
3833
|
+
}
|
|
3834
|
+
async function attachRequestedBy(runtime, run) {
|
|
3835
|
+
const execution = await runtime.storage.executions.getById({
|
|
3836
|
+
projectId: runtime.projectId,
|
|
3837
|
+
id: run.executionId
|
|
3838
|
+
});
|
|
3839
|
+
if (!execution) {
|
|
3840
|
+
throw new Error(`[Sixb] Workflow run '${run.id}' references missing execution '${run.executionId}'.`);
|
|
3841
|
+
}
|
|
3842
|
+
return {
|
|
3843
|
+
...run,
|
|
3844
|
+
...execution.requestedBy === undefined ? {} : { requestedBy: structuredClone(execution.requestedBy) }
|
|
3845
|
+
};
|
|
3846
|
+
}
|
|
3847
|
+
|
|
3848
|
+
// src/runtime/sixb.ts
|
|
3849
|
+
var boundSixbInstances = new WeakSet;
|
|
3850
|
+
function createBoundSixb(runtime, dependencies, execution) {
|
|
3851
|
+
resolveExecutionScopeAuthorization(runtime.projectId, {
|
|
3852
|
+
execution,
|
|
3853
|
+
authorization: runtime.runtimeAuthorization
|
|
3854
|
+
});
|
|
3855
|
+
assertAuthorizedObjectReaderBinding({
|
|
3856
|
+
reader: runtime.objectReader,
|
|
3857
|
+
scope: { execution, authorization: runtime.runtimeAuthorization }
|
|
3858
|
+
});
|
|
3859
|
+
const sixb = {
|
|
3860
|
+
execution,
|
|
3861
|
+
...createExecutionFacades(runtime, execution, dependencies)
|
|
3862
|
+
};
|
|
3863
|
+
shareOntologyMutationRuntime2(runtime, sixb);
|
|
3864
|
+
if (dependencies.connectorConnections) {
|
|
3865
|
+
registerConnectorConnectionsRuntime(sixb, createConnectorConnectionsRuntime(runtime, execution, dependencies.connectorConnections));
|
|
3866
|
+
}
|
|
3867
|
+
boundSixbInstances.add(sixb);
|
|
3868
|
+
return sixb;
|
|
3869
|
+
}
|
|
3870
|
+
function isBoundSixb(value) {
|
|
3871
|
+
return typeof value === "object" && value !== null && boundSixbInstances.has(value);
|
|
3872
|
+
}
|
|
3873
|
+
function createExecutionFacades(runtime, execution, dependencies) {
|
|
3874
|
+
return {
|
|
3875
|
+
objects: createObjectsRuntime(runtime, execution),
|
|
3876
|
+
actions: createActionsRuntime(runtime, execution),
|
|
3877
|
+
datasets: createDatasetsRuntime(runtime, execution, dependencies.definitions.datasets, dependencies.lakeStorage, dependencies.blobStorage),
|
|
3878
|
+
workflows: createWorkflowsRuntime(runtime, execution, dependencies.definitions.workflows),
|
|
3879
|
+
syncs: createSyncsRuntime(runtime, execution, dependencies.definitions.syncs),
|
|
3880
|
+
pipelines: createPipelinesRuntime(runtime, execution, dependencies.definitions.pipelines),
|
|
3881
|
+
projections: createProjectionsRuntime(runtime, dependencies.definitions.projections),
|
|
3882
|
+
rules: createRulesRuntime(runtime, dependencies.definitions.rules),
|
|
3883
|
+
agent: createAgentRuntime(runtime, execution, dependencies.definitions.models),
|
|
3884
|
+
models: createModelsRuntime(runtime, execution, dependencies.definitions.models),
|
|
3885
|
+
aiUsage: createAiUsageRuntime(runtime, dependencies.definitions.security),
|
|
3886
|
+
events: createEventsRuntime(runtime),
|
|
3887
|
+
logs: createLogsRuntime(runtime, dependencies.logging),
|
|
3888
|
+
schedules: createSchedulesRuntime(runtime, dependencies.definitions.schedules),
|
|
3889
|
+
shares: createSharesRuntime(runtime, execution, dependencies.definitions.shares),
|
|
3890
|
+
connector: createConnectorRuntime(runtime, execution, dependencies.connectorService),
|
|
3891
|
+
blobs: createBlobsRuntime(runtime, execution, dependencies.blobStorage)
|
|
3892
|
+
};
|
|
3893
|
+
}
|
|
3894
|
+
// src/execution/agent.ts
|
|
3895
|
+
function canInheritAgentRequestAuthorization2(authorization) {
|
|
3896
|
+
const ref = getAuthorizationRef(authorization);
|
|
3897
|
+
return ref.type === "disabled" || ref.type === "principal" && ref.principal.type === "user" && ref.credential !== undefined;
|
|
3898
|
+
}
|
|
3899
|
+
function createAgentExecutionRecord2(input) {
|
|
3900
|
+
assertAgentPrincipal(input.actorId, input.principal);
|
|
3901
|
+
return {
|
|
3902
|
+
id: input.id,
|
|
3903
|
+
projectId: input.parent.projectId,
|
|
3904
|
+
requesterGroupIds: [...input.parent.requesterGroupIds],
|
|
3905
|
+
...input.parent.requestedBy === undefined ? {} : { requestedBy: structuredClone(input.parent.requestedBy) },
|
|
3906
|
+
executor: { type: "agent", runId: input.runId },
|
|
3907
|
+
source: { type: "execution", executionId: input.parent.id },
|
|
3908
|
+
correlationId: input.parent.correlationId,
|
|
3909
|
+
authorizationRef: {
|
|
3910
|
+
type: "principal",
|
|
3911
|
+
principal: structuredClone(input.principal)
|
|
3912
|
+
}
|
|
3913
|
+
};
|
|
3914
|
+
}
|
|
3915
|
+
function createInheritedAgentExecutionRecord2(input) {
|
|
3916
|
+
const authority = input.parent.authorizationRef;
|
|
3917
|
+
if (authority.type !== "disabled" && !(authority.type === "principal" && authority.principal.type === "user" && authority.credential !== undefined)) {
|
|
3918
|
+
throw new ExecutionStorageError2("invalid_input", `[Sixb] Agent run '${input.runId}' requires inheritable user or auth-disabled authority.`);
|
|
3919
|
+
}
|
|
3920
|
+
return {
|
|
3921
|
+
id: input.id,
|
|
3922
|
+
projectId: input.parent.projectId,
|
|
3923
|
+
requesterGroupIds: [...input.parent.requesterGroupIds],
|
|
3924
|
+
...input.parent.requestedBy === undefined ? {} : { requestedBy: structuredClone(input.parent.requestedBy) },
|
|
3925
|
+
executor: { type: "agent", runId: input.runId },
|
|
3926
|
+
source: { type: "execution", executionId: input.parent.id },
|
|
3927
|
+
correlationId: input.parent.correlationId,
|
|
3928
|
+
authorizationRef: structuredClone(authority)
|
|
3929
|
+
};
|
|
3930
|
+
}
|
|
3931
|
+
function bindDurableAgentExecution2(host, input) {
|
|
3932
|
+
const scope = restoreAgentExecutionScope2(input);
|
|
3933
|
+
const sixb = host.withScope(scope);
|
|
3934
|
+
if (!isBoundSixb(sixb)) {
|
|
3935
|
+
throw new Error("[Sixb] Agent execution host returned an invalid bound SDK.");
|
|
3936
|
+
}
|
|
3937
|
+
return sixb;
|
|
3938
|
+
}
|
|
3939
|
+
function restoreAgentExecutionScope2(input) {
|
|
3940
|
+
assertAgentExecutionRecord2(input);
|
|
3941
|
+
const context = Object.freeze({
|
|
3942
|
+
id: input.execution.id,
|
|
3943
|
+
projectId: input.execution.projectId,
|
|
3944
|
+
...input.execution.requestedBy === undefined ? {} : { requestedBy: Object.freeze(structuredClone(input.execution.requestedBy)) },
|
|
3945
|
+
executor: Object.freeze({
|
|
3946
|
+
type: "agent",
|
|
3947
|
+
...input.actorId === undefined ? {} : { actorId: input.actorId },
|
|
3948
|
+
runId: input.runId
|
|
3949
|
+
}),
|
|
3950
|
+
source: Object.freeze(structuredClone(input.execution.source)),
|
|
3951
|
+
correlationId: input.execution.correlationId
|
|
3952
|
+
});
|
|
3953
|
+
return Object.freeze({
|
|
3954
|
+
execution: context,
|
|
3955
|
+
authorization: createAgentRuntimeAuthorization({
|
|
3956
|
+
execution: context,
|
|
3957
|
+
authority: input.authorization.type === "principal" ? {
|
|
3958
|
+
type: "principal",
|
|
3959
|
+
context: input.authorization.context,
|
|
3960
|
+
...input.execution.authorizationRef.type === "principal" && input.execution.authorizationRef.credential !== undefined ? { credential: input.execution.authorizationRef.credential } : {}
|
|
3961
|
+
} : { type: "disabled" }
|
|
3962
|
+
})
|
|
3963
|
+
});
|
|
3964
|
+
}
|
|
3965
|
+
function assertAgentExecutionRecord2(input) {
|
|
3966
|
+
const authority = input.execution.authorizationRef;
|
|
3967
|
+
if (input.execution.executor.type !== "agent" || input.execution.executor.runId !== input.runId || input.execution.source.type !== "execution") {
|
|
3968
|
+
invalidAgentExecution(input.execution.id, input.runId);
|
|
3969
|
+
}
|
|
3970
|
+
if (input.authorization.type === "disabled" || input.authorization.context.principal.type === "user") {
|
|
3971
|
+
assertInheritedAgentAuthority(input.execution, input.runId, input.authorization);
|
|
3972
|
+
return;
|
|
3973
|
+
}
|
|
3974
|
+
if (input.authorization.type !== "principal" || authority.type !== "principal" || authority.principal.type !== "serviceAccount" || input.authorization.context.principal.type !== "serviceAccount" || authority.principal.id !== input.authorization.context.principal.id || authority.credential !== undefined) {
|
|
3975
|
+
invalidAgentExecution(input.execution.id, input.runId);
|
|
3976
|
+
}
|
|
3977
|
+
if (input.actorId === undefined) {
|
|
3978
|
+
invalidAgentExecution(input.execution.id, input.runId);
|
|
3979
|
+
}
|
|
3980
|
+
assertAgentPrincipal(input.actorId, authority.principal);
|
|
3981
|
+
}
|
|
3982
|
+
function assertInheritedAgentAuthority(execution, runId, authorization) {
|
|
3983
|
+
const authority = execution.authorizationRef;
|
|
3984
|
+
if (authorization.type === "disabled") {
|
|
3985
|
+
if (authority.type !== "disabled")
|
|
3986
|
+
invalidAgentExecution(execution.id, runId);
|
|
3987
|
+
return;
|
|
3988
|
+
}
|
|
3989
|
+
const principal = authorization.context.principal;
|
|
3990
|
+
if (authority.type !== "principal" || authority.principal.type !== "user" || principal.type !== "user" || authority.principal.id !== principal.id || authority.credential === undefined || (authority.credential.type === "session" ? authorization.context.sessionId !== authority.credential.id : authorization.context.sessionId !== undefined)) {
|
|
3991
|
+
invalidAgentExecution(execution.id, runId);
|
|
3992
|
+
}
|
|
3993
|
+
}
|
|
3994
|
+
function assertAgentPrincipal(actorId, principal) {
|
|
3995
|
+
const expectedId = agentServiceAccountId2(actorId);
|
|
3996
|
+
if (principal.id !== expectedId) {
|
|
3997
|
+
throw new ExecutionStorageError2("invalid_input", `[Sixb] Agent '${actorId}' execution authority must reference service account '${expectedId}'.`);
|
|
3998
|
+
}
|
|
3999
|
+
}
|
|
4000
|
+
function invalidAgentExecution(executionId, runId) {
|
|
4001
|
+
throw new ExecutionStorageError2("invalid_input", `[Sixb] Execution '${executionId}' does not authorize Agent run '${runId}'.`);
|
|
4002
|
+
}
|
|
4003
|
+
|
|
4004
|
+
export { resolveAgentContextParts2, agentRunQueueJobId2, subagentRunQueueJobId2, workflowAgentNodeQueueJobId2, dispatchQueuedAgentRuns2, dispatchQueuedSubagentRuns2, createAgentThreadId2, createAgentRunId2, createSubagentRunId2, createSubagentExecutionId2, createAgentMessageId2, agentContextCheckpointId2, createAgentRunExecutionToken2, runModelLoop2, assertNoAgentDefinitions, bindModelExecutionAttempt, ShareError2, WorkflowDefinitionError2, WorkflowValidationError2, assertNonEmpty, isStepDefinition2, isAgentStepDefinition2, isInterventionDefinition2, isWorkflowDefinition2, validateWorkflowDefinition2, validateWorkflowsAtStartup2, validateWorkflowAgentStepGroupReferences2, validateWorkflowInput2, validateWorkflowStepInput2, validateWorkflowStepOutput2, validateWorkflowInterventionInput2, validateWorkflowInterventionResponse2, validateWorkflowInterventionDefaultResponse2, validateWorkflowAgentStepInput2, validateWorkflowAgentStepOutput2, snapshotWorkflowAgentStepInput2, snapshotWorkflowAgentStepOutput2, snapshotWorkflowInput2, snapshotWorkflowStepInput2, snapshotWorkflowStepOutput2, snapshotWorkflowInterventionInput2, snapshotWorkflowInterventionResponse2, snapshotWorkflowInterventionDefaultResponse2, snapshotWorkflowActionInput2, WorkflowRunDispatcher2, requestWorkflowRun2, createBoundSixb, isBoundSixb, canInheritAgentRequestAuthorization2, createAgentExecutionRecord2, createInheritedAgentExecutionRecord2, bindDurableAgentExecution2, restoreAgentExecutionScope2, assertAgentExecutionRecord2, requestAgentRun2, retryAgentRun2 };
|
|
4005
|
+
|
|
4006
|
+
//# debugId=8A992C0F00F3BAC264756E2164756E21
|