@sundaeswap/sprinkles 0.7.0 → 0.8.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 (95) hide show
  1. package/README.md +178 -181
  2. package/dist/cjs/Sprinkle/__tests__/builtin-actions.test.js +4 -4
  3. package/dist/cjs/Sprinkle/__tests__/builtin-actions.test.js.map +1 -1
  4. package/dist/cjs/Sprinkle/__tests__/cli-adapter.test.js +25 -3
  5. package/dist/cjs/Sprinkle/__tests__/cli-adapter.test.js.map +1 -1
  6. package/dist/cjs/Sprinkle/__tests__/fill-in-struct.test.js +15 -1
  7. package/dist/cjs/Sprinkle/__tests__/fill-in-struct.test.js.map +1 -1
  8. package/dist/cjs/Sprinkle/__tests__/mcp-adapter.test.js +7 -9
  9. package/dist/cjs/Sprinkle/__tests__/mcp-adapter.test.js.map +1 -1
  10. package/dist/cjs/Sprinkle/__tests__/native-script.test.js +390 -0
  11. package/dist/cjs/Sprinkle/__tests__/native-script.test.js.map +1 -0
  12. package/dist/cjs/Sprinkle/__tests__/utility-actions.test.js +367 -0
  13. package/dist/cjs/Sprinkle/__tests__/utility-actions.test.js.map +1 -0
  14. package/dist/cjs/Sprinkle/actions/builtin/addressbook-actions.js +164 -0
  15. package/dist/cjs/Sprinkle/actions/builtin/addressbook-actions.js.map +1 -0
  16. package/dist/cjs/Sprinkle/actions/builtin/index.js +60 -3
  17. package/dist/cjs/Sprinkle/actions/builtin/index.js.map +1 -1
  18. package/dist/cjs/Sprinkle/actions/builtin/native-script.js +139 -0
  19. package/dist/cjs/Sprinkle/actions/builtin/native-script.js.map +1 -0
  20. package/dist/cjs/Sprinkle/actions/builtin/utility-actions.js +218 -0
  21. package/dist/cjs/Sprinkle/actions/builtin/utility-actions.js.map +1 -0
  22. package/dist/cjs/Sprinkle/actions/cli-adapter.js +20 -2
  23. package/dist/cjs/Sprinkle/actions/cli-adapter.js.map +1 -1
  24. package/dist/cjs/Sprinkle/actions/index.js +12 -0
  25. package/dist/cjs/Sprinkle/actions/index.js.map +1 -1
  26. package/dist/cjs/Sprinkle/actions/mcp-adapter.js +146 -4
  27. package/dist/cjs/Sprinkle/actions/mcp-adapter.js.map +1 -1
  28. package/dist/cjs/Sprinkle/index.js +282 -6
  29. package/dist/cjs/Sprinkle/index.js.map +1 -1
  30. package/dist/cjs/Sprinkle/schemas.js +17 -1
  31. package/dist/cjs/Sprinkle/schemas.js.map +1 -1
  32. package/dist/esm/Sprinkle/__tests__/builtin-actions.test.js +4 -4
  33. package/dist/esm/Sprinkle/__tests__/builtin-actions.test.js.map +1 -1
  34. package/dist/esm/Sprinkle/__tests__/cli-adapter.test.js +25 -3
  35. package/dist/esm/Sprinkle/__tests__/cli-adapter.test.js.map +1 -1
  36. package/dist/esm/Sprinkle/__tests__/fill-in-struct.test.js +15 -1
  37. package/dist/esm/Sprinkle/__tests__/fill-in-struct.test.js.map +1 -1
  38. package/dist/esm/Sprinkle/__tests__/mcp-adapter.test.js +7 -9
  39. package/dist/esm/Sprinkle/__tests__/mcp-adapter.test.js.map +1 -1
  40. package/dist/esm/Sprinkle/__tests__/native-script.test.js +388 -0
  41. package/dist/esm/Sprinkle/__tests__/native-script.test.js.map +1 -0
  42. package/dist/esm/Sprinkle/__tests__/utility-actions.test.js +365 -0
  43. package/dist/esm/Sprinkle/__tests__/utility-actions.test.js.map +1 -0
  44. package/dist/esm/Sprinkle/actions/builtin/addressbook-actions.js +159 -0
  45. package/dist/esm/Sprinkle/actions/builtin/addressbook-actions.js.map +1 -0
  46. package/dist/esm/Sprinkle/actions/builtin/index.js +8 -3
  47. package/dist/esm/Sprinkle/actions/builtin/index.js.map +1 -1
  48. package/dist/esm/Sprinkle/actions/builtin/native-script.js +133 -0
  49. package/dist/esm/Sprinkle/actions/builtin/native-script.js.map +1 -0
  50. package/dist/esm/Sprinkle/actions/builtin/utility-actions.js +213 -0
  51. package/dist/esm/Sprinkle/actions/builtin/utility-actions.js.map +1 -0
  52. package/dist/esm/Sprinkle/actions/cli-adapter.js +20 -2
  53. package/dist/esm/Sprinkle/actions/cli-adapter.js.map +1 -1
  54. package/dist/esm/Sprinkle/actions/index.js +1 -1
  55. package/dist/esm/Sprinkle/actions/index.js.map +1 -1
  56. package/dist/esm/Sprinkle/actions/mcp-adapter.js +145 -5
  57. package/dist/esm/Sprinkle/actions/mcp-adapter.js.map +1 -1
  58. package/dist/esm/Sprinkle/index.js +260 -9
  59. package/dist/esm/Sprinkle/index.js.map +1 -1
  60. package/dist/esm/Sprinkle/schemas.js +16 -0
  61. package/dist/esm/Sprinkle/schemas.js.map +1 -1
  62. package/dist/types/Sprinkle/actions/builtin/addressbook-actions.d.ts +50 -0
  63. package/dist/types/Sprinkle/actions/builtin/addressbook-actions.d.ts.map +1 -0
  64. package/dist/types/Sprinkle/actions/builtin/index.d.ts +6 -2
  65. package/dist/types/Sprinkle/actions/builtin/index.d.ts.map +1 -1
  66. package/dist/types/Sprinkle/actions/builtin/native-script.d.ts +27 -0
  67. package/dist/types/Sprinkle/actions/builtin/native-script.d.ts.map +1 -0
  68. package/dist/types/Sprinkle/actions/builtin/utility-actions.d.ts +48 -0
  69. package/dist/types/Sprinkle/actions/builtin/utility-actions.d.ts.map +1 -0
  70. package/dist/types/Sprinkle/actions/cli-adapter.d.ts.map +1 -1
  71. package/dist/types/Sprinkle/actions/index.d.ts +2 -1
  72. package/dist/types/Sprinkle/actions/index.d.ts.map +1 -1
  73. package/dist/types/Sprinkle/actions/mcp-adapter.d.ts +24 -0
  74. package/dist/types/Sprinkle/actions/mcp-adapter.d.ts.map +1 -1
  75. package/dist/types/Sprinkle/index.d.ts +5 -2
  76. package/dist/types/Sprinkle/index.d.ts.map +1 -1
  77. package/dist/types/Sprinkle/schemas.d.ts +72 -0
  78. package/dist/types/Sprinkle/schemas.d.ts.map +1 -1
  79. package/dist/types/tsconfig.build.tsbuildinfo +1 -1
  80. package/package.json +1 -1
  81. package/src/Sprinkle/__tests__/builtin-actions.test.ts +4 -4
  82. package/src/Sprinkle/__tests__/cli-adapter.test.ts +24 -3
  83. package/src/Sprinkle/__tests__/fill-in-struct.test.ts +23 -1
  84. package/src/Sprinkle/__tests__/mcp-adapter.test.ts +7 -5
  85. package/src/Sprinkle/__tests__/native-script.test.ts +341 -0
  86. package/src/Sprinkle/__tests__/utility-actions.test.ts +348 -0
  87. package/src/Sprinkle/actions/builtin/addressbook-actions.ts +168 -0
  88. package/src/Sprinkle/actions/builtin/index.ts +41 -2
  89. package/src/Sprinkle/actions/builtin/native-script.ts +165 -0
  90. package/src/Sprinkle/actions/builtin/utility-actions.ts +285 -0
  91. package/src/Sprinkle/actions/cli-adapter.ts +18 -2
  92. package/src/Sprinkle/actions/index.ts +2 -1
  93. package/src/Sprinkle/actions/mcp-adapter.ts +179 -4
  94. package/src/Sprinkle/index.ts +264 -3
  95. package/src/Sprinkle/schemas.ts +20 -0
@@ -0,0 +1 @@
1
+ {"version":3,"file":"native-script.test.js","names":["describe","expect","test","mock","ActionError","provideScriptCalls","mockCompletedTx","toCbor","module","Core","Ed25519KeyHashHex","h","Slot","n","HexBlob","s","ScriptPubkey","constructor","_defineProperty","hash","ScriptAll","scripts","ScriptAny","ScriptNOfK","TimelockExpiry","slot","TimelockStart","NativeScript","fromCbor","hex","Error","__fromCbor","newScriptPubkey","sp","__type","value","newScriptAll","sa","newScriptAny","newScriptNOfK","sn","newTimelockExpiry","te","newTimelockStart","ts","Script","newNativeScript","ns","__nativeScript","repeat","toNativeScript","completeWithScripts","result","toEqual","toBe","toThrow","err","code","keyHash","Signature","key_hash","AllOf","toHaveLength","AnyOf","AtLeast","required","Before","time","After","script_hash","makeTxBuilder","builder","provideScript","script","push","complete","tx","rejects","toMatchObject","expectedScriptHash","attempt","context","sprinkle","addressbook","settings","undefined"],"sources":["../../../../src/Sprinkle/__tests__/native-script.test.ts"],"sourcesContent":["import { describe, expect, test, mock } from \"bun:test\";\nimport { ActionError } from \"../actions/types.js\";\n\n// ---------------------------------------------------------------------------\n// Mocks — mirror the Blaze SDK surface used by native-script.ts\n// ---------------------------------------------------------------------------\n\nlet provideScriptCalls: any[] = [];\nconst mockCompletedTx = { toCbor: () => \"mock-tx-cbor\" };\n\nmock.module(\"@blaze-cardano/sdk\", () => ({\n Core: {\n Ed25519KeyHashHex: (h: string) => h,\n Slot: (n: number) => n,\n HexBlob: (s: string) => s,\n ScriptPubkey: class {\n hash: string;\n constructor(h: string) {\n this.hash = h;\n }\n },\n ScriptAll: class {\n scripts: any[];\n constructor(s: any[]) {\n this.scripts = s;\n }\n },\n ScriptAny: class {\n scripts: any[];\n constructor(s: any[]) {\n this.scripts = s;\n }\n },\n ScriptNOfK: class {\n scripts: any[];\n n: number;\n constructor(s: any[], n: number) {\n this.scripts = s;\n this.n = n;\n }\n },\n TimelockExpiry: class {\n slot: number;\n constructor(s: number) {\n this.slot = s;\n }\n },\n TimelockStart: class {\n slot: number;\n constructor(s: number) {\n this.slot = s;\n }\n },\n NativeScript: {\n fromCbor: (hex: string) => {\n if (hex === \"invalid\") throw new Error(\"Invalid CBOR\");\n return { __fromCbor: hex };\n },\n newScriptPubkey: (sp: any) => ({ __type: \"pubkey\", value: sp }),\n newScriptAll: (sa: any) => ({ __type: \"all\", value: sa }),\n newScriptAny: (sa: any) => ({ __type: \"any\", value: sa }),\n newScriptNOfK: (sn: any) => ({ __type: \"nofk\", value: sn }),\n newTimelockExpiry: (te: any) => ({ __type: \"timelockExpiry\", value: te }),\n newTimelockStart: (ts: any) => ({ __type: \"timelockStart\", value: ts }),\n },\n Script: {\n newNativeScript: (ns: any) => ({\n __nativeScript: ns,\n hash: () => {\n // Produce a deterministic hex hash from the native script content\n if (ns?.__type === \"pubkey\") return ns.value.hash;\n if (ns?.__fromCbor) return \"cbor\" + ns.__fromCbor;\n return \"0\".repeat(56);\n },\n }),\n },\n },\n}));\n\nconst { toNativeScript, completeWithScripts } = await import(\n \"../actions/builtin/native-script.js\"\n);\n\n// ---------------------------------------------------------------------------\n// toNativeScript — CBOR hex input\n// ---------------------------------------------------------------------------\n\ndescribe(\"toNativeScript — CBOR hex\", () => {\n test(\"converts valid CBOR hex string\", () => {\n const result = toNativeScript(\"82018200\");\n expect(result.__nativeScript).toEqual({ __fromCbor: \"82018200\" });\n expect(typeof result.hash).toBe(\"function\");\n });\n\n test(\"throws INVALID_NATIVE_SCRIPT for invalid CBOR\", () => {\n expect(() => toNativeScript(\"invalid\")).toThrow(ActionError);\n try {\n toNativeScript(\"invalid\");\n } catch (err: any) {\n expect(err.code).toBe(\"INVALID_NATIVE_SCRIPT\");\n }\n });\n});\n\n// ---------------------------------------------------------------------------\n// toNativeScript — MultisigScript JSON input\n// ---------------------------------------------------------------------------\n\ndescribe(\"toNativeScript — MultisigScript JSON\", () => {\n const keyHash = \"a\".repeat(56);\n\n test(\"converts Signature\", () => {\n const result = toNativeScript({ Signature: { key_hash: keyHash } });\n expect(result.__nativeScript.__type).toBe(\"pubkey\");\n expect(result.__nativeScript.value.hash).toBe(keyHash);\n });\n\n test(\"converts AllOf with nested scripts\", () => {\n const result = toNativeScript({\n AllOf: {\n scripts: [\n { Signature: { key_hash: keyHash } },\n { Signature: { key_hash: \"b\".repeat(56) } },\n ],\n },\n });\n expect(result.__nativeScript.__type).toBe(\"all\");\n expect(result.__nativeScript.value.scripts).toHaveLength(2);\n });\n\n test(\"converts AnyOf\", () => {\n const result = toNativeScript({\n AnyOf: {\n scripts: [{ Signature: { key_hash: keyHash } }],\n },\n });\n expect(result.__nativeScript.__type).toBe(\"any\");\n });\n\n test(\"converts AtLeast\", () => {\n const result = toNativeScript({\n AtLeast: {\n required: 2n,\n scripts: [\n { Signature: { key_hash: keyHash } },\n { Signature: { key_hash: \"b\".repeat(56) } },\n { Signature: { key_hash: \"c\".repeat(56) } },\n ],\n },\n });\n expect(result.__nativeScript.__type).toBe(\"nofk\");\n expect(result.__nativeScript.value.n).toBe(2);\n expect(result.__nativeScript.value.scripts).toHaveLength(3);\n });\n\n test(\"converts Before (TimelockExpiry)\", () => {\n const result = toNativeScript({ Before: { time: 1000n } });\n expect(result.__nativeScript.__type).toBe(\"timelockExpiry\");\n expect(result.__nativeScript.value.slot).toBe(1000);\n });\n\n test(\"converts After (TimelockStart)\", () => {\n const result = toNativeScript({ After: { time: 500n } });\n expect(result.__nativeScript.__type).toBe(\"timelockStart\");\n expect(result.__nativeScript.value.slot).toBe(500);\n });\n\n test(\"converts Script (script hash reference)\", () => {\n const result = toNativeScript({ Script: { script_hash: keyHash } });\n expect(result.__nativeScript.__type).toBe(\"pubkey\");\n expect(result.__nativeScript.value.hash).toBe(keyHash);\n });\n\n test(\"handles deeply nested structures\", () => {\n const result = toNativeScript({\n AllOf: {\n scripts: [\n {\n AtLeast: {\n required: 1n,\n scripts: [\n { Signature: { key_hash: keyHash } },\n {\n AnyOf: {\n scripts: [{ Signature: { key_hash: \"b\".repeat(56) } }],\n },\n },\n ],\n },\n },\n { After: { time: 100n } },\n ],\n },\n });\n expect(result.__nativeScript.__type).toBe(\"all\");\n expect(result.__nativeScript.value.scripts).toHaveLength(2);\n });\n});\n\n// ---------------------------------------------------------------------------\n// completeWithScripts\n// ---------------------------------------------------------------------------\n\ndescribe(\"completeWithScripts\", () => {\n function makeTxBuilder() {\n provideScriptCalls = [];\n const builder: any = {\n provideScript: (script: any) => {\n provideScriptCalls.push(script);\n return builder;\n },\n complete: async () => mockCompletedTx,\n };\n return builder;\n }\n\n test(\"completes without scripts when none provided\", async () => {\n const builder = makeTxBuilder();\n const tx = await completeWithScripts(builder);\n expect(tx).toBe(mockCompletedTx);\n expect(provideScriptCalls).toHaveLength(0);\n });\n\n test(\"completes without scripts when empty array provided\", async () => {\n const builder = makeTxBuilder();\n const tx = await completeWithScripts(builder, []);\n expect(tx).toBe(mockCompletedTx);\n expect(provideScriptCalls).toHaveLength(0);\n });\n\n test(\"attaches scripts before completing\", async () => {\n const builder = makeTxBuilder();\n const keyHash = \"a\".repeat(56);\n const tx = await completeWithScripts(builder, [\n { Signature: { key_hash: keyHash } },\n \"82018200\",\n ]);\n expect(tx).toBe(mockCompletedTx);\n expect(provideScriptCalls).toHaveLength(2);\n });\n\n test(\"propagates ActionError from invalid script input\", async () => {\n const builder = makeTxBuilder();\n await expect(\n completeWithScripts(builder, [\"invalid\"]),\n ).rejects.toMatchObject({ code: \"INVALID_NATIVE_SCRIPT\" });\n });\n\n test(\"retries with addressbook script on missing script hash error\", async () => {\n const keyHash = \"a\".repeat(56);\n const expectedScriptHash = keyHash;\n let attempt = 0;\n provideScriptCalls = [];\n const builder: any = {\n provideScript: (script: any) => {\n provideScriptCalls.push(script);\n return builder;\n },\n complete: async () => {\n attempt++;\n if (attempt === 1) {\n throw new Error(\n `complete: Could not resolve script hash ${expectedScriptHash}`,\n );\n }\n return mockCompletedTx;\n },\n };\n\n const context = {\n sprinkle: {\n addressbook: {\n \"my-multisig\": { Signature: { key_hash: keyHash } },\n },\n },\n settings: {},\n } as any;\n\n const tx = await completeWithScripts(builder, undefined, context);\n expect(tx).toBe(mockCompletedTx);\n expect(attempt).toBe(2);\n expect(provideScriptCalls).toHaveLength(1);\n });\n\n test(\"throws original error when script hash not in addressbook\", async () => {\n const builder: any = {\n provideScript: () => builder,\n complete: async () => {\n throw new Error(\"complete: Could not resolve script hash deadbeef1234\");\n },\n };\n\n const context = {\n sprinkle: {\n addressbook: {\n \"unrelated\": { Signature: { key_hash: \"b\".repeat(56) } },\n },\n },\n settings: {},\n } as any;\n\n await expect(\n completeWithScripts(builder, undefined, context),\n ).rejects.toThrow(\"Could not resolve script hash deadbeef1234\");\n });\n\n test(\"throws original error when no addressbook in context\", async () => {\n const builder: any = {\n provideScript: () => builder,\n complete: async () => {\n throw new Error(\"complete: Could not resolve script hash deadbeef1234\");\n },\n };\n\n await expect(\n completeWithScripts(builder, undefined, undefined),\n ).rejects.toThrow(\"Could not resolve script hash deadbeef1234\");\n });\n\n test(\"throws non-script errors without retry\", async () => {\n const builder: any = {\n provideScript: () => builder,\n complete: async () => {\n throw new Error(\"some other error\");\n },\n };\n\n const context = {\n sprinkle: {\n addressbook: {\n \"my-sig\": { Signature: { key_hash: \"a\".repeat(56) } },\n },\n },\n settings: {},\n } as any;\n\n await expect(\n completeWithScripts(builder, undefined, context),\n ).rejects.toThrow(\"some other error\");\n });\n});\n"],"mappings":"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","ignoreList":[]}
@@ -0,0 +1,365 @@
1
+ function _defineProperty(e, r, t) { return (r = _toPropertyKey(r)) in e ? Object.defineProperty(e, r, { value: t, enumerable: !0, configurable: !0, writable: !0 }) : e[r] = t, e; }
2
+ function _toPropertyKey(t) { var i = _toPrimitive(t, "string"); return "symbol" == typeof i ? i : i + ""; }
3
+ function _toPrimitive(t, r) { if ("object" != typeof t || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != typeof i) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); }
4
+ import { describe, expect, test, mock, beforeEach } from "bun:test";
5
+ import { ActionError } from "../actions/types.js";
6
+
7
+ // ---------------------------------------------------------------------------
8
+ // Mocks
9
+ // ---------------------------------------------------------------------------
10
+
11
+ // Controllable mock state
12
+ let mockBlaze = {};
13
+ let mockIsHot = true;
14
+ let mockBlazeError = null;
15
+ mock.module("../actions/builtin/blaze-helper.js", () => ({
16
+ getBlazeFromContext: async () => {
17
+ if (mockBlazeError) throw mockBlazeError;
18
+ return mockBlaze;
19
+ },
20
+ isHotWallet: () => mockIsHot
21
+ }));
22
+
23
+ // Track calls to blaze transaction builder
24
+ let mintCalls = [];
25
+ let provideScriptCalls = [];
26
+ let payAssetsCalls = [];
27
+ let registerStakeCalls = [];
28
+
29
+ // Mock transaction returned by complete()
30
+ const mockCompletedTx = {
31
+ toCbor: () => "mock-tx-cbor-hex"
32
+ };
33
+
34
+ // Mock transaction builder chain
35
+ function makeTxBuilder() {
36
+ return {
37
+ addMint: (policyId, mints) => {
38
+ mintCalls.push({
39
+ policyId,
40
+ mints
41
+ });
42
+ return makeTxBuilder();
43
+ },
44
+ provideScript: script => {
45
+ provideScriptCalls.push(script);
46
+ return makeTxBuilder();
47
+ },
48
+ payAssets: (address, value) => {
49
+ payAssetsCalls.push({
50
+ address,
51
+ value
52
+ });
53
+ return makeTxBuilder();
54
+ },
55
+ addRegisterStake: credential => {
56
+ registerStakeCalls.push(credential);
57
+ return makeTxBuilder();
58
+ },
59
+ complete: async () => mockCompletedTx
60
+ };
61
+ }
62
+
63
+ // Mock address with payment credential
64
+ function makeMockAddress(hash = "abcd1234abcd1234abcd1234abcd1234abcd1234abcd1234abcd1234") {
65
+ return {
66
+ toBech32: () => "addr_test1qzmock",
67
+ asBase: () => ({
68
+ getPaymentCredential: () => ({
69
+ hash: {
70
+ toString: () => hash
71
+ }
72
+ })
73
+ })
74
+ };
75
+ }
76
+ mock.module("@blaze-cardano/sdk", () => ({
77
+ Core: {
78
+ Ed25519KeyHashHex: h => h,
79
+ ScriptPubkey: class ScriptPubkey {
80
+ constructor(h) {
81
+ _defineProperty(this, "hash", void 0);
82
+ this.hash = h;
83
+ }
84
+ },
85
+ Script: {
86
+ newNativeScript: ns => ({
87
+ hash: () => "mock-policy-id-hash"
88
+ })
89
+ },
90
+ NativeScript: {
91
+ newScriptPubkey: sp => sp
92
+ },
93
+ PolicyId: s => s,
94
+ AssetName: s => s,
95
+ toHex: buf => buf.toString("hex"),
96
+ Address: {
97
+ fromBech32: addr => {
98
+ if (addr === "invalid-address") throw new Error("Invalid bech32");
99
+ return {
100
+ toBech32: () => addr
101
+ };
102
+ }
103
+ },
104
+ TxCBOR: s => s,
105
+ Hash28ByteBase16: s => s,
106
+ Credential: {
107
+ fromCore: c => c
108
+ },
109
+ CredentialType: {
110
+ ScriptHash: 1
111
+ }
112
+ },
113
+ makeValue: (...args) => ({
114
+ __makeValueArgs: args
115
+ }),
116
+ Blaze: class {},
117
+ HotWallet: class {}
118
+ }));
119
+
120
+ // Import actions after mocks are set up
121
+ const {
122
+ mintToken,
123
+ simpleSend,
124
+ registerStakeScript
125
+ } = await import("../actions/builtin/utility-actions.js");
126
+
127
+ // Minimal context factory
128
+ function makeContext(settingsOverrides = {}) {
129
+ return {
130
+ sprinkle: {},
131
+ settings: {
132
+ network: "preview",
133
+ provider: {
134
+ type: "blockfrost",
135
+ apiKey: "test"
136
+ },
137
+ wallet: {
138
+ type: "hot",
139
+ mnemonic: "test words"
140
+ },
141
+ ...settingsOverrides
142
+ }
143
+ };
144
+ }
145
+
146
+ // ---------------------------------------------------------------------------
147
+ // mint-token
148
+ // ---------------------------------------------------------------------------
149
+
150
+ describe("mint-token", () => {
151
+ beforeEach(() => {
152
+ mockBlazeError = null;
153
+ mockIsHot = true;
154
+ mintCalls = [];
155
+ provideScriptCalls = [];
156
+ mockBlaze = {
157
+ wallet: {
158
+ getChangeAddress: async () => makeMockAddress()
159
+ },
160
+ newTransaction: () => makeTxBuilder()
161
+ };
162
+ });
163
+ test("has correct metadata", () => {
164
+ expect(mintToken.name).toBe("mint-token");
165
+ expect(mintToken.category).toBe("utility");
166
+ });
167
+ test("builds a mint transaction and returns policy info", async () => {
168
+ const ctx = makeContext();
169
+ const result = await mintToken.execute({
170
+ tokenName: "MyToken",
171
+ amount: "1000"
172
+ }, ctx);
173
+ expect(result.policyId).toBe("mock-policy-id-hash");
174
+ expect(result.tokenName).toBe("MyToken");
175
+ expect(result.amount).toBe("1000");
176
+ expect(result.txCbor).toBe("mock-tx-cbor-hex");
177
+ expect(mintCalls).toHaveLength(1);
178
+ expect(provideScriptCalls).toHaveLength(1);
179
+ });
180
+ test("throws COLD_WALLET when wallet is not hot", async () => {
181
+ mockIsHot = false;
182
+ const ctx = makeContext();
183
+ await expect(mintToken.execute({
184
+ tokenName: "T",
185
+ amount: "1"
186
+ }, ctx)).rejects.toMatchObject({
187
+ code: "COLD_WALLET"
188
+ });
189
+ });
190
+ test("throws WALLET_NOT_CONFIGURED when blaze init fails", async () => {
191
+ mockBlazeError = new ActionError("Missing settings", "WALLET_NOT_CONFIGURED", {
192
+ missingFields: ["wallet"]
193
+ });
194
+ const ctx = makeContext();
195
+ await expect(mintToken.execute({
196
+ tokenName: "T",
197
+ amount: "1"
198
+ }, ctx)).rejects.toMatchObject({
199
+ code: "WALLET_NOT_CONFIGURED"
200
+ });
201
+ });
202
+ test("throws NO_ADDRESS when getChangeAddress fails", async () => {
203
+ mockBlaze = {
204
+ wallet: {
205
+ getChangeAddress: async () => {
206
+ throw new Error("no address");
207
+ }
208
+ },
209
+ newTransaction: () => makeTxBuilder()
210
+ };
211
+ const ctx = makeContext();
212
+ await expect(mintToken.execute({
213
+ tokenName: "T",
214
+ amount: "1"
215
+ }, ctx)).rejects.toMatchObject({
216
+ code: "NO_ADDRESS"
217
+ });
218
+ });
219
+ test("throws INVALID_ADDRESS when base address is null", async () => {
220
+ mockBlaze = {
221
+ wallet: {
222
+ getChangeAddress: async () => ({
223
+ toBech32: () => "addr_test1...",
224
+ asBase: () => null
225
+ })
226
+ },
227
+ newTransaction: () => makeTxBuilder()
228
+ };
229
+ const ctx = makeContext();
230
+ await expect(mintToken.execute({
231
+ tokenName: "T",
232
+ amount: "1"
233
+ }, ctx)).rejects.toMatchObject({
234
+ code: "INVALID_ADDRESS"
235
+ });
236
+ });
237
+ });
238
+
239
+ // ---------------------------------------------------------------------------
240
+ // simple-send
241
+ // ---------------------------------------------------------------------------
242
+
243
+ describe("simple-send", () => {
244
+ beforeEach(() => {
245
+ mockBlazeError = null;
246
+ mockIsHot = true;
247
+ payAssetsCalls = [];
248
+ mockBlaze = {
249
+ newTransaction: () => makeTxBuilder()
250
+ };
251
+ });
252
+ test("has correct metadata", () => {
253
+ expect(simpleSend.name).toBe("simple-send");
254
+ expect(simpleSend.category).toBe("wallet");
255
+ });
256
+ test("builds a lovelace-only send transaction", async () => {
257
+ const ctx = makeContext();
258
+ const result = await simpleSend.execute({
259
+ recipientAddress: "addr_test1qzrecipient",
260
+ lovelace: "5000000"
261
+ }, ctx);
262
+ expect(result.txCbor).toBe("mock-tx-cbor-hex");
263
+ expect(payAssetsCalls).toHaveLength(1);
264
+ });
265
+ test("builds a token send transaction", async () => {
266
+ const ctx = makeContext();
267
+ const result = await simpleSend.execute({
268
+ recipientAddress: "addr_test1qzrecipient",
269
+ policyId: "a".repeat(56),
270
+ assetName: "4d79546f6b656e",
271
+ tokenAmount: "100"
272
+ }, ctx);
273
+ expect(result.txCbor).toBe("mock-tx-cbor-hex");
274
+ expect(payAssetsCalls).toHaveLength(1);
275
+ });
276
+ test("throws INVALID_INPUT when neither lovelace nor token provided", async () => {
277
+ const ctx = makeContext();
278
+ await expect(simpleSend.execute({
279
+ recipientAddress: "addr_test1qzrecipient"
280
+ }, ctx)).rejects.toMatchObject({
281
+ code: "INVALID_INPUT"
282
+ });
283
+ });
284
+ test("throws INVALID_ADDRESS for bad recipient", async () => {
285
+ const ctx = makeContext();
286
+ await expect(simpleSend.execute({
287
+ recipientAddress: "invalid-address",
288
+ lovelace: "1000000"
289
+ }, ctx)).rejects.toMatchObject({
290
+ code: "INVALID_ADDRESS"
291
+ });
292
+ });
293
+ test("throws WALLET_NOT_CONFIGURED when blaze init fails", async () => {
294
+ mockBlazeError = new ActionError("Missing settings", "WALLET_NOT_CONFIGURED", {
295
+ missingFields: ["wallet"]
296
+ });
297
+ const ctx = makeContext();
298
+ await expect(simpleSend.execute({
299
+ recipientAddress: "addr_test1qz",
300
+ lovelace: "1000000"
301
+ }, ctx)).rejects.toMatchObject({
302
+ code: "WALLET_NOT_CONFIGURED"
303
+ });
304
+ });
305
+ });
306
+
307
+ // ---------------------------------------------------------------------------
308
+ // register-stake-script
309
+ // ---------------------------------------------------------------------------
310
+
311
+ describe("register-stake-script", () => {
312
+ beforeEach(() => {
313
+ mockBlazeError = null;
314
+ mockIsHot = true;
315
+ registerStakeCalls = [];
316
+ mockBlaze = {
317
+ newTransaction: () => makeTxBuilder()
318
+ };
319
+ });
320
+ test("has correct metadata", () => {
321
+ expect(registerStakeScript.name).toBe("register-stake-script");
322
+ expect(registerStakeScript.category).toBe("utility");
323
+ });
324
+ test("builds a stake registration transaction", async () => {
325
+ const validHash = "a".repeat(56);
326
+ const ctx = makeContext();
327
+ const result = await registerStakeScript.execute({
328
+ scriptHash: validHash
329
+ }, ctx);
330
+ expect(result.txCbor).toBe("mock-tx-cbor-hex");
331
+ expect(registerStakeCalls).toHaveLength(1);
332
+ expect(registerStakeCalls[0]).toMatchObject({
333
+ hash: validHash,
334
+ type: 1 // ScriptHash
335
+ });
336
+ });
337
+ test("throws INVALID_SCRIPT_HASH for wrong length", async () => {
338
+ const ctx = makeContext();
339
+ await expect(registerStakeScript.execute({
340
+ scriptHash: "tooshort"
341
+ }, ctx)).rejects.toMatchObject({
342
+ code: "INVALID_SCRIPT_HASH"
343
+ });
344
+ });
345
+ test("throws INVALID_SCRIPT_HASH for non-hex characters", async () => {
346
+ const ctx = makeContext();
347
+ await expect(registerStakeScript.execute({
348
+ scriptHash: "g".repeat(56)
349
+ }, ctx)).rejects.toMatchObject({
350
+ code: "INVALID_SCRIPT_HASH"
351
+ });
352
+ });
353
+ test("throws WALLET_NOT_CONFIGURED when blaze init fails", async () => {
354
+ mockBlazeError = new ActionError("Missing settings", "WALLET_NOT_CONFIGURED", {
355
+ missingFields: ["provider"]
356
+ });
357
+ const ctx = makeContext();
358
+ await expect(registerStakeScript.execute({
359
+ scriptHash: "a".repeat(56)
360
+ }, ctx)).rejects.toMatchObject({
361
+ code: "WALLET_NOT_CONFIGURED"
362
+ });
363
+ });
364
+ });
365
+ //# sourceMappingURL=utility-actions.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"utility-actions.test.js","names":["describe","expect","test","mock","beforeEach","ActionError","mockBlaze","mockIsHot","mockBlazeError","module","getBlazeFromContext","isHotWallet","mintCalls","provideScriptCalls","payAssetsCalls","registerStakeCalls","mockCompletedTx","toCbor","makeTxBuilder","addMint","policyId","mints","push","provideScript","script","payAssets","address","value","addRegisterStake","credential","complete","makeMockAddress","hash","toBech32","asBase","getPaymentCredential","toString","Core","Ed25519KeyHashHex","h","ScriptPubkey","constructor","_defineProperty","Script","newNativeScript","ns","NativeScript","newScriptPubkey","sp","PolicyId","s","AssetName","toHex","buf","Address","fromBech32","addr","Error","TxCBOR","Hash28ByteBase16","Credential","fromCore","c","CredentialType","ScriptHash","makeValue","args","__makeValueArgs","Blaze","HotWallet","mintToken","simpleSend","registerStakeScript","makeContext","settingsOverrides","sprinkle","settings","network","provider","type","apiKey","wallet","mnemonic","getChangeAddress","newTransaction","name","toBe","category","ctx","result","execute","tokenName","amount","txCbor","toHaveLength","rejects","toMatchObject","code","missingFields","recipientAddress","lovelace","repeat","assetName","tokenAmount","validHash","scriptHash"],"sources":["../../../../src/Sprinkle/__tests__/utility-actions.test.ts"],"sourcesContent":["import { describe, expect, test, mock, beforeEach } from \"bun:test\";\nimport { ActionError } from \"../actions/types.js\";\n\n// ---------------------------------------------------------------------------\n// Mocks\n// ---------------------------------------------------------------------------\n\n// Controllable mock state\nlet mockBlaze: any = {};\nlet mockIsHot = true;\nlet mockBlazeError: Error | null = null;\n\nmock.module(\"../actions/builtin/blaze-helper.js\", () => ({\n getBlazeFromContext: async () => {\n if (mockBlazeError) throw mockBlazeError;\n return mockBlaze;\n },\n isHotWallet: () => mockIsHot,\n}));\n\n// Track calls to blaze transaction builder\nlet mintCalls: Array<{ policyId: string; mints: Map<string, bigint> }> = [];\nlet provideScriptCalls: any[] = [];\nlet payAssetsCalls: Array<{ address: any; value: any }> = [];\nlet registerStakeCalls: any[] = [];\n\n// Mock transaction returned by complete()\nconst mockCompletedTx = {\n toCbor: () => \"mock-tx-cbor-hex\",\n};\n\n// Mock transaction builder chain\nfunction makeTxBuilder() {\n return {\n addMint: (policyId: string, mints: Map<string, bigint>) => {\n mintCalls.push({ policyId, mints });\n return makeTxBuilder();\n },\n provideScript: (script: any) => {\n provideScriptCalls.push(script);\n return makeTxBuilder();\n },\n payAssets: (address: any, value: any) => {\n payAssetsCalls.push({ address, value });\n return makeTxBuilder();\n },\n addRegisterStake: (credential: any) => {\n registerStakeCalls.push(credential);\n return makeTxBuilder();\n },\n complete: async () => mockCompletedTx,\n };\n}\n\n// Mock address with payment credential\nfunction makeMockAddress(hash = \"abcd1234abcd1234abcd1234abcd1234abcd1234abcd1234abcd1234\") {\n return {\n toBech32: () => \"addr_test1qzmock\",\n asBase: () => ({\n getPaymentCredential: () => ({\n hash: { toString: () => hash },\n }),\n }),\n };\n}\n\nmock.module(\"@blaze-cardano/sdk\", () => ({\n Core: {\n Ed25519KeyHashHex: (h: string) => h,\n ScriptPubkey: class {\n hash: string;\n constructor(h: string) { this.hash = h; }\n },\n Script: {\n newNativeScript: (ns: any) => ({\n hash: () => \"mock-policy-id-hash\",\n }),\n },\n NativeScript: {\n newScriptPubkey: (sp: any) => sp,\n },\n PolicyId: (s: string) => s,\n AssetName: (s: string) => s,\n toHex: (buf: Buffer) => buf.toString(\"hex\"),\n Address: {\n fromBech32: (addr: string) => {\n if (addr === \"invalid-address\") throw new Error(\"Invalid bech32\");\n return { toBech32: () => addr };\n },\n },\n TxCBOR: (s: string) => s,\n Hash28ByteBase16: (s: string) => s,\n Credential: {\n fromCore: (c: any) => c,\n },\n CredentialType: {\n ScriptHash: 1,\n },\n },\n makeValue: (...args: any[]) => ({ __makeValueArgs: args }),\n Blaze: class {},\n HotWallet: class {},\n}));\n\n// Import actions after mocks are set up\nconst { mintToken, simpleSend, registerStakeScript } = await import(\n \"../actions/builtin/utility-actions.js\"\n);\n\n// Minimal context factory\nfunction makeContext(settingsOverrides: Record<string, unknown> = {}) {\n return {\n sprinkle: {} as any,\n settings: {\n network: \"preview\",\n provider: { type: \"blockfrost\", apiKey: \"test\" },\n wallet: { type: \"hot\", mnemonic: \"test words\" },\n ...settingsOverrides,\n } as any,\n };\n}\n\n// ---------------------------------------------------------------------------\n// mint-token\n// ---------------------------------------------------------------------------\n\ndescribe(\"mint-token\", () => {\n beforeEach(() => {\n mockBlazeError = null;\n mockIsHot = true;\n mintCalls = [];\n provideScriptCalls = [];\n mockBlaze = {\n wallet: {\n getChangeAddress: async () => makeMockAddress(),\n },\n newTransaction: () => makeTxBuilder(),\n };\n });\n\n test(\"has correct metadata\", () => {\n expect(mintToken.name).toBe(\"mint-token\");\n expect(mintToken.category).toBe(\"utility\");\n });\n\n test(\"builds a mint transaction and returns policy info\", async () => {\n const ctx = makeContext();\n const result = await mintToken.execute(\n { tokenName: \"MyToken\", amount: \"1000\" },\n ctx,\n );\n expect(result.policyId).toBe(\"mock-policy-id-hash\");\n expect(result.tokenName).toBe(\"MyToken\");\n expect(result.amount).toBe(\"1000\");\n expect(result.txCbor).toBe(\"mock-tx-cbor-hex\");\n expect(mintCalls).toHaveLength(1);\n expect(provideScriptCalls).toHaveLength(1);\n });\n\n test(\"throws COLD_WALLET when wallet is not hot\", async () => {\n mockIsHot = false;\n const ctx = makeContext();\n await expect(\n mintToken.execute({ tokenName: \"T\", amount: \"1\" }, ctx),\n ).rejects.toMatchObject({ code: \"COLD_WALLET\" });\n });\n\n test(\"throws WALLET_NOT_CONFIGURED when blaze init fails\", async () => {\n mockBlazeError = new ActionError(\n \"Missing settings\",\n \"WALLET_NOT_CONFIGURED\",\n { missingFields: [\"wallet\"] },\n );\n const ctx = makeContext();\n await expect(\n mintToken.execute({ tokenName: \"T\", amount: \"1\" }, ctx),\n ).rejects.toMatchObject({ code: \"WALLET_NOT_CONFIGURED\" });\n });\n\n test(\"throws NO_ADDRESS when getChangeAddress fails\", async () => {\n mockBlaze = {\n wallet: {\n getChangeAddress: async () => {\n throw new Error(\"no address\");\n },\n },\n newTransaction: () => makeTxBuilder(),\n };\n const ctx = makeContext();\n await expect(\n mintToken.execute({ tokenName: \"T\", amount: \"1\" }, ctx),\n ).rejects.toMatchObject({ code: \"NO_ADDRESS\" });\n });\n\n test(\"throws INVALID_ADDRESS when base address is null\", async () => {\n mockBlaze = {\n wallet: {\n getChangeAddress: async () => ({\n toBech32: () => \"addr_test1...\",\n asBase: () => null,\n }),\n },\n newTransaction: () => makeTxBuilder(),\n };\n const ctx = makeContext();\n await expect(\n mintToken.execute({ tokenName: \"T\", amount: \"1\" }, ctx),\n ).rejects.toMatchObject({ code: \"INVALID_ADDRESS\" });\n });\n});\n\n// ---------------------------------------------------------------------------\n// simple-send\n// ---------------------------------------------------------------------------\n\ndescribe(\"simple-send\", () => {\n beforeEach(() => {\n mockBlazeError = null;\n mockIsHot = true;\n payAssetsCalls = [];\n mockBlaze = {\n newTransaction: () => makeTxBuilder(),\n };\n });\n\n test(\"has correct metadata\", () => {\n expect(simpleSend.name).toBe(\"simple-send\");\n expect(simpleSend.category).toBe(\"wallet\");\n });\n\n test(\"builds a lovelace-only send transaction\", async () => {\n const ctx = makeContext();\n const result = await simpleSend.execute(\n { recipientAddress: \"addr_test1qzrecipient\", lovelace: \"5000000\" },\n ctx,\n );\n expect(result.txCbor).toBe(\"mock-tx-cbor-hex\");\n expect(payAssetsCalls).toHaveLength(1);\n });\n\n test(\"builds a token send transaction\", async () => {\n const ctx = makeContext();\n const result = await simpleSend.execute(\n {\n recipientAddress: \"addr_test1qzrecipient\",\n policyId: \"a\".repeat(56),\n assetName: \"4d79546f6b656e\",\n tokenAmount: \"100\",\n },\n ctx,\n );\n expect(result.txCbor).toBe(\"mock-tx-cbor-hex\");\n expect(payAssetsCalls).toHaveLength(1);\n });\n\n test(\"throws INVALID_INPUT when neither lovelace nor token provided\", async () => {\n const ctx = makeContext();\n await expect(\n simpleSend.execute({ recipientAddress: \"addr_test1qzrecipient\" }, ctx),\n ).rejects.toMatchObject({ code: \"INVALID_INPUT\" });\n });\n\n test(\"throws INVALID_ADDRESS for bad recipient\", async () => {\n const ctx = makeContext();\n await expect(\n simpleSend.execute(\n { recipientAddress: \"invalid-address\", lovelace: \"1000000\" },\n ctx,\n ),\n ).rejects.toMatchObject({ code: \"INVALID_ADDRESS\" });\n });\n\n test(\"throws WALLET_NOT_CONFIGURED when blaze init fails\", async () => {\n mockBlazeError = new ActionError(\n \"Missing settings\",\n \"WALLET_NOT_CONFIGURED\",\n { missingFields: [\"wallet\"] },\n );\n const ctx = makeContext();\n await expect(\n simpleSend.execute(\n { recipientAddress: \"addr_test1qz\", lovelace: \"1000000\" },\n ctx,\n ),\n ).rejects.toMatchObject({ code: \"WALLET_NOT_CONFIGURED\" });\n });\n});\n\n// ---------------------------------------------------------------------------\n// register-stake-script\n// ---------------------------------------------------------------------------\n\ndescribe(\"register-stake-script\", () => {\n beforeEach(() => {\n mockBlazeError = null;\n mockIsHot = true;\n registerStakeCalls = [];\n mockBlaze = {\n newTransaction: () => makeTxBuilder(),\n };\n });\n\n test(\"has correct metadata\", () => {\n expect(registerStakeScript.name).toBe(\"register-stake-script\");\n expect(registerStakeScript.category).toBe(\"utility\");\n });\n\n test(\"builds a stake registration transaction\", async () => {\n const validHash = \"a\".repeat(56);\n const ctx = makeContext();\n const result = await registerStakeScript.execute(\n { scriptHash: validHash },\n ctx,\n );\n expect(result.txCbor).toBe(\"mock-tx-cbor-hex\");\n expect(registerStakeCalls).toHaveLength(1);\n expect(registerStakeCalls[0]).toMatchObject({\n hash: validHash,\n type: 1, // ScriptHash\n });\n });\n\n test(\"throws INVALID_SCRIPT_HASH for wrong length\", async () => {\n const ctx = makeContext();\n await expect(\n registerStakeScript.execute({ scriptHash: \"tooshort\" }, ctx),\n ).rejects.toMatchObject({ code: \"INVALID_SCRIPT_HASH\" });\n });\n\n test(\"throws INVALID_SCRIPT_HASH for non-hex characters\", async () => {\n const ctx = makeContext();\n await expect(\n registerStakeScript.execute({ scriptHash: \"g\".repeat(56) }, ctx),\n ).rejects.toMatchObject({ code: \"INVALID_SCRIPT_HASH\" });\n });\n\n test(\"throws WALLET_NOT_CONFIGURED when blaze init fails\", async () => {\n mockBlazeError = new ActionError(\n \"Missing settings\",\n \"WALLET_NOT_CONFIGURED\",\n { missingFields: [\"provider\"] },\n );\n const ctx = makeContext();\n await expect(\n registerStakeScript.execute({ scriptHash: \"a\".repeat(56) }, ctx),\n ).rejects.toMatchObject({ code: \"WALLET_NOT_CONFIGURED\" });\n });\n});\n"],"mappings":"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","ignoreList":[]}
@@ -0,0 +1,159 @@
1
+ /**
2
+ * Built-in addressbook actions for managing named native scripts.
3
+ *
4
+ * The addressbook stores MultisigScript entries by name in the profile,
5
+ * allowing them to be reused across actions and automatically resolved
6
+ * by script hash during transaction building.
7
+ */
8
+
9
+ import { Type } from "@sinclair/typebox";
10
+ import { MultisigScript } from "../../schemas.js";
11
+ import { ActionError } from "../types.js";
12
+ import { toNativeScript } from "./native-script.js";
13
+
14
+ /**
15
+ * `list-addressbook` -- List all entries in the addressbook.
16
+ */
17
+ export const listAddressbook = {
18
+ name: "list-addressbook",
19
+ description: "List all named native scripts in the addressbook.",
20
+ category: "addressbook",
21
+ inputSchema: Type.Object({}),
22
+ outputSchema: Type.Object({
23
+ entries: Type.Array(Type.Object({
24
+ name: Type.String(),
25
+ scriptHash: Type.String(),
26
+ script: MultisigScript
27
+ }))
28
+ }),
29
+ execute: async (_input, context) => {
30
+ const addressbook = context.sprinkle.addressbook ?? {};
31
+ const entries = [];
32
+ for (const [name, ms] of Object.entries(addressbook)) {
33
+ try {
34
+ const script = toNativeScript(ms);
35
+ entries.push({
36
+ name,
37
+ scriptHash: script.hash(),
38
+ script: ms
39
+ });
40
+ } catch {
41
+ // Include entries even if hash computation fails
42
+ entries.push({
43
+ name,
44
+ scriptHash: "unknown",
45
+ script: ms
46
+ });
47
+ }
48
+ }
49
+ return {
50
+ entries
51
+ };
52
+ }
53
+ };
54
+
55
+ /**
56
+ * `set-addressbook-entry` -- Add or update a named native script in the addressbook.
57
+ */
58
+ export const setAddressbookEntry = {
59
+ name: "set-addressbook-entry",
60
+ description: "Add or update a named native script in the addressbook. Accepts a MultisigScript JSON structure.",
61
+ category: "addressbook",
62
+ inputSchema: Type.Object({
63
+ name: Type.String({
64
+ minLength: 1,
65
+ description: "Name for this addressbook entry"
66
+ }),
67
+ script: MultisigScript
68
+ }),
69
+ outputSchema: Type.Object({
70
+ name: Type.String(),
71
+ scriptHash: Type.String({
72
+ description: "Computed script hash"
73
+ })
74
+ }),
75
+ execute: async (input, context) => {
76
+ // Validate the script can be converted
77
+ const blazeScript = toNativeScript(input.script);
78
+ const scriptHash = blazeScript.hash();
79
+ context.sprinkle.addressbook[input.name] = input.script;
80
+ context.sprinkle.saveSettings();
81
+ return {
82
+ name: input.name,
83
+ scriptHash
84
+ };
85
+ }
86
+ };
87
+
88
+ /**
89
+ * `delete-addressbook-entry` -- Remove a named native script from the addressbook.
90
+ */
91
+ export const deleteAddressbookEntry = {
92
+ name: "delete-addressbook-entry",
93
+ description: "Remove a named native script from the addressbook.",
94
+ category: "addressbook",
95
+ inputSchema: Type.Object({
96
+ name: Type.String({
97
+ minLength: 1,
98
+ description: "Name of the addressbook entry to delete"
99
+ })
100
+ }),
101
+ outputSchema: Type.Object({
102
+ deleted: Type.Boolean(),
103
+ name: Type.String()
104
+ }),
105
+ execute: async (input, context) => {
106
+ if (!(input.name in context.sprinkle.addressbook)) {
107
+ throw new ActionError(`Addressbook entry "${input.name}" not found.`, "NOT_FOUND", {
108
+ name: input.name
109
+ });
110
+ }
111
+ delete context.sprinkle.addressbook[input.name];
112
+ context.sprinkle.saveSettings();
113
+ return {
114
+ deleted: true,
115
+ name: input.name
116
+ };
117
+ }
118
+ };
119
+
120
+ /**
121
+ * `get-addressbook-entry` -- Get a specific named native script from the addressbook.
122
+ */
123
+ export const getAddressbookEntry = {
124
+ name: "get-addressbook-entry",
125
+ description: "Get a specific named native script from the addressbook.",
126
+ category: "addressbook",
127
+ inputSchema: Type.Object({
128
+ name: Type.String({
129
+ minLength: 1,
130
+ description: "Name of the addressbook entry to retrieve"
131
+ })
132
+ }),
133
+ outputSchema: Type.Object({
134
+ name: Type.String(),
135
+ scriptHash: Type.String(),
136
+ script: MultisigScript
137
+ }),
138
+ execute: async (input, context) => {
139
+ const ms = context.sprinkle.addressbook[input.name];
140
+ if (!ms) {
141
+ throw new ActionError(`Addressbook entry "${input.name}" not found.`, "NOT_FOUND", {
142
+ name: input.name
143
+ });
144
+ }
145
+ let scriptHash = "unknown";
146
+ try {
147
+ const blazeScript = toNativeScript(ms);
148
+ scriptHash = blazeScript.hash();
149
+ } catch {
150
+ // Return entry even if hash computation fails
151
+ }
152
+ return {
153
+ name: input.name,
154
+ scriptHash,
155
+ script: ms
156
+ };
157
+ }
158
+ };
159
+ //# sourceMappingURL=addressbook-actions.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"addressbook-actions.js","names":["Type","MultisigScript","ActionError","toNativeScript","listAddressbook","name","description","category","inputSchema","Object","outputSchema","entries","Array","String","scriptHash","script","execute","_input","context","addressbook","sprinkle","ms","push","hash","setAddressbookEntry","minLength","input","blazeScript","saveSettings","deleteAddressbookEntry","deleted","Boolean","getAddressbookEntry"],"sources":["../../../../../src/Sprinkle/actions/builtin/addressbook-actions.ts"],"sourcesContent":["/**\n * Built-in addressbook actions for managing named native scripts.\n *\n * The addressbook stores MultisigScript entries by name in the profile,\n * allowing them to be reused across actions and automatically resolved\n * by script hash during transaction building.\n */\n\nimport { Type } from \"@sinclair/typebox\";\nimport type { TSchema } from \"@sinclair/typebox\";\nimport { MultisigScript } from \"../../schemas.js\";\nimport type { TMultisigScript } from \"../../schemas.js\";\nimport { ActionError } from \"../types.js\";\nimport type { IAction } from \"../types.js\";\nimport { toNativeScript } from \"./native-script.js\";\n\n/**\n * `list-addressbook` -- List all entries in the addressbook.\n */\nexport const listAddressbook: IAction<\n Record<string, never>,\n { entries: Array<{ name: string; scriptHash: string; script: TMultisigScript }> },\n TSchema\n> = {\n name: \"list-addressbook\",\n description: \"List all named native scripts in the addressbook.\",\n category: \"addressbook\",\n inputSchema: Type.Object({}),\n outputSchema: Type.Object({\n entries: Type.Array(\n Type.Object({\n name: Type.String(),\n scriptHash: Type.String(),\n script: MultisigScript,\n }),\n ),\n }),\n execute: async (_input, context) => {\n const addressbook = context.sprinkle.addressbook ?? {};\n const entries = [];\n for (const [name, ms] of Object.entries(addressbook)) {\n try {\n const script = toNativeScript(ms);\n entries.push({ name, scriptHash: script.hash(), script: ms });\n } catch {\n // Include entries even if hash computation fails\n entries.push({ name, scriptHash: \"unknown\", script: ms });\n }\n }\n return { entries };\n },\n};\n\n/**\n * `set-addressbook-entry` -- Add or update a named native script in the addressbook.\n */\nexport const setAddressbookEntry: IAction<\n { name: string; script: TMultisigScript },\n { name: string; scriptHash: string },\n TSchema\n> = {\n name: \"set-addressbook-entry\",\n description:\n \"Add or update a named native script in the addressbook. Accepts a MultisigScript JSON structure.\",\n category: \"addressbook\",\n inputSchema: Type.Object({\n name: Type.String({\n minLength: 1,\n description: \"Name for this addressbook entry\",\n }),\n script: MultisigScript,\n }),\n outputSchema: Type.Object({\n name: Type.String(),\n scriptHash: Type.String({ description: \"Computed script hash\" }),\n }),\n execute: async (input, context) => {\n // Validate the script can be converted\n const blazeScript = toNativeScript(input.script);\n const scriptHash = blazeScript.hash();\n\n context.sprinkle.addressbook[input.name] = input.script;\n context.sprinkle.saveSettings();\n\n return { name: input.name, scriptHash };\n },\n};\n\n/**\n * `delete-addressbook-entry` -- Remove a named native script from the addressbook.\n */\nexport const deleteAddressbookEntry: IAction<\n { name: string },\n { deleted: boolean; name: string },\n TSchema\n> = {\n name: \"delete-addressbook-entry\",\n description: \"Remove a named native script from the addressbook.\",\n category: \"addressbook\",\n inputSchema: Type.Object({\n name: Type.String({\n minLength: 1,\n description: \"Name of the addressbook entry to delete\",\n }),\n }),\n outputSchema: Type.Object({\n deleted: Type.Boolean(),\n name: Type.String(),\n }),\n execute: async (input, context) => {\n if (!(input.name in context.sprinkle.addressbook)) {\n throw new ActionError(\n `Addressbook entry \"${input.name}\" not found.`,\n \"NOT_FOUND\",\n { name: input.name },\n );\n }\n\n delete context.sprinkle.addressbook[input.name];\n context.sprinkle.saveSettings();\n\n return { deleted: true, name: input.name };\n },\n};\n\n/**\n * `get-addressbook-entry` -- Get a specific named native script from the addressbook.\n */\nexport const getAddressbookEntry: IAction<\n { name: string },\n { name: string; scriptHash: string; script: TMultisigScript },\n TSchema\n> = {\n name: \"get-addressbook-entry\",\n description: \"Get a specific named native script from the addressbook.\",\n category: \"addressbook\",\n inputSchema: Type.Object({\n name: Type.String({\n minLength: 1,\n description: \"Name of the addressbook entry to retrieve\",\n }),\n }),\n outputSchema: Type.Object({\n name: Type.String(),\n scriptHash: Type.String(),\n script: MultisigScript,\n }),\n execute: async (input, context) => {\n const ms = context.sprinkle.addressbook[input.name];\n if (!ms) {\n throw new ActionError(\n `Addressbook entry \"${input.name}\" not found.`,\n \"NOT_FOUND\",\n { name: input.name },\n );\n }\n\n let scriptHash = \"unknown\";\n try {\n const blazeScript = toNativeScript(ms);\n scriptHash = blazeScript.hash();\n } catch {\n // Return entry even if hash computation fails\n }\n\n return { name: input.name, scriptHash, script: ms };\n },\n};\n"],"mappings":"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","ignoreList":[]}