@jangts/agent-core 0.1.1 → 0.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (558) hide show
  1. package/CHANGELOG.md +25 -0
  2. package/LICENSE +55 -0
  3. package/NOTICE +6 -0
  4. package/README.md +8 -0
  5. package/development/docs/README.en.md +70 -0
  6. package/development/docs/README.md +1 -1
  7. package/development/docs/acceptance.en.md +34 -0
  8. package/development/docs/agent-development.en.md +42 -0
  9. package/development/docs/api/README.en.md +62 -0
  10. package/development/docs/api/advanced-agents.en.md +135 -0
  11. package/development/docs/api/context-processing.en.md +110 -0
  12. package/development/docs/api/core.en.md +274 -0
  13. package/development/docs/api/examples.en.md +118 -0
  14. package/development/docs/api/kits.en.md +183 -0
  15. package/development/docs/api/knowledge-answering.en.md +166 -0
  16. package/development/docs/api/mock.en.md +186 -0
  17. package/development/docs/api/observability.en.md +166 -0
  18. package/development/docs/api/reference.en.md +2235 -0
  19. package/development/docs/api/reference.md +1907 -1874
  20. package/development/docs/api/support.en.md +252 -0
  21. package/development/docs/api/support.md +27 -0
  22. package/development/docs/api/types.en.md +181 -0
  23. package/development/docs/api/workflow.en.md +188 -0
  24. package/development/docs/basic-usage.en.md +78 -0
  25. package/development/docs/create-app.en.md +76 -0
  26. package/development/docs/examples/offline-agent.en.md +273 -0
  27. package/development/docs/examples.en.md +36 -0
  28. package/development/docs/flows/knowledge-maintenance.en.md +38 -0
  29. package/development/docs/getting-started.en.md +71 -0
  30. package/development/docs/knowledge.en.md +89 -0
  31. package/development/docs/maintenance.en.md +62 -0
  32. package/development/docs/materials.en.md +38 -0
  33. package/development/docs/mechanisms.en.md +227 -0
  34. package/development/docs/memory-and-learning.en.md +42 -0
  35. package/development/docs/operations.en.md +51 -0
  36. package/development/docs/records.en.md +63 -0
  37. package/development/docs/registration.en.md +63 -0
  38. package/development/skills/agent-core-app/scripts/create-app.mjs +286 -70
  39. package/development/skills/agent-core-app/scripts/lib/knowledge.mjs +77 -16
  40. package/development/skills/agent-core-app/scripts/lib/source.mjs +30 -2
  41. package/development/skills/agent-core-app/scripts/plan.mjs +46 -12
  42. package/development/skills/agent-core-app/scripts/prepare-source.mjs +61 -10
  43. package/development/skills/agent-core-app/scripts/resources.mjs +62 -17
  44. package/development/skills/agent-core-app/scripts/validate-knowledge.mjs +18 -1
  45. package/development/skills/agent-core-app/templates/catalog.json +36 -22
  46. package/dist/cjs/capabilities/index.js +13 -0
  47. package/dist/cjs/capabilities/invocation.js +80 -10
  48. package/dist/cjs/capabilities/model.js +126 -13
  49. package/dist/cjs/capabilities/tool-runtime.js +64 -12
  50. package/dist/cjs/capabilities/tools.js +266 -31
  51. package/dist/cjs/context/assembly.js +46 -5
  52. package/dist/cjs/context/audit.js +31 -6
  53. package/dist/cjs/context/fragments.js +54 -11
  54. package/dist/cjs/context/index.js +12 -0
  55. package/dist/cjs/context/journal.js +84 -7
  56. package/dist/cjs/context/plan.js +30 -2
  57. package/dist/cjs/diagnostics/catalog.js +17 -3
  58. package/dist/cjs/diagnostics/index.js +149 -29
  59. package/dist/cjs/diagnostics/sub-flow.js +240 -40
  60. package/dist/cjs/errors.js +99 -17
  61. package/dist/cjs/execution/branch.js +20 -4
  62. package/dist/cjs/execution/engine.js +470 -56
  63. package/dist/cjs/execution/events.js +136 -18
  64. package/dist/cjs/execution/index.js +7 -0
  65. package/dist/cjs/execution/reporting.js +75 -6
  66. package/dist/cjs/execution/state.js +161 -22
  67. package/dist/cjs/execution/workflow.js +224 -32
  68. package/dist/cjs/index.js +18 -0
  69. package/dist/cjs/kits/aggregation.js +45 -3
  70. package/dist/cjs/kits/answering/batch.js +23 -4
  71. package/dist/cjs/kits/answering/check-result.js +31 -8
  72. package/dist/cjs/kits/answering/checks.js +24 -3
  73. package/dist/cjs/kits/answering/flow.js +192 -36
  74. package/dist/cjs/kits/answering/index.js +19 -1
  75. package/dist/cjs/kits/answering/tasks.js +88 -13
  76. package/dist/cjs/kits/artifacts.js +36 -4
  77. package/dist/cjs/kits/candidates.js +47 -5
  78. package/dist/cjs/kits/delivery.js +40 -5
  79. package/dist/cjs/kits/durable.js +155 -31
  80. package/dist/cjs/kits/evidence.js +66 -15
  81. package/dist/cjs/kits/family.js +152 -22
  82. package/dist/cjs/kits/index.js +12 -1
  83. package/dist/cjs/kits/inference.js +104 -16
  84. package/dist/cjs/kits/intents/catalog.js +67 -16
  85. package/dist/cjs/kits/intents/index.js +11 -0
  86. package/dist/cjs/kits/intents/registry.js +188 -43
  87. package/dist/cjs/kits/intents/scopes.js +215 -46
  88. package/dist/cjs/kits/interaction/command.js +140 -36
  89. package/dist/cjs/kits/interaction/commands.js +86 -11
  90. package/dist/cjs/kits/interaction/handlers.js +27 -10
  91. package/dist/cjs/kits/interaction/index.js +10 -0
  92. package/dist/cjs/kits/interaction/transfer.js +80 -14
  93. package/dist/cjs/kits/knowledge/catalog.js +62 -11
  94. package/dist/cjs/kits/knowledge/index.js +16 -1
  95. package/dist/cjs/kits/knowledge/publication.js +99 -23
  96. package/dist/cjs/kits/knowledge/sections.js +33 -4
  97. package/dist/cjs/kits/normalization.js +51 -7
  98. package/dist/cjs/kits/policies.js +79 -15
  99. package/dist/cjs/kits/presentation/events.js +54 -10
  100. package/dist/cjs/kits/presentation/index.js +24 -1
  101. package/dist/cjs/kits/presentation/outputs.js +176 -38
  102. package/dist/cjs/kits/presentation/templates.js +33 -5
  103. package/dist/cjs/kits/presentation/variants.js +31 -2
  104. package/dist/cjs/kits/projection.js +63 -8
  105. package/dist/cjs/kits/rank-fusion.js +27 -4
  106. package/dist/cjs/kits/reflection-log-source.js +89 -16
  107. package/dist/cjs/kits/reflection.js +234 -60
  108. package/dist/cjs/kits/retrieval.js +98 -18
  109. package/dist/cjs/kits/search.js +180 -27
  110. package/dist/cjs/kits/text-skills.js +104 -19
  111. package/dist/cjs/kits/tools.js +415 -74
  112. package/dist/cjs/kits/vector-search.js +50 -16
  113. package/dist/cjs/mock/node.js +7 -1
  114. package/dist/cjs/mock/web.js +7 -1
  115. package/dist/cjs/mock.js +7 -1
  116. package/dist/cjs/model/binding.js +68 -17
  117. package/dist/cjs/model/call-budget.js +45 -4
  118. package/dist/cjs/model/decision-retry.js +19 -1
  119. package/dist/cjs/model/defaults.js +27 -4
  120. package/dist/cjs/model/index.js +7 -0
  121. package/dist/cjs/model/interactions/arguments.js +36 -1
  122. package/dist/cjs/model/interactions/json-object.js +48 -12
  123. package/dist/cjs/model/interactions/native-functions.js +52 -10
  124. package/dist/cjs/model/message-diagnostics.js +17 -4
  125. package/dist/cjs/model/options.js +9 -1
  126. package/dist/cjs/model/preparation.js +86 -12
  127. package/dist/cjs/model/runner.js +413 -79
  128. package/dist/cjs/model/selection-transport.js +48 -8
  129. package/dist/cjs/model/settings.js +67 -13
  130. package/dist/cjs/model/token-budget.js +69 -11
  131. package/dist/cjs/model/transports.js +59 -6
  132. package/dist/cjs/structs/common.js +11 -0
  133. package/dist/cjs/structs/debug.js +34 -5
  134. package/dist/cjs/structs/errors.js +26 -1
  135. package/dist/cjs/structs/index.js +11 -1
  136. package/dist/cjs/structs/kits/durable.js +7 -0
  137. package/dist/cjs/structs/kits/family.js +1 -0
  138. package/dist/cjs/structs/kits/interaction.js +8 -1
  139. package/dist/cjs/structs/kits/knowledge-publication.js +1 -0
  140. package/dist/cjs/structs/kits/reflection.js +18 -3
  141. package/dist/cjs/structs/model/chat-provider.js +6 -0
  142. package/dist/cjs/structs/support/model/completion.js +2 -0
  143. package/dist/cjs/structs/support/model/messages.js +2 -0
  144. package/dist/cjs/support/capabilities.js +43 -6
  145. package/dist/cjs/support/context/assembly.js +88 -16
  146. package/dist/cjs/support/context/compression.js +48 -6
  147. package/dist/cjs/support/context/fragments.js +6 -0
  148. package/dist/cjs/support/context/history.js +36 -1
  149. package/dist/cjs/support/context/index.js +11 -0
  150. package/dist/cjs/support/context/nodes.js +164 -35
  151. package/dist/cjs/support/context/processing.js +319 -61
  152. package/dist/cjs/support/context/selection-policy.js +98 -21
  153. package/dist/cjs/support/context/selection.js +61 -10
  154. package/dist/cjs/support/context/snapshot.js +29 -7
  155. package/dist/cjs/support/context/strategies.js +120 -28
  156. package/dist/cjs/support/index.js +9 -1
  157. package/dist/cjs/support/model/capabilities.js +20 -1
  158. package/dist/cjs/support/model/chat-completions.js +92 -20
  159. package/dist/cjs/support/model/children.js +34 -6
  160. package/dist/cjs/support/model/compatible-provider.js +189 -59
  161. package/dist/cjs/support/model/completion/calls.js +61 -0
  162. package/dist/cjs/support/model/completion/default.js +33 -0
  163. package/dist/cjs/support/model/completion/index.js +28 -0
  164. package/dist/cjs/support/model/completion/session.js +107 -0
  165. package/dist/cjs/support/model/index.js +12 -0
  166. package/dist/cjs/support/model/interactions/index.js +12 -1
  167. package/dist/cjs/support/model/interactions/json-object.js +6 -0
  168. package/dist/cjs/support/model/interactions/native-functions.js +6 -0
  169. package/dist/cjs/support/model/observer.js +32 -6
  170. package/dist/cjs/support/model/preview-rules.js +66 -16
  171. package/dist/cjs/support/model/reply-preview.js +77 -17
  172. package/dist/cjs/support/model/stage-transport.js +33 -7
  173. package/dist/cjs/support/model/strategies.js +75 -14
  174. package/dist/cjs/support/model/transports.js +53 -11
  175. package/dist/cjs/support/registration.js +49 -7
  176. package/dist/cjs/support/schema.js +46 -4
  177. package/dist/cjs/support/stream-events.js +60 -8
  178. package/dist/cjs/support/tool-runtime.js +6 -0
  179. package/dist/cjs/support/tools.js +79 -10
  180. package/dist/cjs/support/transport/index.js +7 -0
  181. package/dist/cjs/support/transport/json.js +28 -4
  182. package/dist/cjs/support/transport/sse.js +25 -2
  183. package/dist/cjs/utils/break-observer.js +20 -2
  184. package/dist/cjs/utils/cancellation.js +77 -9
  185. package/dist/cjs/utils/catalog.js +19 -4
  186. package/dist/cjs/utils/debug.js +14 -2
  187. package/dist/cjs/utils/index.js +8 -0
  188. package/dist/cjs/utils/interaction-definition.js +26 -6
  189. package/dist/cjs/utils/invocation.js +42 -4
  190. package/dist/cjs/utils/model-protocol.js +20 -1
  191. package/dist/cjs/utils/object.js +16 -0
  192. package/dist/cjs/utils/observer.js +22 -2
  193. package/dist/cjs/utils/protocol-registry.js +47 -4
  194. package/dist/cjs/utils/query-key.js +21 -2
  195. package/dist/cjs/utils/registration.js +18 -2
  196. package/dist/cjs/utils/rules.js +39 -11
  197. package/dist/cjs/utils/schema-adapter.js +25 -2
  198. package/dist/cjs/utils/synchronous.js +64 -7
  199. package/dist/cjs/utils/text.js +15 -1
  200. package/dist/esm/capabilities/index.d.ts +13 -0
  201. package/dist/esm/capabilities/index.js +13 -0
  202. package/dist/esm/capabilities/invocation.d.ts +16 -2
  203. package/dist/esm/capabilities/invocation.js +80 -10
  204. package/dist/esm/capabilities/model.d.ts +68 -1
  205. package/dist/esm/capabilities/model.js +126 -13
  206. package/dist/esm/capabilities/tool-runtime.d.ts +11 -0
  207. package/dist/esm/capabilities/tool-runtime.js +64 -12
  208. package/dist/esm/capabilities/tools.d.ts +96 -3
  209. package/dist/esm/capabilities/tools.js +267 -32
  210. package/dist/esm/context/assembly.d.ts +13 -2
  211. package/dist/esm/context/assembly.js +46 -5
  212. package/dist/esm/context/audit.d.ts +23 -1
  213. package/dist/esm/context/audit.js +31 -6
  214. package/dist/esm/context/fragments.d.ts +37 -3
  215. package/dist/esm/context/fragments.js +54 -11
  216. package/dist/esm/context/index.d.ts +12 -0
  217. package/dist/esm/context/index.js +12 -0
  218. package/dist/esm/context/journal.d.ts +32 -1
  219. package/dist/esm/context/journal.js +84 -7
  220. package/dist/esm/context/plan.d.ts +11 -1
  221. package/dist/esm/context/plan.js +30 -2
  222. package/dist/esm/diagnostics/catalog.d.ts +6 -0
  223. package/dist/esm/diagnostics/catalog.js +17 -3
  224. package/dist/esm/diagnostics/index.d.ts +30 -2
  225. package/dist/esm/diagnostics/index.js +149 -29
  226. package/dist/esm/diagnostics/sub-flow.d.ts +41 -3
  227. package/dist/esm/diagnostics/sub-flow.js +240 -40
  228. package/dist/esm/errors.d.ts +22 -2
  229. package/dist/esm/errors.js +99 -17
  230. package/dist/esm/execution/branch.d.ts +19 -1
  231. package/dist/esm/execution/branch.js +20 -4
  232. package/dist/esm/execution/engine.d.ts +291 -5
  233. package/dist/esm/execution/engine.js +471 -57
  234. package/dist/esm/execution/events.d.ts +16 -2
  235. package/dist/esm/execution/events.js +136 -18
  236. package/dist/esm/execution/index.d.ts +7 -0
  237. package/dist/esm/execution/index.js +7 -0
  238. package/dist/esm/execution/reporting.d.ts +49 -1
  239. package/dist/esm/execution/reporting.js +75 -6
  240. package/dist/esm/execution/state.d.ts +126 -10
  241. package/dist/esm/execution/state.js +161 -22
  242. package/dist/esm/execution/workflow.d.ts +121 -3
  243. package/dist/esm/execution/workflow.js +224 -32
  244. package/dist/esm/index.d.ts +17 -1
  245. package/dist/esm/index.js +18 -0
  246. package/dist/esm/kits/aggregation.d.ts +34 -2
  247. package/dist/esm/kits/aggregation.js +45 -3
  248. package/dist/esm/kits/answering/batch.d.ts +17 -0
  249. package/dist/esm/kits/answering/batch.js +23 -4
  250. package/dist/esm/kits/answering/check-result.d.ts +18 -1
  251. package/dist/esm/kits/answering/check-result.js +31 -8
  252. package/dist/esm/kits/answering/checks.d.ts +11 -0
  253. package/dist/esm/kits/answering/checks.js +24 -3
  254. package/dist/esm/kits/answering/flow.d.ts +25 -2
  255. package/dist/esm/kits/answering/flow.js +192 -36
  256. package/dist/esm/kits/answering/index.d.ts +12 -0
  257. package/dist/esm/kits/answering/index.js +19 -1
  258. package/dist/esm/kits/answering/tasks.d.ts +32 -1
  259. package/dist/esm/kits/answering/tasks.js +88 -13
  260. package/dist/esm/kits/artifacts.d.ts +11 -0
  261. package/dist/esm/kits/artifacts.js +36 -4
  262. package/dist/esm/kits/candidates.d.ts +23 -1
  263. package/dist/esm/kits/candidates.js +47 -5
  264. package/dist/esm/kits/delivery.d.ts +34 -0
  265. package/dist/esm/kits/delivery.js +40 -5
  266. package/dist/esm/kits/durable.d.ts +19 -0
  267. package/dist/esm/kits/durable.js +155 -31
  268. package/dist/esm/kits/evidence.d.ts +28 -5
  269. package/dist/esm/kits/evidence.js +66 -15
  270. package/dist/esm/kits/family.d.ts +17 -1
  271. package/dist/esm/kits/family.js +152 -22
  272. package/dist/esm/kits/index.d.ts +12 -1
  273. package/dist/esm/kits/index.js +12 -1
  274. package/dist/esm/kits/inference.d.ts +64 -0
  275. package/dist/esm/kits/inference.js +104 -16
  276. package/dist/esm/kits/intents/catalog.d.ts +13 -1
  277. package/dist/esm/kits/intents/catalog.js +67 -16
  278. package/dist/esm/kits/intents/index.d.ts +11 -0
  279. package/dist/esm/kits/intents/index.js +11 -0
  280. package/dist/esm/kits/intents/registry.d.ts +61 -3
  281. package/dist/esm/kits/intents/registry.js +188 -43
  282. package/dist/esm/kits/intents/scopes.d.ts +73 -3
  283. package/dist/esm/kits/intents/scopes.js +215 -46
  284. package/dist/esm/kits/interaction/command.d.ts +38 -4
  285. package/dist/esm/kits/interaction/command.js +140 -36
  286. package/dist/esm/kits/interaction/commands.d.ts +66 -2
  287. package/dist/esm/kits/interaction/commands.js +86 -11
  288. package/dist/esm/kits/interaction/handlers.d.ts +19 -2
  289. package/dist/esm/kits/interaction/handlers.js +27 -10
  290. package/dist/esm/kits/interaction/index.d.ts +10 -0
  291. package/dist/esm/kits/interaction/index.js +10 -0
  292. package/dist/esm/kits/interaction/transfer.d.ts +39 -2
  293. package/dist/esm/kits/interaction/transfer.js +80 -14
  294. package/dist/esm/kits/knowledge/catalog.d.ts +13 -0
  295. package/dist/esm/kits/knowledge/catalog.js +62 -11
  296. package/dist/esm/kits/knowledge/index.d.ts +11 -0
  297. package/dist/esm/kits/knowledge/index.js +16 -1
  298. package/dist/esm/kits/knowledge/publication.d.ts +15 -1
  299. package/dist/esm/kits/knowledge/publication.js +99 -23
  300. package/dist/esm/kits/knowledge/sections.d.ts +31 -1
  301. package/dist/esm/kits/knowledge/sections.js +33 -4
  302. package/dist/esm/kits/normalization.d.ts +25 -2
  303. package/dist/esm/kits/normalization.js +51 -7
  304. package/dist/esm/kits/policies.d.ts +26 -3
  305. package/dist/esm/kits/policies.js +79 -15
  306. package/dist/esm/kits/presentation/events.d.ts +51 -4
  307. package/dist/esm/kits/presentation/events.js +54 -10
  308. package/dist/esm/kits/presentation/index.d.ts +12 -0
  309. package/dist/esm/kits/presentation/index.js +25 -2
  310. package/dist/esm/kits/presentation/outputs.d.ts +30 -1
  311. package/dist/esm/kits/presentation/outputs.js +176 -38
  312. package/dist/esm/kits/presentation/templates.d.ts +32 -3
  313. package/dist/esm/kits/presentation/templates.js +33 -5
  314. package/dist/esm/kits/presentation/variants.d.ts +29 -0
  315. package/dist/esm/kits/presentation/variants.js +31 -2
  316. package/dist/esm/kits/projection.d.ts +42 -5
  317. package/dist/esm/kits/projection.js +63 -8
  318. package/dist/esm/kits/rank-fusion.d.ts +21 -1
  319. package/dist/esm/kits/rank-fusion.js +28 -5
  320. package/dist/esm/kits/reflection-log-source.d.ts +28 -1
  321. package/dist/esm/kits/reflection-log-source.js +89 -16
  322. package/dist/esm/kits/reflection.d.ts +17 -1
  323. package/dist/esm/kits/reflection.js +235 -61
  324. package/dist/esm/kits/retrieval.d.ts +18 -2
  325. package/dist/esm/kits/retrieval.js +98 -18
  326. package/dist/esm/kits/search.d.ts +56 -3
  327. package/dist/esm/kits/search.js +180 -27
  328. package/dist/esm/kits/text-skills.d.ts +16 -2
  329. package/dist/esm/kits/text-skills.js +104 -19
  330. package/dist/esm/kits/tools.d.ts +122 -2
  331. package/dist/esm/kits/tools.js +416 -74
  332. package/dist/esm/kits/vector-search.d.ts +47 -1
  333. package/dist/esm/kits/vector-search.js +51 -17
  334. package/dist/esm/mock/node.d.ts +7 -0
  335. package/dist/esm/mock/node.js +7 -1
  336. package/dist/esm/mock/web.d.ts +7 -0
  337. package/dist/esm/mock/web.js +7 -1
  338. package/dist/esm/mock.d.ts +7 -0
  339. package/dist/esm/mock.js +7 -1
  340. package/dist/esm/model/binding.d.ts +32 -3
  341. package/dist/esm/model/binding.js +68 -17
  342. package/dist/esm/model/call-budget.d.ts +30 -2
  343. package/dist/esm/model/call-budget.js +45 -4
  344. package/dist/esm/model/decision-retry.d.ts +10 -1
  345. package/dist/esm/model/decision-retry.js +19 -1
  346. package/dist/esm/model/defaults.d.ts +13 -2
  347. package/dist/esm/model/defaults.js +27 -4
  348. package/dist/esm/model/index.d.ts +7 -0
  349. package/dist/esm/model/index.js +7 -0
  350. package/dist/esm/model/interactions/arguments.d.ts +27 -0
  351. package/dist/esm/model/interactions/arguments.js +36 -1
  352. package/dist/esm/model/interactions/json-object.d.ts +7 -1
  353. package/dist/esm/model/interactions/json-object.js +48 -12
  354. package/dist/esm/model/interactions/native-functions.d.ts +6 -0
  355. package/dist/esm/model/interactions/native-functions.js +52 -10
  356. package/dist/esm/model/message-diagnostics.d.ts +17 -1
  357. package/dist/esm/model/message-diagnostics.js +17 -4
  358. package/dist/esm/model/options.d.ts +18 -1
  359. package/dist/esm/model/options.js +9 -1
  360. package/dist/esm/model/preparation.d.ts +30 -2
  361. package/dist/esm/model/preparation.js +86 -12
  362. package/dist/esm/model/runner.d.ts +129 -5
  363. package/dist/esm/model/runner.js +414 -80
  364. package/dist/esm/model/selection-transport.d.ts +14 -1
  365. package/dist/esm/model/selection-transport.js +48 -8
  366. package/dist/esm/model/settings.d.ts +11 -0
  367. package/dist/esm/model/settings.js +67 -13
  368. package/dist/esm/model/token-budget.d.ts +59 -1
  369. package/dist/esm/model/token-budget.js +69 -11
  370. package/dist/esm/model/transports.d.ts +20 -2
  371. package/dist/esm/model/transports.js +59 -6
  372. package/dist/esm/structs/capabilities/invocation.d.ts +36 -0
  373. package/dist/esm/structs/capabilities/model.d.ts +27 -0
  374. package/dist/esm/structs/capabilities/tools.d.ts +38 -0
  375. package/dist/esm/structs/common.d.ts +62 -2
  376. package/dist/esm/structs/common.js +11 -0
  377. package/dist/esm/structs/context/fragments.d.ts +28 -0
  378. package/dist/esm/structs/context/journal.d.ts +28 -3
  379. package/dist/esm/structs/context/processing.d.ts +11 -0
  380. package/dist/esm/structs/debug.d.ts +58 -1
  381. package/dist/esm/structs/debug.js +34 -5
  382. package/dist/esm/structs/diagnostics.d.ts +119 -1
  383. package/dist/esm/structs/errors.d.ts +42 -1
  384. package/dist/esm/structs/errors.js +26 -1
  385. package/dist/esm/structs/execution/engine.d.ts +24 -1
  386. package/dist/esm/structs/execution/events.d.ts +12 -0
  387. package/dist/esm/structs/execution/workflow.d.ts +71 -0
  388. package/dist/esm/structs/index.d.ts +11 -1
  389. package/dist/esm/structs/index.js +11 -1
  390. package/dist/esm/structs/invocation.d.ts +30 -0
  391. package/dist/esm/structs/kits/aggregation.d.ts +12 -0
  392. package/dist/esm/structs/kits/answering/checks.d.ts +11 -0
  393. package/dist/esm/structs/kits/answering/flow.d.ts +35 -1
  394. package/dist/esm/structs/kits/answering/state.d.ts +21 -0
  395. package/dist/esm/structs/kits/answering/tasks.d.ts +21 -0
  396. package/dist/esm/structs/kits/artifacts.d.ts +14 -0
  397. package/dist/esm/structs/kits/candidates.d.ts +19 -0
  398. package/dist/esm/structs/kits/delivery.d.ts +22 -0
  399. package/dist/esm/structs/kits/durable.d.ts +56 -3
  400. package/dist/esm/structs/kits/durable.js +7 -0
  401. package/dist/esm/structs/kits/evidence.d.ts +23 -0
  402. package/dist/esm/structs/kits/family.d.ts +49 -1
  403. package/dist/esm/structs/kits/family.js +1 -0
  404. package/dist/esm/structs/kits/intents/catalog.d.ts +26 -0
  405. package/dist/esm/structs/kits/intents/registry.d.ts +34 -0
  406. package/dist/esm/structs/kits/intents/scopes.d.ts +36 -1
  407. package/dist/esm/structs/kits/interaction.d.ts +64 -0
  408. package/dist/esm/structs/kits/interaction.js +8 -1
  409. package/dist/esm/structs/kits/knowledge-publication.d.ts +43 -1
  410. package/dist/esm/structs/kits/knowledge-publication.js +1 -0
  411. package/dist/esm/structs/kits/knowledge.d.ts +39 -2
  412. package/dist/esm/structs/kits/normalization.d.ts +15 -0
  413. package/dist/esm/structs/kits/policies.d.ts +25 -1
  414. package/dist/esm/structs/kits/presentation/events.d.ts +28 -4
  415. package/dist/esm/structs/kits/presentation/outputs.d.ts +38 -1
  416. package/dist/esm/structs/kits/presentation/templates.d.ts +15 -0
  417. package/dist/esm/structs/kits/projection.d.ts +21 -0
  418. package/dist/esm/structs/kits/reflection.d.ts +61 -2
  419. package/dist/esm/structs/kits/reflection.js +18 -3
  420. package/dist/esm/structs/kits/retrieval.d.ts +39 -0
  421. package/dist/esm/structs/kits/search.d.ts +24 -0
  422. package/dist/esm/structs/kits/text-skills.d.ts +36 -0
  423. package/dist/esm/structs/kits/tools.d.ts +87 -0
  424. package/dist/esm/structs/model/chat-provider.d.ts +24 -1
  425. package/dist/esm/structs/model/chat-provider.js +6 -0
  426. package/dist/esm/structs/model/interactions.d.ts +38 -0
  427. package/dist/esm/structs/model/messages.d.ts +34 -0
  428. package/dist/esm/structs/model/runtime.d.ts +104 -6
  429. package/dist/esm/structs/support/capabilities.d.ts +19 -2
  430. package/dist/esm/structs/support/context-processing.d.ts +88 -9
  431. package/dist/esm/structs/support/context.d.ts +29 -1
  432. package/dist/esm/structs/support/model/completion.d.ts +50 -0
  433. package/dist/esm/structs/support/model/completion.js +1 -0
  434. package/dist/esm/structs/support/model/interactions.d.ts +13 -1
  435. package/dist/esm/structs/support/model/messages.d.ts +54 -0
  436. package/dist/esm/structs/support/model/messages.js +1 -0
  437. package/dist/esm/structs/support/model/provider-observer.d.ts +22 -1
  438. package/dist/esm/structs/support/model/provider.d.ts +71 -6
  439. package/dist/esm/structs/support/registration.d.ts +13 -0
  440. package/dist/esm/structs/support/schema.d.ts +14 -0
  441. package/dist/esm/structs/support/tools.d.ts +28 -0
  442. package/dist/esm/structs/support/transport/json.d.ts +16 -0
  443. package/dist/esm/structs/support/transport/sse.d.ts +15 -0
  444. package/dist/esm/structs/utils/rules.d.ts +19 -0
  445. package/dist/esm/support/capabilities.d.ts +25 -2
  446. package/dist/esm/support/capabilities.js +43 -6
  447. package/dist/esm/support/context/assembly.d.ts +35 -4
  448. package/dist/esm/support/context/assembly.js +88 -16
  449. package/dist/esm/support/context/compression.d.ts +17 -1
  450. package/dist/esm/support/context/compression.js +48 -6
  451. package/dist/esm/support/context/fragments.d.ts +6 -0
  452. package/dist/esm/support/context/fragments.js +6 -0
  453. package/dist/esm/support/context/history.d.ts +43 -0
  454. package/dist/esm/support/context/history.js +36 -1
  455. package/dist/esm/support/context/index.d.ts +13 -2
  456. package/dist/esm/support/context/index.js +12 -1
  457. package/dist/esm/support/context/nodes.d.ts +65 -3
  458. package/dist/esm/support/context/nodes.js +165 -36
  459. package/dist/esm/support/context/processing.d.ts +152 -1
  460. package/dist/esm/support/context/processing.js +320 -62
  461. package/dist/esm/support/context/selection-policy.d.ts +42 -2
  462. package/dist/esm/support/context/selection-policy.js +98 -21
  463. package/dist/esm/support/context/selection.d.ts +14 -1
  464. package/dist/esm/support/context/selection.js +61 -10
  465. package/dist/esm/support/context/snapshot.d.ts +23 -1
  466. package/dist/esm/support/context/snapshot.js +29 -7
  467. package/dist/esm/support/context/strategies.d.ts +35 -2
  468. package/dist/esm/support/context/strategies.js +120 -28
  469. package/dist/esm/support/index.d.ts +9 -1
  470. package/dist/esm/support/index.js +9 -1
  471. package/dist/esm/support/model/capabilities.d.ts +10 -0
  472. package/dist/esm/support/model/capabilities.js +20 -1
  473. package/dist/esm/support/model/chat-completions.d.ts +44 -15
  474. package/dist/esm/support/model/chat-completions.js +92 -20
  475. package/dist/esm/support/model/children.d.ts +34 -2
  476. package/dist/esm/support/model/children.js +34 -6
  477. package/dist/esm/support/model/compatible-provider.d.ts +29 -3
  478. package/dist/esm/support/model/compatible-provider.js +190 -60
  479. package/dist/esm/support/model/completion/calls.d.ts +40 -0
  480. package/dist/esm/support/model/completion/calls.js +58 -0
  481. package/dist/esm/support/model/completion/default.d.ts +11 -0
  482. package/dist/esm/support/model/completion/default.js +30 -0
  483. package/dist/esm/support/model/completion/index.d.ts +10 -0
  484. package/dist/esm/support/model/completion/index.js +22 -0
  485. package/dist/esm/support/model/completion/session.d.ts +16 -0
  486. package/dist/esm/support/model/completion/session.js +104 -0
  487. package/dist/esm/support/model/index.d.ts +14 -0
  488. package/dist/esm/support/model/index.js +12 -0
  489. package/dist/esm/support/model/interactions/index.d.ts +1 -1
  490. package/dist/esm/support/model/interactions/index.js +12 -1
  491. package/dist/esm/support/model/interactions/json-object.d.ts +6 -0
  492. package/dist/esm/support/model/interactions/json-object.js +6 -0
  493. package/dist/esm/support/model/interactions/native-functions.d.ts +6 -0
  494. package/dist/esm/support/model/interactions/native-functions.js +6 -0
  495. package/dist/esm/support/model/observer.d.ts +25 -2
  496. package/dist/esm/support/model/observer.js +32 -6
  497. package/dist/esm/support/model/preview-rules.d.ts +26 -2
  498. package/dist/esm/support/model/preview-rules.js +66 -16
  499. package/dist/esm/support/model/reply-preview.d.ts +22 -1
  500. package/dist/esm/support/model/reply-preview.js +77 -17
  501. package/dist/esm/support/model/stage-transport.d.ts +9 -1
  502. package/dist/esm/support/model/stage-transport.js +33 -7
  503. package/dist/esm/support/model/strategies.d.ts +28 -2
  504. package/dist/esm/support/model/strategies.js +75 -14
  505. package/dist/esm/support/model/transports.d.ts +17 -1
  506. package/dist/esm/support/model/transports.js +53 -11
  507. package/dist/esm/support/registration.d.ts +20 -1
  508. package/dist/esm/support/registration.js +49 -7
  509. package/dist/esm/support/schema.d.ts +31 -1
  510. package/dist/esm/support/schema.js +46 -4
  511. package/dist/esm/support/stream-events.d.ts +22 -1
  512. package/dist/esm/support/stream-events.js +60 -8
  513. package/dist/esm/support/tool-runtime.d.ts +6 -0
  514. package/dist/esm/support/tool-runtime.js +6 -0
  515. package/dist/esm/support/tools.d.ts +22 -0
  516. package/dist/esm/support/tools.js +79 -10
  517. package/dist/esm/support/transport/index.d.ts +7 -0
  518. package/dist/esm/support/transport/index.js +7 -0
  519. package/dist/esm/support/transport/json.d.ts +29 -2
  520. package/dist/esm/support/transport/json.js +28 -4
  521. package/dist/esm/support/transport/sse.d.ts +31 -1
  522. package/dist/esm/support/transport/sse.js +25 -2
  523. package/dist/esm/types.d.ts +9 -1
  524. package/dist/esm/utils/break-observer.d.ts +27 -2
  525. package/dist/esm/utils/break-observer.js +20 -2
  526. package/dist/esm/utils/cancellation.d.ts +56 -5
  527. package/dist/esm/utils/cancellation.js +77 -9
  528. package/dist/esm/utils/catalog.d.ts +20 -1
  529. package/dist/esm/utils/catalog.js +19 -4
  530. package/dist/esm/utils/debug.d.ts +20 -1
  531. package/dist/esm/utils/debug.js +14 -2
  532. package/dist/esm/utils/index.d.ts +8 -0
  533. package/dist/esm/utils/index.js +8 -0
  534. package/dist/esm/utils/interaction-definition.d.ts +18 -1
  535. package/dist/esm/utils/interaction-definition.js +26 -6
  536. package/dist/esm/utils/invocation.d.ts +36 -1
  537. package/dist/esm/utils/invocation.js +42 -4
  538. package/dist/esm/utils/model-protocol.d.ts +8 -0
  539. package/dist/esm/utils/model-protocol.js +20 -1
  540. package/dist/esm/utils/object.d.ts +16 -0
  541. package/dist/esm/utils/object.js +16 -0
  542. package/dist/esm/utils/observer.d.ts +19 -1
  543. package/dist/esm/utils/observer.js +22 -2
  544. package/dist/esm/utils/protocol-registry.d.ts +38 -1
  545. package/dist/esm/utils/protocol-registry.js +47 -4
  546. package/dist/esm/utils/query-key.d.ts +11 -1
  547. package/dist/esm/utils/query-key.js +21 -2
  548. package/dist/esm/utils/registration.d.ts +34 -2
  549. package/dist/esm/utils/registration.js +18 -2
  550. package/dist/esm/utils/rules.d.ts +81 -4
  551. package/dist/esm/utils/rules.js +39 -11
  552. package/dist/esm/utils/schema-adapter.d.ts +12 -1
  553. package/dist/esm/utils/schema-adapter.js +25 -2
  554. package/dist/esm/utils/synchronous.d.ts +60 -4
  555. package/dist/esm/utils/synchronous.js +64 -7
  556. package/dist/esm/utils/text.d.ts +15 -1
  557. package/dist/esm/utils/text.js +15 -1
  558. package/package.json +7 -3
@@ -0,0 +1,274 @@
1
+ # Core: execution, models, and real tools
2
+
3
+ [Shared types](types.md) · [Back to home](README.md). Below, `execution`, `OperationContext`, `SchemaAdapter`, and `ReadonlyCatalog` all use the shared contracts.
4
+
5
+ ## ModelRunner
6
+
7
+ ```ts
8
+ new ModelRunner({ provider, transports?, execution?, ...options })
9
+ runner.invoke({ input, stageId?, transport?, maxOutputTokens? }): Promise<ModelResult<Output>>
10
+ runner.invoke(input: string): Promise<ModelResult<string>> // 只归一化输入,返回外形不变
11
+ ```
12
+
13
+ | Constructor field | Type / semantics |
14
+ | --- | --- |
15
+ | provider | ChatProvider; the App supplies the actual model connection |
16
+ | transports | Read-only ModelTransport array with unique registered IDs; defaults to only core:plain-text |
17
+ | execution | ExecutionOptions; bound to one request, and Core supplies signal when absent |
18
+ | maxCalls | Per-request model call limit, including selection and compression calls that use the Runner of the same request |
19
+ | callTimeoutMs | Duration of a single call; does not extend the upper request deadline |
20
+ | maxInputChars/maxOutputChars/maxSchemaChars | Three distinct character budgets; they are not interchangeable |
21
+ | tokenBudget | Token budget with an explicit counter identity and counting port; character conversion is never guessed |
22
+ | maxOutputTokens | Default output reservation for a single call; invoke can override it |
23
+ | sink.output | (event: ModelOutputEvent) => void \| Promise<void>; body delivery is awaited in order and failures propagate; model.end is a bounded wrap-up notification |
24
+ | execution.observe | ExecutionObserver; uniformly receives node, model, and tool process facts, out of band, with failure isolation |
25
+
26
+ `input` is the shared ModelInput: plain text, a read-only message array, BuiltContext, or ContextPlan. The string shorthand omits the input object and returns the same kind of ModelResult.
27
+
28
+ The two plain-text calls are fully equivalent:
29
+
30
+ ```ts
31
+ const a = await runner.invoke('你好');
32
+ const b = await runner.invoke({ input: '你好' });
33
+ // a、b都为ModelResult<string>,正文取value,调用信息取invocation。
34
+ ```
35
+
36
+ A successful result is always `{ value, invocation }`. A structured model only changes the static type of value; it never switches to a bare object and offers no raw/fullResponse return mode. Errors propagate through Promise rejection. The model cannot fill invocation with actual call events or receipts.
37
+
38
+ Type inference comes from the read-only transports tuple that preserves literal IDs at construction; Output cannot be inferred from an arbitrary string alone. When invoke omits transport it always selects the built-in `core:plain-text` and does not guess a default from the "only registered transport"; stageId defaults to `model`. A known literal ID returns the matching ModelResult<T>, while a dynamic string returns ModelResult<unknown>. The string shorthand and an object input with the same value infer identically.
39
+
40
+ The same `transport` field accepts a registered ID or a transport handle. When a handle is passed, the original object is verified as registered and the result is inferred from that object's contract.
41
+
42
+ Budgets default to the current modelRunnerDefaults: maxCalls=8, callTimeoutMs=30000, maxInputChars=32000, maxOutputChars=16000, maxSchemaChars=16000, maxOutputTokens=1024. maxCalls is a non-negative safe integer; maxInputChars/maxOutputChars are non-negative safe integers or Infinity; maxSchemaChars/maxOutputTokens are positive safe integers, and callTimeoutMs is a safe integer from 1 to 2147483647. The token budget additionally validates the window, counter, and safety margin; these defaults are not a statement of provider capacity.
43
+
44
+ Input messages contain fields such as role/content/images, and images in read-only input are retained with the message. remainingCalls, signal, and journal can be read directly; call counts use callCount/totalCallCount. lastCall is a read-only snapshot of the previous completed record and is not a basis for concurrent correlation. Selection and compression nodes share counts through the same model port. A single runner executes one call at a time; concurrent tasks each use a child runner, and each returned value is correlated by its own invocation.
45
+
46
+ ```ts
47
+ interface ModelCapability<Input, Output = Input> {
48
+ readonly id: string;
49
+ readonly description: string;
50
+ readonly inputSchema: SchemaAdapter<Input>;
51
+ resolve(input: Input, context: Readonly<{ stageId: string }>): Output;
52
+ }
53
+ interface ModelSelection {
54
+ readonly capabilityId: string;
55
+ readonly input: unknown;
56
+ }
57
+ interface ModelTransportDefinition<Output> {
58
+ readonly id: string;
59
+ prepare(stageId: string): PreparedModelTransport<Output>;
60
+ }
61
+ ```
62
+
63
+ PreparedModelTransport<Output> is the unified transport preparation contract: options, schemaChars, optional instruction, and createResponse(). The returned collector has outputChars, push(part), and finish(): Output; the text collector accumulates and rejects function-call parts, and the structured collector returns a result only after full parsing. A collector is a new instance per call and does not reuse state across requests. PreparedModelInteraction is used for structured adapter composition, while text transports implement the generic collection contract directly.
64
+
65
+ ModelCapability uses inputSchema.parse to parse capability parameters and resolve(input, { stageId }) to produce a typed stage result. resolve runs synchronously; a mistakenly returned thenable is rejected, and it neither executes tools nor authorizes. ModelCapabilitySource.resolve(selection, context) first verifies the IDs available in this stage, then parses, converts, and runs the declared refine checks.
66
+
67
+ Core reads outputChars after the collector factory returns, after each push, and after finish: the value must be a non-negative safe integer, and NaN, Infinity, negative numbers, and fractions are rejected as protocol errors. maxOutputChars may be explicitly set to Infinity, but that does not relax the collector counting contract. Diagnostics keep the peak of each valid observation, and finish may release or normalize internal buffers; buffers are not required to grow indefinitely.
68
+
69
+ Native interaction accepts a string or a valid function-call-delta. A function part must be a non-array object with index 0; id, when provided, must be a non-empty string, and name and arguments, when provided, must be strings. Conflicting IDs, multiple calls, unregistered capabilities, mixed body text, or incomplete arguments are rejected, and no tool is executed.
70
+
71
+ Optional call metadata on the collector is read only once on a best-effort basis; a throwing getter does not overwrite an obtained business result, the original error, or cancellation, nor does it block the model.end wrap-up. outputChars is an execution-validated field and is exempt from this tolerance rule.
72
+
73
+ Plain-text and structured transports each provide their own constructor that returns an implementation satisfying the transport preparation contract. A prepared interaction collects the complete result and parses the selection; raw parts cannot become a tool receipt.
74
+
75
+ ### Optional request preparation and actual measurement
76
+
77
+ An ordinary `runner.invoke(input)` needs no preparation step. When an explicit context node must judge candidate input in advance, it can prepare a transport snapshot once:
78
+
79
+ ```ts
80
+ const prepared = runner.prepare({ stageId: 'reply', transport, maxOutputTokens: 1000 });
81
+ const measurement = prepared.measure(candidateMessages);
82
+ // 调整候选消息后可以重新 measure;不会重新 prepare 或消耗模型调用。
83
+ const result = await runner.invoke({ input: finalMessages, prepared });
84
+ ```
85
+
86
+ `context.model` provides the same prepare/invoke contract, and the handle can be kept in this Workflow's state for later nodes. With multiple models, a preparation request may specify modelId, and the final invoke locates the original model through the handle without passing it again; the processing model and the final model are still bounded by the same request budget.
87
+
88
+ Preparation fixes the instruction, Schema, options, and collector factory receiver of the current dynamic transport. Measurement covers the merged real messages, transport instruction, and Schema; with an explicit counter, the input token limit deducts this call's output reservation and safety margin. A handle for a registered model also keeps modelId, so selection or compression can explicitly reference another registered model while the final call still targets the originally prepared model. Without a counter no token estimate is produced. App body text is bounded by maxInputChars, while transport instructions and declarations are independently bounded by maxSchemaChars; budgets are not borrowed across them. If a JSON Schema is already embedded in the instruction, the actual total is not added twice.
89
+
90
+ Measurement returns `ModelInputMeasurement` with body messageChars, added instructionChars, out-of-message declaration schemaChars, transport budget usage transportChars, the actual total inputChars, the effective limit, and withinBudget. It is not a budget reservation or a pass: the final input is still measured and validated again before the Provider. A handle belongs only to the Runner/Workflow request that prepared it, can be consumed once, and cannot replace stageId, transport, or the output reservation. Cancellation, expiry, foreign handles, and reuse are rejected; a pre-check rejection still consumes no model calls.
91
+
92
+ The final call fixes a snapshot of message role, content, and images before the first asynchronous wait, and budgeting, token counting, and Provider sending share that snapshot; the caller modifying the original object afterwards does not rewrite the request. prepare fixes the set of capability IDs for this preparation, and capabilities registered later are available only to new preparations.
93
+
94
+ Character budgets accept only non-negative safe integers or Infinity; a budget carried by BuiltContext must pass the same validation and can only narrow the Runner upper limit. NaN, missing budgets, fractions, and other invalid values are rejected before billing and Provider calls, and measurement and actual execution use the same judgment.
95
+
96
+ ### Fixed invocation results
97
+
98
+ ```ts
99
+ interface ModelCallRecord extends InvocationMetadata {
100
+ readonly stageId?: string;
101
+ readonly modelId?: string;
102
+ readonly callSequence: number;
103
+ readonly startedAtMs: TimestampMs;
104
+ readonly status: 'success'; // 仅成功返回的invocation
105
+ readonly usage?: ModelUsage;
106
+ }
107
+ interface ToolCallRecord extends InvocationMetadata {
108
+ readonly toolId: string;
109
+ readonly startedAtMs: TimestampMs;
110
+ readonly status: 'success'; // 仅成功返回的invocation
111
+ }
112
+ ```
113
+
114
+ The invocation in a successful invoke return is always a success record; failure records go to events/diagnostics, and the failed call itself throws. Registered external models in ModelCalls set modelId, and Agent model stages set stageId; this does not change the result shape and does not require models to supply call metadata.
115
+
116
+ ### Provider and model output
117
+
118
+ ```ts
119
+ interface ChatProvider {
120
+ stream(
121
+ messages: readonly ModelMessage[],
122
+ context: ModelProviderContext,
123
+ ): AsyncIterable<ModelPart>;
124
+ }
125
+ interface ModelProviderContext {
126
+ readonly signal: AbortSignal;
127
+ readonly options: Readonly<ModelOptions>;
128
+ readonly diagnostics?: DiagnosticContext;
129
+ }
130
+ ```
131
+
132
+ ModelOptions provides provider-neutral fields such as json, temperature, functions, includeUsage, and maxOutputTokens. The usage receiver is an execution accounting port: it records actual usage before notifying the observer, and observer failure isolation does not affect the usage record.
133
+
134
+ The Provider contract only passes real call and transport parameters; it does not decide business authorization. The output token value on a request is called maxOutputTokens; the hard limit in connection configuration is called outputTokenLimit, and the two must not be confused with the default reservation. Provider wire fields such as max_tokens/tools continue to be converted by the adapter.
135
+
136
+ The model sink and process observation reuse the same CoreEvent envelope. The sink receives model.start, model.output, model.parsed, and model.end on success, failure, or cancellation; the payload is in payload, and the real invocationId isolates calls. model.parsed means the full model value passed parsing and still must wait for delivery and cancellation checks before commit; it is not the App's final reply. model.end uses a separate 250-millisecond wrap-up deadline and still attempts to notify preview withdrawal after cancellation; a failed notification does not overwrite a committed result or the original exception, and consumers must still handle connection loss themselves. Events are discriminated by type, stage references use stageId, and model ordinal uses callSequence (starting at 1). Previews remain transient, and a final value is returned only after complete collection, parsing, budget, and cancellation checks pass.
137
+
138
+ ## AgentCoreEngine and Workflow
139
+
140
+ ### Existing request model service
141
+
142
+ ```ts
143
+ const runner = new ModelRunner({ provider, maxCalls: 4, execution });
144
+ const agent = new AgentCoreEngine({ workflow }).bindModelRuntime(runner);
145
+ await agent.run(state);
146
+ ```
147
+
148
+ When bindModel configures a definition, each run builds an independent request Runner; when bindModelRuntime binds an existing request service, it reuses that service's existing counting, budget, cancellation, and observation scope, and later runs receive no extra budget. Nodes obtain the call parent and live counts automatically through context.model. Two requests must not run overlappingly on the same Engine; fork requires resume to explicitly provide the restored model, avoiding implicit sharing of run state. Structured implementations can also be attached, and the canonical invoke/prepare fix the original receiver at bind time; the service itself is neither cloned nor frozen.
149
+
150
+ ### Child execution and shared budget
151
+
152
+ ```ts
153
+ const child = parent.createChild({
154
+ id: 'app.analysis', maxCalls: 8, reserveCalls: 1, timeoutMs: 60000,
155
+ transports: specialistTransports, diagnostics: operation.diagnostics,
156
+ });
157
+ const engine = new AgentCoreEngine({ maxRounds: 8, execution: child.execution });
158
+ // 使用同一 Engine/Workflow,App 提供独立 state、app、工具与完成检查。
159
+ ```
160
+
161
+ `ModelChildOptions` are explicit child execution settings. A child runner inherits the Provider, per-call limits, token counter, and call observation ports; it does not inherit the parent conversation, journal, output sink, or transport list. When `transports` is omitted, the built-in plain-text transport is used; add specialized transports as needed. `execution` is a read-only signal/diagnostics pair that can be passed to the Engine and tool registrars. The child signal is bounded by both parent cancellation and the local deadline, and diagnostics use the single child scope of the same run and cannot be swapped for the observation parent of another run.
162
+
163
+ `maxCalls` is a local limit, and `reserveCalls` is budget left for ancestors. A call atomically deducts from the local and ancestor ledgers before provider I/O, and failures do not refund the attempt; pre-check rejections do not deduct. `remainingCalls` reflects local, total budget, and reservation limits together; `callCount` still counts only this instance, while `totalCallCount` includes child calls. Creating new instances does not expand the whole-request budget.
164
+
165
+ `children` configures `maxDepth`, `maxConcurrentCalls`, and `maxChildren` for this request family, defaulting to 1, 1, and 32. Depth starts at 0 for the root runner; the total creation count is not returned when subtasks finish. Configuration is fixed when the root is constructed, all descendants share capacity, and each level still keeps its own ancestor wrap-up budget. `ModelChildOptions.signal` can attach additional local cancellation, and parent cancellation propagates to all descendants.
166
+
167
+ ```ts
168
+ const parent = new ModelRunner({
169
+ provider, maxCalls: 12,
170
+ children: { maxDepth: 3, maxConcurrentCalls: 2, maxChildren: 16 },
171
+ execution,
172
+ });
173
+ ```
174
+
175
+ Context nodes share budget through the ordinary model port. The App supplies the role list, permission ports, and result contracts, organizes tasks with Workflow/handlers, and passes the child signal to real tools and wrap-up side effects. To compose bounded parallel tasks, use [Support.runChildren](advanced-agents.md#bounded-subtask-composition).
176
+
177
+ ```ts
178
+ const agent = new AgentCoreEngine({ workflow, app, tools, maxRounds: 8 });
179
+ const result = await agent.run(state);
180
+ ```
181
+
182
+ `defineWorkflow` compiles a definition. When the Workflow is known, it can be bound at construction, or bound once during assembly with `bindWorkflow`. A tool runtime instance can likewise be bound through the constructor parameter `tools`, or bound once during assembly with `bindToolRuntime`; both accept the same contract and cannot be bound repeatedly. For complete usage of nodes, routes, models, and tools, see [Workflow primer](workflow.md).
183
+
184
+ `maxRounds` bounds rounds and defaults to 8. The low-level callback loop is still available through `engine.run(step)`, whose callback receives the round and execution context and returns `StepOutcome`.
185
+
186
+ `run(step, { signal })` and Workflow's `run(state, { signal })` both combine single-run cancellation with the instance execution.signal and preserve the original cancellation reason. CoreStep calls without a bound Workflow do not accept modelId selection.
187
+
188
+ A self-orchestrated CoreStep callback should pass the context signal to internal asynchronous operations and check cancellation before side effects. Cancellation stops waiting for the current callback, and late results do not enter subsequent rounds; cancellation cannot forcibly terminate arbitrary JavaScript, nor does it treat an unconfirmed storage commit as rolled back. Apps or Kits holding a transaction or exclusive lock must wait for the already-started storage commit to confirm before releasing resources.
189
+
190
+ ```ts
191
+ type StepOutcome<Output> =
192
+ | { readonly type: 'continue' }
193
+ | { readonly type: 'complete'; readonly value: Output };
194
+ interface WorkflowContext<App> extends OperationContext<App> {
195
+ readonly roundIndex: number;
196
+ readonly error?: unknown;
197
+ }
198
+ interface WorkflowNode<State, Output, App> {
199
+ readonly id: string;
200
+ readonly description: string;
201
+ readonly startsRound?: boolean;
202
+ readonly requires?: readonly (keyof State & string)[];
203
+ readonly provides?: readonly (keyof State & string)[];
204
+ readonly onErrorNodeId?: string;
205
+ run?(state: Readonly<State>, context: WorkflowContext<App>): MaybePromise<Partial<State> | void>;
206
+ readonly routes: readonly WorkflowRoute<State, Output, App>[];
207
+ }
208
+ ```
209
+
210
+ run(step) uses StepOutcome and allows undefined as a legitimate completion value. Workflow routes distinguish jumps from completion explicitly through targetNodeId and complete:
211
+
212
+ ```ts
213
+ type WorkflowRoute<State, Output, App> =
214
+ | { readonly when?: WorkflowGuard<State, App>; readonly targetNodeId: string }
215
+ | { readonly when?: WorkflowGuard<State, App>; readonly complete: (state: Readonly<State>, context: WorkflowContext<App>) => Output };
216
+ ```
217
+
218
+ WorkflowGuard<State, App> is the synchronous `(state: Readonly<State>, context: WorkflowContext<App>) => boolean`; a mistakenly returned thenable is rejected. WorkflowDefinition contains id, entryNodeId, read-only nodes, and optional isResult; node references, reachability, and bounded loops are checked at define time. At execution, requires is checked first, then the handler runs, cancellation and provides are checked before the patch is committed, and finally the first matching route is taken. Cancellation and contract errors cannot be turned into business success by onError.
219
+
220
+ isResult only answers with a boolean; if a resumable business check is needed, the App calls a checker inside a workflow node. Workflow state remains separate from app dependencies.
221
+
222
+ ## ToolRegistry and ToolRuntime
223
+
224
+ The low-level ToolRegistry in Core can take hand-written ExecutableTool implementations; Support's ToolRuntime comes from typed tool catalogs. Both reuse the same real invocation mechanism.
225
+
226
+ ```ts
227
+ interface ExecutableTool {
228
+ readonly id: string;
229
+ readonly kind: string;
230
+ parseInput(input: unknown): unknown;
231
+ execute(input: unknown, context: ToolExecutionContext): unknown;
232
+ parseOutput(output: unknown): unknown;
233
+ }
234
+ new ToolRegistry({ execution?, errors? })
235
+ registry.register(definition): this
236
+ registry.registerAll(definitions): this
237
+ registry.seal(): this
238
+ registry.invoke({ toolId, input }): ToolResult<unknown> // 同步,拒绝thenable
239
+ registry.invokeAsync({ toolId, input }): Promise<ToolResult<unknown>>
240
+ ```
241
+
242
+ The low-level value stays unknown, and the call result still uses the fixed InvocationResult; there is no "type validation" in which the caller self-reports Output. Type inference comes from Support catalogs. The registry implements the shared Catalog surface: get returns undefined for a missing entry, and require throws.
243
+
244
+ The pipeline is fixed: parse input → registered execution/authorization adapter → await the actual result → parse output → cancellation check → record completion. The low-level execution contract does not require every tool to carry extra business authorization fields; real rules are supplied by the App or by handlers adapted through Support.
245
+
246
+ The ToolCallRecord in a successful return always has status=success; a failed call throws. ToolExecutionEvent and ModelCallTrace in read-only events distinguish success/error/cancelled and carry the same InvocationMetadata; business check conclusions are recorded separately by the App and do not overwrite call status.
247
+
248
+ ## Journal and diagnostics
249
+
250
+ [Requests, call chains, events, and Journal](observability.md) defines the complete correlation and storage contracts: per-event records and explicit parent-child keys, where Journal is the run projection of the same execution facts and does not build a second accounting system.
251
+
252
+ ```ts
253
+ journal.model({ stageId, value, invocation }): void
254
+ journal.beginTool({ toolId, input, invocation? }): string // 返回同一invocationId
255
+ journal.finishTool({ invocationId, status, value }): void // success | error | cancelled
256
+ journal.snapshot(): readonly ContextRecord[]
257
+ createDiagnostics({ output?, runId?, spanId? }): DiagnosticContext
258
+ ```
259
+
260
+ invocationId is assigned by the real tool call boundary, and Journal uses the same identity. Cross-run correlation must combine runId; App requestId is correlated separately by the App. A nonexistent call or a duplicate finish is rejected. One real execution nesting Tools Kit/Support/Core allocates only one invocationId, passed down the execution context; executeInvocation and its Journal share the invocationId of that boundary. A genuinely nested tool execution is another child call with an independent ID, correlated to the parent call through parentInvocationId. IDs remain unique across instances.
261
+
262
+ Low-level execution callbacks and business bindings both return the original business value, and only the public invoke boundary wraps it once; internal compression subcalls use result.value and must not hand the whole envelope to a parser. durationMs covers preparation, execution, parsing, and delivery waiting for the current call, and startedAtMs is recorded when the corresponding boundary starts; callSequence is allocated only to model calls that are actually issued, and pre-check rejections go to rejected diagnostics without fabricating provider calls.
263
+
264
+ ContextRecord uses type discrimination, producerSequence (starting at 1), stageId/toolId/invocationId, and value. Tool call status is success, error, or cancelled. Tool and workflow diagnostic payloads use known fields and the WorkflowEvent type; model-generated values and App exceptions may be unknown.
265
+
266
+ The Core fact envelope uses version, eventId, type, occurredAtMs, runId, spanId, parentSpanId, optional invocationId, and payload. Cross-source storage sequence is assigned uniformly by the App run collector, while Core local ordinals use producerSequence. Core, Provider, and Kit each define their own event catalogs.
267
+
268
+ For complete exports, exact overloads, and declaration sources, see [Public symbol reference](reference.md). Signatures in examples are for reading only; omitted fields cannot be used to infer arbitrary extension options.
269
+
270
+ ### Boundaries of observation and budget
271
+
272
+ ModelCallTrace contains the required invocationId, startedAtMs, durationMs, callSequence, and stageId; status is success/error/cancelled. Call results, traces, and diagnostics use the same call identity. `model.end` reports only accepted attempts; input/budget pre-check rejections go to runtime.rejected and do not fabricate output when no provider I/O was initiated. An accepted attempt whose collector factory fails still wraps up as error and retains the consumed attempt count.
273
+
274
+ ModelRunner defaults and error priority are defined by modelRunnerDefaults and the executor; the original BudgetError.code and getErrorInfo.code of a budget error are both BUDGET, and the App can map them to a more specific business message in its own presentation layer. Timeout and cancellation preserve the original exception identity. CallTrace measurement covers preparation, parsing, and delivery waiting for that call; child calls share the total budget, and duration is not an additive cost.
@@ -0,0 +1,118 @@
1
+ # Getting Started from the Same Contract Set
2
+
3
+ [Back to home](README.md). Running the examples requires the App to supply the provider, business storage, and authentication configuration.
4
+
5
+ ## One Output Shape, Two Input Forms
6
+
7
+ ```ts
8
+ const runner = new ModelRunner({ provider });
9
+
10
+ const a = await runner.invoke('你好');
11
+ const b = await runner.invoke({ input: '你好' });
12
+
13
+ // 两者都是ModelResult<string>。
14
+ console.log(a.value);
15
+ console.log(b.value);
16
+ console.log(a.invocation.durationMs);
17
+ ```
18
+
19
+ The short form is only equivalent to `{ input: '你好' }`. No path returns a string directly, and there is no raw/fullResponse option to switch the return structure. A structured transport only makes value a parsed object; the outer layer is still a ModelResult.
20
+
21
+ ## Single-Source Tool Declaration, Model Selection, and Real Execution
22
+
23
+ ```ts
24
+ import { ModelRunner, Support } from '@jangts/agent-core';
25
+ import type { OperationContext } from '@jangts/agent-core';
26
+
27
+ interface ReadNote { noteId: string }
28
+ interface Note { title: string; body: string }
29
+ interface App {
30
+ visibleNoteIds: ReadonlySet<string>;
31
+ notes: { read(id: string, signal: AbortSignal): Promise<Note> };
32
+ }
33
+
34
+ const inputSchema = Support.defineSchema<ReadNote>({
35
+ jsonSchema: {
36
+ type: 'object', required: ['noteId'], additionalProperties: false,
37
+ properties: { noteId: { type: 'string', minLength: 1 } },
38
+ },
39
+ parse(value: unknown): ReadNote {
40
+ if (!value || typeof value !== 'object' || !('noteId' in value)
41
+ || typeof value.noteId !== 'string' || !value.noteId.trim()) {
42
+ throw new TypeError('noteId is required');
43
+ }
44
+ return { noteId: value.noteId };
45
+ },
46
+ });
47
+
48
+ const readNote = Support.defineTool({
49
+ id: 'note-read', kind: 'read', description: '读取当前用户可见的笔记。',
50
+ inputSchema,
51
+ authorize(input: ReadNote, context: OperationContext<App>) {
52
+ if (!context.app.visibleNoteIds.has(input.noteId)) throw new Error('Access denied');
53
+ },
54
+ execute(input: ReadNote, context: OperationContext<App>) {
55
+ return context.app.notes.read(input.noteId, context.signal);
56
+ },
57
+ parseOutput(value: unknown): Note {
58
+ if (!value || typeof value !== 'object'
59
+ || !('title' in value) || typeof value.title !== 'string'
60
+ || !('body' in value) || typeof value.body !== 'string') {
61
+ throw new TypeError('Invalid note');
62
+ }
63
+ return { title: value.title, body: value.body };
64
+ },
65
+ });
66
+
67
+ const catalog = Support.defineToolCatalog([readNote]);
68
+ const transport = Support.createModelTransport({
69
+ id: 'note-selection', capabilities: catalog.capabilities,
70
+ });
71
+ ```
72
+
73
+ A definition does not close over this user, signal, or budget; the same catalog can serve multiple requests. Binding happens only after entering a request:
74
+
75
+ ```ts
76
+ const execution = { signal: requestSignal };
77
+ const tools = catalog.bind({ app: authenticatedApp, execution });
78
+ const runner = new ModelRunner({
79
+ provider, transports: [transport] as const, execution, maxCalls: 2,
80
+ });
81
+
82
+ const selected = await runner.invoke({
83
+ stageId: 'choose-note', transport: 'note-selection',
84
+ input: '读取刚才那份笔记。',
85
+ });
86
+ const executed = await tools.invoke({
87
+ toolId: selected.value.toolId,
88
+ input: selected.value.input,
89
+ });
90
+
91
+ // 同一外层形状,不同业务值。模型提议不是执行回执。
92
+ const proposal = selected.value;
93
+ const actualNote = executed.value;
94
+ const actualInvocationId = executed.invocation.invocationId;
95
+ ```
96
+
97
+ The visible set is trusted server-side context, and real storage must still check ownership and resource lifecycle again. The schema and model selection grant no permission; authorize returning false is not part of the target contract.
98
+
99
+ ## Reading Knowledge with the Collection Methods You Already Know
100
+
101
+ ```ts
102
+ import { defineKnowledgeCatalog } from '@jangts/agent-core/kits/knowledge';
103
+
104
+ const knowledge = defineKnowledgeCatalog([
105
+ { id: 'manual', revision: 'r1', parts: ['已维护的资料。'] },
106
+ ]);
107
+
108
+ const optional = knowledge.get('missing'); // undefined
109
+ const required = knowledge.require('manual'); // 必须存在
110
+ const snapshot = knowledge.read({
111
+ documentId: required.id,
112
+ selection: { mode: 'document' },
113
+ });
114
+ ```
115
+
116
+ read is a read with an explicit content model and returns a KnowledgeSnapshot; it is not another output mode of model invoke. The same shape is required only for the same method with the same responsibility, so not every scalar, collection, and snapshot is called a Response.
117
+
118
+ The calls above can be composed into the same Workflow; the model only proposes a structured selection, and the registered implementation performs the actual tool authorization, execution, and result checking.
@@ -0,0 +1,183 @@
1
+ # Other optional Kits
2
+
3
+ [Shared types](types.md) · [Back to home](README.md). Each Kit is imported by named function/constructor from its own subpath, with static declarations separated from the per-run context.
4
+
5
+ ## Intents, Interaction, Tools
6
+
7
+ | Capability | Preferred interface/key contract |
8
+ | --- | --- |
9
+ | IntentRegistry | Defines the primary key id, uses scopePolicy/targetPolicy, implements the shared Registry contract |
10
+ | ScopeRegistry | id, intentIds, toolIds, queryScopeIds, knowledgeTopicIds; aliases are retained, and query methods use scopeId |
11
+ | defineAgentCatalog | Projects relationships from actual registrations; the current task is `{ intentId, scopeId? }`, and scope cannot be used for both policy and reference |
12
+ | defineInteractionProtocol | One commands declaration compiles the protocol; commandField is owned by the App, which is not forced to name its wire field type or kind |
13
+ | defineCommandCatalog | The closed commands set may be written as a Record; the public definitions are an array, and toRecord() is the explicit mapping |
14
+ | bindInteraction | Aligns protocol with named handlers; dispatch(input, context) never executes unregistered commands |
15
+ | ToolLifecycleRegistry | Actual execution delegates to Core tools; assertDecision checks decisions, authorize returns void on approval and throws on rejection |
16
+
17
+ Registrar declarations and query results use the same set of fields. ID lists use ids(), naming rules use idPattern, and custom assertions use assertDefinition. Scope aliases are business-name references resolved by normalize.
18
+
19
+ When the complete list is available at construction time, use IntentRegistry.create(definitions, policy) or ScopeRegistry.create(definitions, policy) to build and seal the catalog at once. When staged assembly is needed, use new Registry(policy).registerAll(definitions).seal(); both follow the same registration contract.
20
+
21
+ InteractionProtocol and CommandCatalog are public constructors; Interaction and Interaction.Commands provide their namespace entries respectively.
22
+
23
+ The Tools Kit preserves the real order: global check → selected check → authorization → resume/execute → completion → finalize. Lifecycle and contribution are local protocols of this Kit. The receiver field is called receiver and is not conflated with OutputField.owner; the in-request journal reuses the invocationId allocated by Core.
24
+
25
+ ## Evidence and Retrieval
26
+
27
+ ```ts
28
+ defineEvidenceChecklist(providers): EvidenceChecklist
29
+ checklist.isSatisfied({ observations, requirement }): boolean
30
+ checklist.missing({ observations, requirements }): readonly EvidenceRequirement[]
31
+ checklist.isComplete({ observations, requirements }): boolean
32
+
33
+ defineEvidenceProjection(definition): EvidenceProjection
34
+ projection.project({ observations, sourceIds }): readonly Observation[]
35
+
36
+ defineRetrieval(definition): Retrieval
37
+ retrieval.run(input, context): RetrievalReceipt
38
+ ```
39
+
40
+ EvidenceRequirement describes a requirement, not an existing resource; it cannot be merged with ArtifactReference permissions just because both contain an ID. Projection keeps the current evidence boundary for no selection, unknown selection, and complete candidates.
41
+
42
+ Retrieval definitions use assertInput, authorize, execute, assertResult, and named effects. RetrievalSource.sourceId is the reference identifier for this request and may coexist with the material entity's own id; it is not another spelling of an entity primary key. Receipt uses startedAtMs, and retrieval counts use queryCount. Definitions must not bind request state; state/budget come from this run's context.app, and errors.duplicate/budget declare rejection reasons centrally. Synchronous runs stay synchronous, and an accidental Promise return is explicitly rejected.
43
+
44
+ Retrieval provides run(input, OperationContext); assertInput in the definition is a required assertion, result assertions use assertResult, and error factories live in errors.duplicate/errors.budget. limit and queryCount must be non-negative safe integers, and a quota of 0 does not start any read. Deduplication takes priority over budget; a rejected authorization makes no reservation, and a failed read retains the seen key. Cancellation is checked again before submitting evidence after source binding completes; once submitted, effects run in order, and cancellation or failure stops subsequent items without fabricating a rollback.
45
+
46
+ ## Policies, Normalization, Delivery, Candidates
47
+
48
+ | Kit | Preferred creation and execution | Termination/error semantics |
49
+ | --- | --- | --- |
50
+ | Policies | definePolicySet; assess(input) | Reports all matching reasons, not just the first hit |
51
+ | Recovery | defineRecoveryChain; tryRecover(input) | The first explicit takeover; errors must not be swallowed accidentally; use an explicit handled flag when the final value may be undefined |
52
+ | Normalization | defineNormalization; normalize(input, context) | Sequential transformation, when conditions, and isComplete decisions; preserves 0/false/empty string |
53
+ | Delivery | defineDelivery; deliver(input, context) | Stage hooks interleaved with handlers; explicit continue/complete, supports legitimate undefined final values |
54
+ | Candidates | defineCandidateSelection; parse({ value, allowed }) | minCandidates/maxCandidates; order and count are constrained by real declarations |
55
+
56
+ In candidate parsing, value is the value to parse and allowed indicates whether this task permits a candidate envelope. maxCandidates must be configured explicitly, and minCandidates defaults to 1 when omitted; an ordinary single value still returns a single-element array, new candidates cannot be submitted after the task has taken over, and candidates cannot be nested.
57
+
58
+ Delivery stages use id; beforeStage receives { stageId, state } and OperationContext, and handle receives state and the same context. deliver's second argument provides the real signal and optional diagnostics, and cancellation is checked on entering a stage and before and after each handler; synchronous hooks or handlers do not accept Promises. ContentProjection uses named requests, and TreeProjection uses visit traversal.
59
+
60
+ Each policy definition uses id, description, when, and a named handler. An ordinary single condition does not need to become a stage class; sequential pipelines, first-match, merging, and rejection checks remain distinct flows.
61
+
62
+ ## Projection, Aggregation, TextSkills
63
+
64
+ | Kit | Shared contract |
65
+ | --- | --- |
66
+ | ContentProjection | defineContentProjection; project({ value, maxChars }) returns `{ text, truncated }`; fallback text must also satisfy the budget, and is rejected if it cannot; data cannot be fabricated |
67
+ | TreeProjection | defineTreeProjection; visit(input, context), with explicit synchronous semantics for maxDepth and omit |
68
+ | QueryAggregation | defineQueryAggregation; collect(inputs, context), preserving serial order, deduplication keys, overrides, and counting basis |
69
+ | TextSkills | defineTextSkillLoader; load(input, context), with real file reads provided by an App port |
70
+
71
+ A TextSkill definition uses id, entry, toolIds, and kind=text-workflow. Catalog entry structure is separated from body description, and IDs and tool references come from the same registration source.
72
+
73
+ TextSkillLoader accepts load({ entries }, { read }). Registration ID, path, tool reference, and duplicate checks precede reading the corresponding file, and both read and custom parsers must be synchronous. The read port, registration entries, and error factory may be implemented by a class, and prototype getters and original method receivers are preserved. App-owned fields in tool receipts are projected explicitly by the App.
74
+
75
+ ## TextSearch, VectorSearch, RRF, ModelCalls
76
+
77
+ ```ts
78
+ interface SearchHit<Document> {
79
+ readonly id: string;
80
+ readonly score: number;
81
+ readonly document: Readonly<Document>;
82
+ }
83
+ new TextSearch({ indexRevision, fields, storedFields, ...options })
84
+ new VectorSearch({ identity, dimensions })
85
+ textSearch.search({ query, limit, filter }): readonly TextSearchHit<Document>[]
86
+ vectorSearch.search({ vector, limit, filter, minScore?, groupBy? }): readonly VectorSearchHit<Document>[]
87
+ vectorSearch.upsert({ document, vector }): void
88
+ reciprocalRankFusion(lists, options): readonly FusedRank[]
89
+ ```
90
+
91
+ TextSearch's payload is still a Partial<Document> of the declared stored fields, while VectorSearch may return full documents; the unified document field does not mean full-text data has been read. Extra terms/contributions extend each algorithm. The three scores are not the same confidence, and RRF cannot mix raw scores directly.
92
+
93
+ TextSearch copies only the declared index and stored fields; input originals, filter callbacks, and returned results do not share nested metadata. VectorSearch's filter and grouping callbacks each receive an independent document copy; modifying these copies does not rewrite the index or affect the other callback. Index metadata must be structuredClone-able, and vectors must supply a numeric value for every dimension; sparse arrays are rejected.
94
+
95
+ TextSearch.snapshot() returns version=2, engine, configurationFingerprint, and serializedIndex; restore accepts version=2. Both the fingerprint and public constructor parameters use indexRevision/storedFields. remove waits for index vacuum before returning, ensuring deleted content does not remain in the next serialization.
96
+
97
+ ```ts
98
+ new ModelCalls(bindings)
99
+ models.invoke({ modelId, input, timeoutMs }, context): Promise<ModelResult<Output>>
100
+ ```
101
+
102
+ Bindings use id, identity, invoke, assertInput/assertOutput. Binding callbacks return business values, and the ModelCalls public boundary wraps them as `{ value, invocation }`. id is the registration key and identity is the actual model identity; context.signal and timeoutMs together constrain external I/O. Heterogeneous models infer I/O from the registration ID, while dynamic IDs stay unknown.
103
+
104
+ After input validation passes, ModelCalls hands over to invoke in the current call stack without queueing an extra microtask. Arbitrary App inputs may retain class instances and prototypes; if a handler uses mutable data across an await, that handler must explicitly snapshot the required fields.
105
+
106
+ ```ts
107
+ const attemptBudget = new AttemptBudget(2);
108
+ await models.invoke({ modelId, input, timeoutMs: 1000 }, { signal, attemptBudget });
109
+ ```
110
+
111
+ attemptBudget is the optional call-attempt port for the current request and may directly use Core's AttemptBudget. Resolution/pre-cancellation does not consume quota; an actually accepted attempt atomically takes one before I/O and is not refunded on failure. A batch call still counts as one, while vector entries, tokens, and chat call counts are defined and metered by the App; without a budget passed in, one must not claim that external inference is subject to a unified quota. Reusing the model catalog does not automatically create a business quota for user Q&A. Upstream and downstream bindings may pass the same budget port; Core does not build in providers, model roles, or cross-business total quotas.
112
+
113
+ ## Artifacts
114
+
115
+ ```ts
116
+ interface ArtifactReference {
117
+ readonly resolverId: string;
118
+ readonly artifactId: string;
119
+ readonly revision?: string;
120
+ }
121
+ interface ArtifactResolver<Output, App> {
122
+ readonly id: string;
123
+ resolve(reference: ArtifactReference, context: OperationContext<App>): MaybePromise<Output>;
124
+ }
125
+ defineArtifactCatalog(resolvers): ArtifactCatalog
126
+ catalog.resolve(reference, context): Promise<Output>
127
+ ```
128
+
129
+ resolverId points to the registered resolver and artifactId points to the resource; the two do not reuse the ambiguous id/kind. The Resolver is responsible for validating real accounts, existence, revision, and lifecycle; additional URL/path fields do not select the actual resource. Cancellation interrupts waiting and consumes late rejections, but does not prove that external reads have stopped.
130
+
131
+ The execution entry accepts ArtifactReference and OperationContext. Implementations may carry their own extra members, while execution reads the fields defined by the interface.
132
+
133
+ ## Durable
134
+
135
+ ```ts
136
+ defineDurableTask(definition, options?): DurableTask
137
+ interface DurableTaskDefinition<State, App> {
138
+ readonly id: string;
139
+ readonly revision: string;
140
+ readonly steps: readonly DurableStep<State, App>[];
141
+ isState(input: unknown): input is State;
142
+ authorize?(checkpoint, context): void | Promise<void>;
143
+ }
144
+ task.run({ taskId, store }, context): Promise<State>
145
+ ```
146
+
147
+ Steps still have id, replayPolicy, run, and optional reconcile; handlers take state first and OperationContext second. The App provides store exclusive access, load/save, user ownership, retention, and serialization validation; no SDK default database or automatic scheduling is added.
148
+
149
+ Checkpoint v2 uses definitionId, revision, nextStepIndex, attemptCount, maxAttempts, deadlineAtMs, status, state. status is a Kit state and must not become a required field for all Core applications.
150
+
151
+ Save the attempt and running before execution; safe steps interrupted mid-way may be safely re-run with the App's guarantee, while reconcile steps only go through reconciliation and are rejected when no reconciliation implementation exists. Recovery does not reset counts or deadlines; after a handler returns a copy of the state, check signal/deadline/shape first, then save the confirmation. Cancellation during a save cannot pretend the write was withdrawn.
152
+
153
+ The DurableStore interface includes exclusive(taskId, operation), load(taskId), save(taskId, checkpoint). load/save use version=2; before execution, check definitionId/revision, state, index, count, and deadline. Unknown versions are rejected and do not fall back to a new task. A resumed task does not gain extra budget or authorization.
154
+
155
+ Durable validates state with isState, decides replay with replayPolicy, and executes via run({ taskId, store }, OperationContext). Cancellation or deadline is checked when entering exclusive operations, after reading, after state validation and cloning, and before and after each save; saves always wait inside the lock, and cancellation races cannot pretend to revoke an already committed write. Handlers receive the diagnostics of the current Loop sub-scope.
156
+
157
+ Full exports, exact reloads, and declaration sources are in the [public symbol reference](reference.md). Signatures in the examples are for reading only; omitted fields do not imply arbitrary extra options.
158
+
159
+ ## Intentional differences of local protocols and pure algorithms
160
+
161
+ PolicySet/RecoveryChain provide definitions/ids/values/entries/has/get/require and operate directly on caller input. Pure predicates/recovery chains do not need an execution signal; the second Context of Normalization, TreeProjection, and Aggregation is the algorithm context declared by the caller and has no external execution lifecycle. Reads, tool execution, and durable tasks use OperationContext.
162
+
163
+ Interaction protocol receivers and handlers both plug in as interfaces, so standalone objects or class instances need no conversion to plain objects. bindInteraction fixes the command handling function and the original receiver at binding time; private state and prototype methods remain effective. Selection errors and envelope callbacks provided by the protocol class also preserve the original receiver.
164
+
165
+ Interaction's ProtocolField uses jsonSchema; a compiled command exposes inputJsonSchema (complete required fields), modelJsonSchema (the projection the model may submit), and fieldSchemas (per-field descriptions), while assert performs assertions and parse performs conversion. when must be a synchronous boolean; occur is a synchronous rejection predicate or an OR array of predicates. refine returns void and format returns the converted value; all callbacks fix the original method and original receiver.
166
+
167
+ ToolLifecycle's composition selects a structured template provider and preserves its existing falsey-rejection semantics without treating it as an arbitrary generic final value; control protocols in Delivery, Recovery, and AnswerFlow that may legitimately return undefined must be discriminated explicitly. Other synchronous hooks reject thenables, and authorize/inspect must return void. Bound execution signal and diagnostics are passed down through the real call context.
168
+
169
+ Every RRF input ranking and contribution detail uses sourceId. The filter in Text/VectorSearch is provided by the App and must return a boolean synchronously. VectorSearch.upsert uses { document, vector }, and search uses named requests. Both hits use document, with score semantics being lexical weight and cosine similarity respectively; RRF only fuses ranks and cannot compare their scores directly.
170
+
171
+ ModelCalls bindings use assertInput/assertOutput to check input and output. timeoutMs must be a safe integer from 1 to 2147483647, and illegal values are rejected before the call.
172
+
173
+ DurableTask's second construction options may bind store and now; run's named request may provide a store for this run. `authorize` checks the current identity, source revision, and authorization on every resume and before returning a completed result.
174
+
175
+ A Checkpoint may contain `modelBudget: { maxCalls, reservedCalls, maxCallsPerAttempt }`. Before each execution, persist the reservation for the whole run, then hand it to the handler's `maxModelCalls`; the App uses it to constrain the real runner. Interrupted or unused reservations are not refunded, so recovery after a crash cannot reset the accumulated quota. State predicates are synchronous booleans, and steps have explicit replayPolicy; clock, cancellation during save, and reconciliation follow the same lifecycle. See [Durable tasks](advanced-agents.md#durable-professional-tasks) for a complete example.
176
+
177
+ ## Reflection, Family, and knowledge publishing
178
+
179
+ [Reflection, branching, and material publishing](advanced-agents.md) introduces the configuration and use of `defineReflection`, `defineAgentFamily`, and `Knowledge.defineKnowledgePublication`. They are optional Kits for the App, while identity, real storage, and publishing decisions are provided by the App.
180
+
181
+ ## MockGPT
182
+
183
+ The simulated model Kit is used from `@jangts/agent-core/mock`; Node service and web source are provided by `/mock/node` and `/mock/web` respectively. It can generate JSON values directly and also test a model client's HTTP/SSE and failure handling. See [MockGPT API](mock.md) for complete input, returns, budget, and TS/JS examples.