digital-tools 2.1.1 → 2.3.0
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/CHANGELOG.md +17 -0
- package/README.md +2 -0
- package/dist/client.d.ts +109 -0
- package/dist/client.d.ts.map +1 -0
- package/dist/client.js +69 -0
- package/dist/client.js.map +1 -0
- package/dist/define.d.ts +2 -2
- package/dist/define.d.ts.map +1 -1
- package/dist/define.js +22 -20
- package/dist/define.js.map +1 -1
- package/dist/function-ref.d.ts +229 -0
- package/dist/function-ref.d.ts.map +1 -0
- package/dist/function-ref.js +28 -0
- package/dist/function-ref.js.map +1 -0
- package/dist/function-sugar.d.ts +57 -0
- package/dist/function-sugar.d.ts.map +1 -0
- package/dist/function-sugar.js +79 -0
- package/dist/function-sugar.js.map +1 -0
- package/dist/index.d.ts +10 -3
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +24 -4
- package/dist/index.js.map +1 -1
- package/dist/providers/analytics/mixpanel.d.ts.map +1 -1
- package/dist/providers/analytics/mixpanel.js +21 -18
- package/dist/providers/analytics/mixpanel.js.map +1 -1
- package/dist/providers/calendar/cal-com.d.ts.map +1 -1
- package/dist/providers/calendar/cal-com.js +10 -10
- package/dist/providers/calendar/cal-com.js.map +1 -1
- package/dist/providers/calendar/google-calendar.d.ts.map +1 -1
- package/dist/providers/calendar/google-calendar.js +4 -4
- package/dist/providers/calendar/google-calendar.js.map +1 -1
- package/dist/providers/crm/hubspot.d.ts.map +1 -1
- package/dist/providers/crm/hubspot.js +107 -85
- package/dist/providers/crm/hubspot.js.map +1 -1
- package/dist/providers/development/github.d.ts.map +1 -1
- package/dist/providers/development/github.js +40 -43
- package/dist/providers/development/github.js.map +1 -1
- package/dist/providers/ecommerce/shopify.d.ts.map +1 -1
- package/dist/providers/ecommerce/shopify.js +79 -62
- package/dist/providers/ecommerce/shopify.js.map +1 -1
- package/dist/providers/email/resend.d.ts.map +1 -1
- package/dist/providers/email/resend.js +20 -16
- package/dist/providers/email/resend.js.map +1 -1
- package/dist/providers/email/sendgrid.d.ts.map +1 -1
- package/dist/providers/email/sendgrid.js +12 -9
- package/dist/providers/email/sendgrid.js.map +1 -1
- package/dist/providers/finance/stripe.d.ts.map +1 -1
- package/dist/providers/finance/stripe.js +44 -42
- package/dist/providers/finance/stripe.js.map +1 -1
- package/dist/providers/forms/typeform.d.ts.map +1 -1
- package/dist/providers/forms/typeform.js +68 -58
- package/dist/providers/forms/typeform.js.map +1 -1
- package/dist/providers/knowledge/notion.d.ts.map +1 -1
- package/dist/providers/knowledge/notion.js +75 -41
- package/dist/providers/knowledge/notion.js.map +1 -1
- package/dist/providers/marketing/mailchimp.d.ts.map +1 -1
- package/dist/providers/marketing/mailchimp.js +74 -61
- package/dist/providers/marketing/mailchimp.js.map +1 -1
- package/dist/providers/media/cloudinary.d.ts.map +1 -1
- package/dist/providers/media/cloudinary.js +30 -28
- package/dist/providers/media/cloudinary.js.map +1 -1
- package/dist/providers/messaging/slack.d.ts.map +1 -1
- package/dist/providers/messaging/slack.js +75 -58
- package/dist/providers/messaging/slack.js.map +1 -1
- package/dist/providers/messaging/twilio-sms.d.ts.map +1 -1
- package/dist/providers/messaging/twilio-sms.js +33 -15
- package/dist/providers/messaging/twilio-sms.js.map +1 -1
- package/dist/providers/project-management/linear.d.ts.map +1 -1
- package/dist/providers/project-management/linear.js +31 -27
- package/dist/providers/project-management/linear.js.map +1 -1
- package/dist/providers/spreadsheet/google-sheets.d.ts.map +1 -1
- package/dist/providers/spreadsheet/google-sheets.js +21 -18
- package/dist/providers/spreadsheet/google-sheets.js.map +1 -1
- package/dist/providers/spreadsheet/xlsx.d.ts.map +1 -1
- package/dist/providers/spreadsheet/xlsx.js +4 -4
- package/dist/providers/spreadsheet/xlsx.js.map +1 -1
- package/dist/providers/storage/index.js +1 -0
- package/dist/providers/storage/index.js.map +1 -1
- package/dist/providers/storage/s3.d.ts.map +1 -1
- package/dist/providers/storage/s3.js +36 -27
- package/dist/providers/storage/s3.js.map +1 -1
- package/dist/providers/support/zendesk.d.ts.map +1 -1
- package/dist/providers/support/zendesk.js +24 -25
- package/dist/providers/support/zendesk.js.map +1 -1
- package/dist/providers/tasks/todoist.d.ts.map +1 -1
- package/dist/providers/tasks/todoist.js +18 -18
- package/dist/providers/tasks/todoist.js.map +1 -1
- package/dist/providers/video-conferencing/google-meet.d.ts.map +1 -1
- package/dist/providers/video-conferencing/google-meet.js +11 -11
- package/dist/providers/video-conferencing/google-meet.js.map +1 -1
- package/dist/providers/video-conferencing/jitsi.js +14 -14
- package/dist/providers/video-conferencing/jitsi.js.map +1 -1
- package/dist/providers/video-conferencing/teams.d.ts.map +1 -1
- package/dist/providers/video-conferencing/teams.js +9 -7
- package/dist/providers/video-conferencing/teams.js.map +1 -1
- package/dist/providers/video-conferencing/zoom.d.ts.map +1 -1
- package/dist/providers/video-conferencing/zoom.js +26 -24
- package/dist/providers/video-conferencing/zoom.js.map +1 -1
- package/dist/tools/data.d.ts.map +1 -1
- package/dist/tools/data.js +5 -12
- package/dist/tools/data.js.map +1 -1
- package/dist/tools/index.d.ts +1 -0
- package/dist/tools/index.d.ts.map +1 -1
- package/dist/tools/index.js +1 -0
- package/dist/tools/index.js.map +1 -1
- package/dist/tools/system.d.ts +289 -0
- package/dist/tools/system.d.ts.map +1 -0
- package/dist/tools/system.js +752 -0
- package/dist/tools/system.js.map +1 -0
- package/dist/tools/web.d.ts.map +1 -1
- package/dist/tools/web.js +22 -10
- package/dist/tools/web.js.map +1 -1
- package/dist/track-record.d.ts +101 -0
- package/dist/track-record.d.ts.map +1 -0
- package/dist/track-record.js +17 -0
- package/dist/track-record.js.map +1 -0
- package/dist/types.d.ts +210 -9
- package/dist/types.d.ts.map +1 -1
- package/dist/verb-registration.d.ts +122 -0
- package/dist/verb-registration.d.ts.map +1 -0
- package/dist/verb-registration.js +176 -0
- package/dist/verb-registration.js.map +1 -0
- package/dist/worker.d.ts +93 -0
- package/dist/worker.d.ts.map +1 -0
- package/dist/worker.js +315 -0
- package/dist/worker.js.map +1 -0
- package/dist/wrap.d.ts +89 -0
- package/dist/wrap.d.ts.map +1 -0
- package/dist/wrap.js +225 -0
- package/dist/wrap.js.map +1 -0
- package/package.json +21 -4
- package/src/client.ts +136 -0
- package/src/define.ts +31 -37
- package/src/function-ref.ts +264 -0
- package/src/function-sugar.ts +134 -0
- package/src/index.ts +132 -10
- package/src/providers/analytics/mixpanel.ts +19 -18
- package/src/providers/calendar/cal-com.ts +29 -18
- package/src/providers/calendar/google-calendar.ts +20 -14
- package/src/providers/crm/hubspot.ts +225 -99
- package/src/providers/development/github.ts +206 -135
- package/src/providers/ecommerce/shopify.ts +250 -89
- package/src/providers/email/resend.ts +101 -28
- package/src/providers/email/sendgrid.ts +12 -9
- package/src/providers/finance/stripe.ts +128 -49
- package/src/providers/forms/typeform.ts +74 -58
- package/src/providers/knowledge/notion.ts +340 -88
- package/src/providers/marketing/mailchimp.ts +86 -70
- package/src/providers/media/cloudinary.ts +99 -41
- package/src/providers/messaging/slack.ts +283 -85
- package/src/providers/messaging/twilio-sms.ts +35 -15
- package/src/providers/project-management/linear.ts +143 -55
- package/src/providers/spreadsheet/google-sheets.ts +222 -56
- package/src/providers/spreadsheet/xlsx.ts +47 -16
- package/src/providers/storage/s3.ts +119 -47
- package/src/providers/support/zendesk.ts +196 -46
- package/src/providers/tasks/todoist.ts +20 -26
- package/src/providers/video-conferencing/google-meet.ts +17 -20
- package/src/providers/video-conferencing/jitsi.ts +14 -14
- package/src/providers/video-conferencing/teams.ts +14 -13
- package/src/providers/video-conferencing/zoom.ts +54 -49
- package/src/tools/data.ts +6 -16
- package/src/tools/index.ts +1 -0
- package/src/tools/system.ts +887 -0
- package/src/tools/web.ts +22 -10
- package/src/track-record.ts +106 -0
- package/src/types.ts +241 -13
- package/src/verb-registration.ts +197 -0
- package/src/worker.ts +370 -0
- package/src/wrap.ts +260 -0
- package/test/client.test.ts +146 -0
- package/test/communication-tools-extended.test.ts +734 -0
- package/test/data-tools-extended.test.ts +743 -0
- package/test/define-extended.test.ts +819 -0
- package/test/define.test.ts +150 -41
- package/test/entities.test.ts +623 -0
- package/test/extended-entities.test.ts +1228 -0
- package/test/provider-implementations.test.ts +725 -0
- package/test/provider-registry-extended.test.ts +583 -0
- package/test/providers/google-sheets.test.ts +851 -0
- package/test/providers/helpers.ts +554 -0
- package/test/providers/hubspot.test.ts +576 -0
- package/test/providers/slack.test.ts +932 -0
- package/test/providers/stripe.test.ts +701 -0
- package/test/providers.test.ts +578 -0
- package/test/system-tools-extended.test.ts +632 -0
- package/test/system.test.ts +673 -0
- package/test/tools.test.ts +15 -11
- package/test/types.test.ts +402 -0
- package/test/verb-registration.test.ts +395 -0
- package/test/web-tools.test.ts +553 -0
- package/test/worker-extended.test.ts +699 -0
- package/test/worker.test.ts +576 -0
- package/test/wrap.test.ts +366 -0
- package/tsconfig.json +3 -13
- package/vitest.config.ts +37 -0
- package/wrangler.jsonc +9 -0
- package/.turbo/turbo-build.log +0 -5
- package/dist/providers/voice/vapi.d.ts +0 -27
- package/dist/providers/voice/vapi.d.ts.map +0 -1
- package/dist/providers/voice/vapi.js +0 -440
- package/dist/providers/voice/vapi.js.map +0 -1
- package/src/define.js +0 -267
- package/src/entities/advertising.js +0 -999
- package/src/entities/ai.js +0 -756
- package/src/entities/analytics.js +0 -1588
- package/src/entities/automation.js +0 -601
- package/src/entities/communication.js +0 -1150
- package/src/entities/crm.js +0 -1386
- package/src/entities/design.js +0 -546
- package/src/entities/development.js +0 -2212
- package/src/entities/document.js +0 -874
- package/src/entities/ecommerce.js +0 -1429
- package/src/entities/experiment.js +0 -1039
- package/src/entities/finance.js +0 -3478
- package/src/entities/forms.js +0 -1892
- package/src/entities/hr.js +0 -661
- package/src/entities/identity.js +0 -997
- package/src/entities/index.js +0 -282
- package/src/entities/infrastructure.js +0 -1153
- package/src/entities/knowledge.js +0 -1438
- package/src/entities/marketing.js +0 -1610
- package/src/entities/media.js +0 -1634
- package/src/entities/notification.js +0 -1199
- package/src/entities/presentation.js +0 -1274
- package/src/entities/productivity.js +0 -1317
- package/src/entities/project-management.js +0 -1136
- package/src/entities/recruiting.js +0 -736
- package/src/entities/shipping.js +0 -509
- package/src/entities/signature.js +0 -1102
- package/src/entities/site.js +0 -222
- package/src/entities/spreadsheet.js +0 -1341
- package/src/entities/storage.js +0 -1198
- package/src/entities/support.js +0 -1166
- package/src/entities/video-conferencing.js +0 -1750
- package/src/entities/video.js +0 -950
- package/src/entities.js +0 -1663
- package/src/index.js +0 -74
- package/src/providers/analytics/index.js +0 -17
- package/src/providers/analytics/mixpanel.js +0 -255
- package/src/providers/calendar/cal-com.js +0 -303
- package/src/providers/calendar/google-calendar.js +0 -335
- package/src/providers/calendar/index.js +0 -20
- package/src/providers/crm/hubspot.js +0 -566
- package/src/providers/crm/index.js +0 -17
- package/src/providers/development/github.js +0 -472
- package/src/providers/development/index.js +0 -17
- package/src/providers/ecommerce/index.js +0 -17
- package/src/providers/ecommerce/shopify.js +0 -378
- package/src/providers/email/index.js +0 -20
- package/src/providers/email/resend.js +0 -258
- package/src/providers/email/sendgrid.js +0 -161
- package/src/providers/finance/index.js +0 -17
- package/src/providers/finance/stripe.js +0 -549
- package/src/providers/forms/index.js +0 -17
- package/src/providers/forms/typeform.js +0 -500
- package/src/providers/index.js +0 -123
- package/src/providers/knowledge/index.js +0 -17
- package/src/providers/knowledge/notion.js +0 -389
- package/src/providers/marketing/index.js +0 -17
- package/src/providers/marketing/mailchimp.js +0 -443
- package/src/providers/media/cloudinary.js +0 -318
- package/src/providers/media/index.js +0 -17
- package/src/providers/messaging/index.js +0 -20
- package/src/providers/messaging/slack.js +0 -393
- package/src/providers/messaging/twilio-sms.js +0 -249
- package/src/providers/project-management/index.js +0 -17
- package/src/providers/project-management/linear.js +0 -575
- package/src/providers/registry.js +0 -86
- package/src/providers/spreadsheet/google-sheets.js +0 -375
- package/src/providers/spreadsheet/index.js +0 -20
- package/src/providers/spreadsheet/xlsx.js +0 -423
- package/src/providers/storage/index.js +0 -24
- package/src/providers/storage/s3.js +0 -419
- package/src/providers/support/index.js +0 -17
- package/src/providers/support/zendesk.js +0 -373
- package/src/providers/tasks/index.js +0 -17
- package/src/providers/tasks/todoist.js +0 -286
- package/src/providers/types.js +0 -9
- package/src/providers/video-conferencing/google-meet.js +0 -286
- package/src/providers/video-conferencing/index.js +0 -31
- package/src/providers/video-conferencing/jitsi.js +0 -254
- package/src/providers/video-conferencing/teams.js +0 -270
- package/src/providers/video-conferencing/zoom.js +0 -332
- package/src/registry.js +0 -128
- package/src/tools/communication.js +0 -184
- package/src/tools/data.js +0 -205
- package/src/tools/index.js +0 -11
- package/src/tools/web.js +0 -137
- package/src/types.js +0 -10
- package/test/define.test.js +0 -306
- package/test/registry.test.js +0 -357
- package/test/tools.test.js +0 -363
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Verb Auto-Registration (aip-47tm)
|
|
3
|
+
*
|
|
4
|
+
* Bridges `defineTool()` (synchronous, side-effect-free builder) to
|
|
5
|
+
* `digital-objects`' provider-mediated `defineVerb()` (async, I/O-bound).
|
|
6
|
+
*
|
|
7
|
+
* ## Design choice — Option B: explicit bootstrap
|
|
8
|
+
*
|
|
9
|
+
* `defineTool({ verb, frame })` records the metadata on the Tool but does
|
|
10
|
+
* NOT call `provider.defineVerb()` itself. Cross-package side effects
|
|
11
|
+
* from a pure builder are surprising; the provider is also caller-supplied,
|
|
12
|
+
* so eager registration would force `defineTool` to know about a provider
|
|
13
|
+
* it doesn't currently take.
|
|
14
|
+
*
|
|
15
|
+
* Instead, registration is an explicit, idempotent helper:
|
|
16
|
+
*
|
|
17
|
+
* - `registerToolVerb(provider, tool)` — single-tool, used from
|
|
18
|
+
* custom dispatchers that
|
|
19
|
+
* want lazy-on-first-call.
|
|
20
|
+
* - `registerToolVerbs(provider, tools)` — bootstrap list, used at
|
|
21
|
+
* startup once per provider.
|
|
22
|
+
*
|
|
23
|
+
* Both are idempotent: re-registering a Verb with the same name and same
|
|
24
|
+
* frame is a no-op. Re-registering with a different frame throws —
|
|
25
|
+
* silent overwrite would mask an ontology drift bug.
|
|
26
|
+
*
|
|
27
|
+
* ## Why not Option A (lazy in `wrapTool`)
|
|
28
|
+
*
|
|
29
|
+
* `wrapTool()` takes auth + payment brokers, not a `DigitalObjectsProvider`.
|
|
30
|
+
* Wiring a provider into `wrapTool()` would couple HTTP wrapping to the
|
|
31
|
+
* digital-objects ontology — a layering inversion. Callers that want
|
|
32
|
+
* lazy-on-first-call can compose `registerToolVerb()` into their own
|
|
33
|
+
* dispatcher; the helper is fast enough to call per-request because the
|
|
34
|
+
* idempotency check short-circuits to a single `getVerb()` lookup.
|
|
35
|
+
*
|
|
36
|
+
* ## Why not Option C (eager-with-deferred-provider queue)
|
|
37
|
+
*
|
|
38
|
+
* A module-level queue is global state in `digital-tools` — exactly what
|
|
39
|
+
* the bead forbids. It also can't flush deterministically across
|
|
40
|
+
* concurrent test workers, and ordering becomes load-dependent.
|
|
41
|
+
*
|
|
42
|
+
* @packageDocumentation
|
|
43
|
+
*/
|
|
44
|
+
import type { Frame, Verb, VerbDefinition } from 'digital-objects';
|
|
45
|
+
import type { AnyTool, Tool } from './types.js';
|
|
46
|
+
/**
|
|
47
|
+
* Subset of `DigitalObjectsProvider` that this module requires.
|
|
48
|
+
*
|
|
49
|
+
* We deliberately accept only `getVerb` + `defineVerb` (rather than the
|
|
50
|
+
* full provider interface) so callers can pass any object with these
|
|
51
|
+
* two methods — including HTTP/RPC clients, test doubles, and the
|
|
52
|
+
* canonical `MemoryProvider`.
|
|
53
|
+
*/
|
|
54
|
+
export interface VerbRegistrationProvider {
|
|
55
|
+
defineVerb(def: VerbDefinition): Promise<Verb>;
|
|
56
|
+
getVerb(name: string): Promise<Verb | null>;
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Mismatch error raised when a Tool tries to register a Verb whose name
|
|
60
|
+
* already exists with a different frame. We do not silently overwrite —
|
|
61
|
+
* conflicting ontology shapes are almost always a bug (two tools claiming
|
|
62
|
+
* the same verb with different role expectations).
|
|
63
|
+
*/
|
|
64
|
+
export declare class VerbRegistrationConflictError extends Error {
|
|
65
|
+
readonly verbName: string;
|
|
66
|
+
readonly existing: Frame | undefined;
|
|
67
|
+
readonly incoming: Frame | undefined;
|
|
68
|
+
constructor(verbName: string, existing: Frame | undefined, incoming: Frame | undefined);
|
|
69
|
+
}
|
|
70
|
+
/**
|
|
71
|
+
* Register the Verb declared by a single Tool against `provider`.
|
|
72
|
+
*
|
|
73
|
+
* - Tools without a `verb` field are skipped (they are not SVO-aware).
|
|
74
|
+
* - If the verb already exists with the same frame, the call is a no-op
|
|
75
|
+
* and the existing Verb is returned (idempotent).
|
|
76
|
+
* - If the verb already exists with a different frame, throws
|
|
77
|
+
* {@link VerbRegistrationConflictError}.
|
|
78
|
+
*
|
|
79
|
+
* Suitable for both eager bootstrap and lazy-per-request use:
|
|
80
|
+
* the idempotency check is a single `getVerb()` lookup, so it is safe
|
|
81
|
+
* to call from a hot dispatch path.
|
|
82
|
+
*
|
|
83
|
+
* @returns The registered Verb, or `null` if the tool has no `verb` field.
|
|
84
|
+
*
|
|
85
|
+
* @example Lazy registration in a custom dispatcher
|
|
86
|
+
* ```ts
|
|
87
|
+
* async function dispatch(provider: DigitalObjectsProvider, tool: Tool, args: unknown) {
|
|
88
|
+
* await registerToolVerb(provider, tool) // idempotent, cheap on subsequent calls
|
|
89
|
+
* return tool.handler(args)
|
|
90
|
+
* }
|
|
91
|
+
* ```
|
|
92
|
+
*/
|
|
93
|
+
export declare function registerToolVerb(provider: VerbRegistrationProvider, tool: Tool<unknown, unknown> | AnyTool): Promise<Verb | null>;
|
|
94
|
+
/**
|
|
95
|
+
* Bootstrap helper: register the Verbs for every SVO-aware tool in
|
|
96
|
+
* `tools` against `provider`.
|
|
97
|
+
*
|
|
98
|
+
* Tools without a `verb` field are skipped silently (legacy / non-SVO
|
|
99
|
+
* tools coexist with SVO-aware tools in the same registry).
|
|
100
|
+
*
|
|
101
|
+
* Conflicts (same verb name, different frame) throw on the first
|
|
102
|
+
* conflicting tool — the caller can decide whether to retry without
|
|
103
|
+
* the conflicting tool or surface the error.
|
|
104
|
+
*
|
|
105
|
+
* @returns The list of Verbs that were registered (or already existed,
|
|
106
|
+
* for idempotent calls). Tools with no verb are not included.
|
|
107
|
+
*
|
|
108
|
+
* @example Startup
|
|
109
|
+
* ```ts
|
|
110
|
+
* import { MemoryProvider, registerToolVerbs, getBuiltinTools } from 'digital-tools'
|
|
111
|
+
*
|
|
112
|
+
* const provider = new MemoryProvider()
|
|
113
|
+
* await registerToolVerbs(provider, getBuiltinTools())
|
|
114
|
+
* ```
|
|
115
|
+
*/
|
|
116
|
+
export declare function registerToolVerbs(provider: VerbRegistrationProvider, tools: ReadonlyArray<Tool<unknown, unknown> | AnyTool>): Promise<Verb[]>;
|
|
117
|
+
/**
|
|
118
|
+
* Alias for {@link registerToolVerbs}. The "bootstrap" name reads better
|
|
119
|
+
* at startup sites where a list of tools is wired against a provider once.
|
|
120
|
+
*/
|
|
121
|
+
export declare const bootstrapTools: typeof registerToolVerbs;
|
|
122
|
+
//# sourceMappingURL=verb-registration.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"verb-registration.d.ts","sourceRoot":"","sources":["../src/verb-registration.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA0CG;AAEH,OAAO,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAA;AAClE,OAAO,KAAK,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,YAAY,CAAA;AAE/C;;;;;;;GAOG;AACH,MAAM,WAAW,wBAAwB;IACvC,UAAU,CAAC,GAAG,EAAE,cAAc,GAAG,OAAO,CAAC,IAAI,CAAC,CAAA;IAC9C,OAAO,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,GAAG,IAAI,CAAC,CAAA;CAC5C;AAkCD;;;;;GAKG;AACH,qBAAa,6BAA8B,SAAQ,KAAK;aAEpC,QAAQ,EAAE,MAAM;aAChB,QAAQ,EAAE,KAAK,GAAG,SAAS;aAC3B,QAAQ,EAAE,KAAK,GAAG,SAAS;gBAF3B,QAAQ,EAAE,MAAM,EAChB,QAAQ,EAAE,KAAK,GAAG,SAAS,EAC3B,QAAQ,EAAE,KAAK,GAAG,SAAS;CAU9C;AAED;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,wBAAsB,gBAAgB,CACpC,QAAQ,EAAE,wBAAwB,EAClC,IAAI,EAAE,IAAI,CAAC,OAAO,EAAE,OAAO,CAAC,GAAG,OAAO,GACrC,OAAO,CAAC,IAAI,GAAG,IAAI,CAAC,CAgBtB;AAED;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,wBAAsB,iBAAiB,CACrC,QAAQ,EAAE,wBAAwB,EAClC,KAAK,EAAE,aAAa,CAAC,IAAI,CAAC,OAAO,EAAE,OAAO,CAAC,GAAG,OAAO,CAAC,GACrD,OAAO,CAAC,IAAI,EAAE,CAAC,CAOjB;AAED;;;GAGG;AACH,eAAO,MAAM,cAAc,0BAAoB,CAAA"}
|
|
@@ -0,0 +1,176 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Verb Auto-Registration (aip-47tm)
|
|
3
|
+
*
|
|
4
|
+
* Bridges `defineTool()` (synchronous, side-effect-free builder) to
|
|
5
|
+
* `digital-objects`' provider-mediated `defineVerb()` (async, I/O-bound).
|
|
6
|
+
*
|
|
7
|
+
* ## Design choice — Option B: explicit bootstrap
|
|
8
|
+
*
|
|
9
|
+
* `defineTool({ verb, frame })` records the metadata on the Tool but does
|
|
10
|
+
* NOT call `provider.defineVerb()` itself. Cross-package side effects
|
|
11
|
+
* from a pure builder are surprising; the provider is also caller-supplied,
|
|
12
|
+
* so eager registration would force `defineTool` to know about a provider
|
|
13
|
+
* it doesn't currently take.
|
|
14
|
+
*
|
|
15
|
+
* Instead, registration is an explicit, idempotent helper:
|
|
16
|
+
*
|
|
17
|
+
* - `registerToolVerb(provider, tool)` — single-tool, used from
|
|
18
|
+
* custom dispatchers that
|
|
19
|
+
* want lazy-on-first-call.
|
|
20
|
+
* - `registerToolVerbs(provider, tools)` — bootstrap list, used at
|
|
21
|
+
* startup once per provider.
|
|
22
|
+
*
|
|
23
|
+
* Both are idempotent: re-registering a Verb with the same name and same
|
|
24
|
+
* frame is a no-op. Re-registering with a different frame throws —
|
|
25
|
+
* silent overwrite would mask an ontology drift bug.
|
|
26
|
+
*
|
|
27
|
+
* ## Why not Option A (lazy in `wrapTool`)
|
|
28
|
+
*
|
|
29
|
+
* `wrapTool()` takes auth + payment brokers, not a `DigitalObjectsProvider`.
|
|
30
|
+
* Wiring a provider into `wrapTool()` would couple HTTP wrapping to the
|
|
31
|
+
* digital-objects ontology — a layering inversion. Callers that want
|
|
32
|
+
* lazy-on-first-call can compose `registerToolVerb()` into their own
|
|
33
|
+
* dispatcher; the helper is fast enough to call per-request because the
|
|
34
|
+
* idempotency check short-circuits to a single `getVerb()` lookup.
|
|
35
|
+
*
|
|
36
|
+
* ## Why not Option C (eager-with-deferred-provider queue)
|
|
37
|
+
*
|
|
38
|
+
* A module-level queue is global state in `digital-tools` — exactly what
|
|
39
|
+
* the bead forbids. It also can't flush deterministically across
|
|
40
|
+
* concurrent test workers, and ordering becomes load-dependent.
|
|
41
|
+
*
|
|
42
|
+
* @packageDocumentation
|
|
43
|
+
*/
|
|
44
|
+
/**
|
|
45
|
+
* Compare two optional Frames structurally. Returns true when both are
|
|
46
|
+
* undefined, or both define the same set of role -> NounRef mappings.
|
|
47
|
+
*
|
|
48
|
+
* `manner` (string[]) is compared as an unordered set since the role
|
|
49
|
+
* order is not semantically meaningful.
|
|
50
|
+
*/
|
|
51
|
+
function framesEqual(a, b) {
|
|
52
|
+
if (a === b)
|
|
53
|
+
return true;
|
|
54
|
+
if (!a || !b)
|
|
55
|
+
return false;
|
|
56
|
+
const keys = new Set([
|
|
57
|
+
...Object.keys(a),
|
|
58
|
+
...Object.keys(b),
|
|
59
|
+
]);
|
|
60
|
+
for (const k of keys) {
|
|
61
|
+
const av = a[k];
|
|
62
|
+
const bv = b[k];
|
|
63
|
+
if (k === 'manner') {
|
|
64
|
+
const aArr = av ?? [];
|
|
65
|
+
const bArr = bv ?? [];
|
|
66
|
+
if (aArr.length !== bArr.length)
|
|
67
|
+
return false;
|
|
68
|
+
const aSet = new Set(aArr);
|
|
69
|
+
for (const v of bArr)
|
|
70
|
+
if (!aSet.has(v))
|
|
71
|
+
return false;
|
|
72
|
+
}
|
|
73
|
+
else {
|
|
74
|
+
if (av !== bv)
|
|
75
|
+
return false;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
return true;
|
|
79
|
+
}
|
|
80
|
+
/**
|
|
81
|
+
* Mismatch error raised when a Tool tries to register a Verb whose name
|
|
82
|
+
* already exists with a different frame. We do not silently overwrite —
|
|
83
|
+
* conflicting ontology shapes are almost always a bug (two tools claiming
|
|
84
|
+
* the same verb with different role expectations).
|
|
85
|
+
*/
|
|
86
|
+
export class VerbRegistrationConflictError extends Error {
|
|
87
|
+
verbName;
|
|
88
|
+
existing;
|
|
89
|
+
incoming;
|
|
90
|
+
constructor(verbName, existing, incoming) {
|
|
91
|
+
super(`Verb "${verbName}" is already registered with a different frame. ` +
|
|
92
|
+
`Tools that share a verb name must declare the same frame. ` +
|
|
93
|
+
`Re-registering a verb with the same frame is a no-op (idempotent), ` +
|
|
94
|
+
`but the incoming frame does not match the existing one.`);
|
|
95
|
+
this.verbName = verbName;
|
|
96
|
+
this.existing = existing;
|
|
97
|
+
this.incoming = incoming;
|
|
98
|
+
this.name = 'VerbRegistrationConflictError';
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
/**
|
|
102
|
+
* Register the Verb declared by a single Tool against `provider`.
|
|
103
|
+
*
|
|
104
|
+
* - Tools without a `verb` field are skipped (they are not SVO-aware).
|
|
105
|
+
* - If the verb already exists with the same frame, the call is a no-op
|
|
106
|
+
* and the existing Verb is returned (idempotent).
|
|
107
|
+
* - If the verb already exists with a different frame, throws
|
|
108
|
+
* {@link VerbRegistrationConflictError}.
|
|
109
|
+
*
|
|
110
|
+
* Suitable for both eager bootstrap and lazy-per-request use:
|
|
111
|
+
* the idempotency check is a single `getVerb()` lookup, so it is safe
|
|
112
|
+
* to call from a hot dispatch path.
|
|
113
|
+
*
|
|
114
|
+
* @returns The registered Verb, or `null` if the tool has no `verb` field.
|
|
115
|
+
*
|
|
116
|
+
* @example Lazy registration in a custom dispatcher
|
|
117
|
+
* ```ts
|
|
118
|
+
* async function dispatch(provider: DigitalObjectsProvider, tool: Tool, args: unknown) {
|
|
119
|
+
* await registerToolVerb(provider, tool) // idempotent, cheap on subsequent calls
|
|
120
|
+
* return tool.handler(args)
|
|
121
|
+
* }
|
|
122
|
+
* ```
|
|
123
|
+
*/
|
|
124
|
+
export async function registerToolVerb(provider, tool) {
|
|
125
|
+
if (!tool.verb)
|
|
126
|
+
return null;
|
|
127
|
+
const existing = await provider.getVerb(tool.verb);
|
|
128
|
+
if (existing) {
|
|
129
|
+
if (framesEqual(existing.frame, tool.frame)) {
|
|
130
|
+
return existing;
|
|
131
|
+
}
|
|
132
|
+
throw new VerbRegistrationConflictError(tool.verb, existing.frame, tool.frame);
|
|
133
|
+
}
|
|
134
|
+
return provider.defineVerb({
|
|
135
|
+
name: tool.verb,
|
|
136
|
+
...(tool.frame !== undefined && { frame: tool.frame }),
|
|
137
|
+
...(tool.description !== undefined && { description: tool.description }),
|
|
138
|
+
});
|
|
139
|
+
}
|
|
140
|
+
/**
|
|
141
|
+
* Bootstrap helper: register the Verbs for every SVO-aware tool in
|
|
142
|
+
* `tools` against `provider`.
|
|
143
|
+
*
|
|
144
|
+
* Tools without a `verb` field are skipped silently (legacy / non-SVO
|
|
145
|
+
* tools coexist with SVO-aware tools in the same registry).
|
|
146
|
+
*
|
|
147
|
+
* Conflicts (same verb name, different frame) throw on the first
|
|
148
|
+
* conflicting tool — the caller can decide whether to retry without
|
|
149
|
+
* the conflicting tool or surface the error.
|
|
150
|
+
*
|
|
151
|
+
* @returns The list of Verbs that were registered (or already existed,
|
|
152
|
+
* for idempotent calls). Tools with no verb are not included.
|
|
153
|
+
*
|
|
154
|
+
* @example Startup
|
|
155
|
+
* ```ts
|
|
156
|
+
* import { MemoryProvider, registerToolVerbs, getBuiltinTools } from 'digital-tools'
|
|
157
|
+
*
|
|
158
|
+
* const provider = new MemoryProvider()
|
|
159
|
+
* await registerToolVerbs(provider, getBuiltinTools())
|
|
160
|
+
* ```
|
|
161
|
+
*/
|
|
162
|
+
export async function registerToolVerbs(provider, tools) {
|
|
163
|
+
const registered = [];
|
|
164
|
+
for (const tool of tools) {
|
|
165
|
+
const verb = await registerToolVerb(provider, tool);
|
|
166
|
+
if (verb)
|
|
167
|
+
registered.push(verb);
|
|
168
|
+
}
|
|
169
|
+
return registered;
|
|
170
|
+
}
|
|
171
|
+
/**
|
|
172
|
+
* Alias for {@link registerToolVerbs}. The "bootstrap" name reads better
|
|
173
|
+
* at startup sites where a list of tools is wired against a provider once.
|
|
174
|
+
*/
|
|
175
|
+
export const bootstrapTools = registerToolVerbs;
|
|
176
|
+
//# sourceMappingURL=verb-registration.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"verb-registration.js","sourceRoot":"","sources":["../src/verb-registration.ts"],"names":[],"mappings":"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"}
|
package/dist/worker.d.ts
ADDED
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Tool Worker - provides tool service via RPC
|
|
3
|
+
*
|
|
4
|
+
* This worker can be deployed to Cloudflare Workers or run locally via Miniflare.
|
|
5
|
+
* It exposes tool registration, discovery, execution, and MCP conversion via Workers RPC.
|
|
6
|
+
*
|
|
7
|
+
* Uses Cloudflare Workers RPC (WorkerEntrypoint, RpcTarget) for communication.
|
|
8
|
+
*/
|
|
9
|
+
import { WorkerEntrypoint, RpcTarget } from 'cloudflare:workers';
|
|
10
|
+
import type { AnyTool, ToolCategory, ToolQuery, MCPTool, ToolSubcategory } from './types.js';
|
|
11
|
+
/**
|
|
12
|
+
* Core tool service - extends RpcTarget so it can be passed over RPC
|
|
13
|
+
*
|
|
14
|
+
* Contains all tool functionality: registration, discovery, execution, and MCP conversion
|
|
15
|
+
*/
|
|
16
|
+
export declare class ToolServiceCore extends RpcTarget {
|
|
17
|
+
private tools;
|
|
18
|
+
constructor();
|
|
19
|
+
/**
|
|
20
|
+
* Register built-in tools
|
|
21
|
+
*/
|
|
22
|
+
private registerBuiltins;
|
|
23
|
+
/**
|
|
24
|
+
* Register a tool in the service registry
|
|
25
|
+
*/
|
|
26
|
+
register(tool: AnyTool): void;
|
|
27
|
+
/**
|
|
28
|
+
* Unregister a tool
|
|
29
|
+
*/
|
|
30
|
+
unregister(id: string): boolean;
|
|
31
|
+
/**
|
|
32
|
+
* Get a tool by ID
|
|
33
|
+
*/
|
|
34
|
+
get(id: string): AnyTool | undefined;
|
|
35
|
+
/**
|
|
36
|
+
* Check if a tool exists
|
|
37
|
+
*/
|
|
38
|
+
has(id: string): boolean;
|
|
39
|
+
/**
|
|
40
|
+
* List all tool IDs
|
|
41
|
+
*/
|
|
42
|
+
list(): string[];
|
|
43
|
+
/**
|
|
44
|
+
* Query tools with filtering
|
|
45
|
+
*/
|
|
46
|
+
query(options: ToolQuery): AnyTool[];
|
|
47
|
+
/**
|
|
48
|
+
* Get tools by category
|
|
49
|
+
*/
|
|
50
|
+
byCategory(category: ToolCategory): AnyTool[];
|
|
51
|
+
/**
|
|
52
|
+
* Execute a tool by ID
|
|
53
|
+
*/
|
|
54
|
+
executeTool<TInput = unknown, TOutput = unknown>(id: string, input: TInput): Promise<TOutput>;
|
|
55
|
+
/**
|
|
56
|
+
* Convert a Tool to MCP format
|
|
57
|
+
*/
|
|
58
|
+
toMCP(tool: AnyTool): MCPTool;
|
|
59
|
+
/**
|
|
60
|
+
* Convert all registered tools to MCP format
|
|
61
|
+
*/
|
|
62
|
+
listMCPTools(): MCPTool[];
|
|
63
|
+
/**
|
|
64
|
+
* Import a tool from MCP format
|
|
65
|
+
*/
|
|
66
|
+
fromMCP(mcpTool: MCPTool, handler: (input: unknown) => unknown | Promise<unknown>, options?: {
|
|
67
|
+
category?: ToolCategory;
|
|
68
|
+
subcategory?: ToolSubcategory;
|
|
69
|
+
tags?: string[];
|
|
70
|
+
}): AnyTool;
|
|
71
|
+
/**
|
|
72
|
+
* Clear all tools (except built-ins if keepBuiltins is true)
|
|
73
|
+
*/
|
|
74
|
+
clear(keepBuiltins?: boolean): void;
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Main tool service exposed via RPC as WorkerEntrypoint
|
|
78
|
+
*
|
|
79
|
+
* Usage:
|
|
80
|
+
* const tools = await env.TOOLS.connect()
|
|
81
|
+
* tools.register({ id: 'my.tool', ... })
|
|
82
|
+
* tools.list()
|
|
83
|
+
* const result = await tools.executeTool('data.json.parse', { text: '{}' })
|
|
84
|
+
*/
|
|
85
|
+
export declare class ToolService extends WorkerEntrypoint {
|
|
86
|
+
/**
|
|
87
|
+
* Get a tool service instance - returns an RpcTarget that can be used directly
|
|
88
|
+
*/
|
|
89
|
+
connect(): ToolServiceCore;
|
|
90
|
+
}
|
|
91
|
+
export default ToolService;
|
|
92
|
+
export { ToolService as ToolWorker };
|
|
93
|
+
//# sourceMappingURL=worker.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"worker.d.ts","sourceRoot":"","sources":["../src/worker.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,gBAAgB,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAA;AAChE,OAAO,KAAK,EAAE,OAAO,EAAE,YAAY,EAAE,SAAS,EAAE,OAAO,EAAE,eAAe,EAAE,MAAM,YAAY,CAAA;AAE5F;;;;GAIG;AACH,qBAAa,eAAgB,SAAQ,SAAS;IAC5C,OAAO,CAAC,KAAK,CAAkC;;IAQ/C;;OAEG;IACH,OAAO,CAAC,gBAAgB;IAsIxB;;OAEG;IACH,QAAQ,CAAC,IAAI,EAAE,OAAO,GAAG,IAAI;IAI7B;;OAEG;IACH,UAAU,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO;IAI/B;;OAEG;IACH,GAAG,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,GAAG,SAAS;IAIpC;;OAEG;IACH,GAAG,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO;IAIxB;;OAEG;IACH,IAAI,IAAI,MAAM,EAAE;IAIhB;;OAEG;IACH,KAAK,CAAC,OAAO,EAAE,SAAS,GAAG,OAAO,EAAE;IA4CpC;;OAEG;IACH,UAAU,CAAC,QAAQ,EAAE,YAAY,GAAG,OAAO,EAAE;IAI7C;;OAEG;IACG,WAAW,CAAC,MAAM,GAAG,OAAO,EAAE,OAAO,GAAG,OAAO,EACnD,EAAE,EAAE,MAAM,EACV,KAAK,EAAE,MAAM,GACZ,OAAO,CAAC,OAAO,CAAC;IAQnB;;OAEG;IACH,KAAK,CAAC,IAAI,EAAE,OAAO,GAAG,OAAO;IAmB7B;;OAEG;IACH,YAAY,IAAI,OAAO,EAAE;IAIzB;;OAEG;IACH,OAAO,CACL,OAAO,EAAE,OAAO,EAChB,OAAO,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,OAAO,GAAG,OAAO,CAAC,OAAO,CAAC,EACvD,OAAO,CAAC,EAAE;QACR,QAAQ,CAAC,EAAE,YAAY,CAAA;QACvB,WAAW,CAAC,EAAE,eAAe,CAAA;QAC7B,IAAI,CAAC,EAAE,MAAM,EAAE,CAAA;KAChB,GACA,OAAO;IA0BV;;OAEG;IACH,KAAK,CAAC,YAAY,GAAE,OAAe,GAAG,IAAI;CAU3C;AAED;;;;;;;;GAQG;AACH,qBAAa,WAAY,SAAQ,gBAAgB;IAC/C;;OAEG;IACH,OAAO,IAAI,eAAe;CAG3B;AAGD,eAAe,WAAW,CAAA;AAG1B,OAAO,EAAE,WAAW,IAAI,UAAU,EAAE,CAAA"}
|