@edge-protocol/sdk 0.8.0 → 0.9.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 ADDED
@@ -0,0 +1,110 @@
1
+ # Changelog
2
+
3
+ All notable changes to `@edge-protocol/sdk` are documented here.
4
+
5
+ ---
6
+
7
+ ## [0.8.0] — 2026-06-20
8
+
9
+ ### Added
10
+
11
+ - **`sdk.simulate(pass, requests[])`** — predict outcomes for a sequence of transactions without executing. Zero network calls. Returns `SimulationResult` with approved, blocked, and escalated decisions plus projected budget state after each step. Use to show agents their plan before touching the chain.
12
+
13
+ - **`sdk.budgetStatus(pass)`** — returns a complete `BudgetStatus` snapshot: spent, remaining, utilization percentage, `isNearLimit`, `isExhausted`.
14
+
15
+ - **`sdk.utilizationPct(pass)`** — budget utilization as 0-100 number. Use for progress bars and budget warnings.
16
+
17
+ - **`sdk.isNearLimit(pass, threshold?)`** — returns true if utilization exceeds threshold (default 80%). Use to warn agents before they exhaust budget.
18
+
19
+ - **`sdk.timeRemaining(pass)`** — milliseconds until pass expires. Returns 0 if expired.
20
+
21
+ - **`sdk.isExpiringSoon(pass, withinMs?)`** — returns true if pass expires within the given window (default 1 hour).
22
+
23
+ - **`EdgePass.withPolicy(pass, signer, sdk, fn)`** — higher-order function that wraps any async tool call with EdgePass policy enforcement. The wrapped function only executes if the transaction is approved. Perfect for Vercel AI SDK / Mastra tool definitions.
24
+
25
+ - **New types exported:** `SimulatedDecision`, `SimulationResult`, `BudgetStatus`
26
+
27
+ ### Changed
28
+
29
+ - `PolicyEngine.simulate()` is now a static method on `PolicyEngine` and also exposed as `sdk.simulate()` on the `EdgePass` class for convenience.
30
+ - All budget and time helpers are now available both as static `PolicyEngine` methods and instance `sdk` methods.
31
+
32
+ ---
33
+
34
+ ## [0.7.1] — 2026-06-19
35
+
36
+ ### Fixed
37
+
38
+ - Reverted `tx.objectRef()` optimization from v0.7.0. While theoretically faster, storing object version at fetch time caused version conflicts when Enoki gas sponsorship updated the object between fetch and execution. `tx.object(pass.id)` resolves version at signing time which is the correct and safe pattern.
39
+
40
+ ---
41
+
42
+ ## [0.7.0] — 2026-06-19 — YANKED
43
+
44
+ Version yanked due to object version conflict regression. Use 0.7.1 instead.
45
+
46
+ ---
47
+
48
+ ## [0.6.6] — 2026-06-18
49
+
50
+ ### Changed
51
+
52
+ - Updated README with mainnet contract address and live transaction digests
53
+ - Stronger competitive positioning and security model documentation
54
+
55
+ ---
56
+
57
+ ## [0.6.0] — 2026-06-17
58
+
59
+ ### Added
60
+
61
+ - **Error status as a distinct fourth outcome** — infrastructure failures (`status: 'error'`) are now clearly distinguished from policy rejections (`status: 'blocked'`). A network failure no longer pretends to be a policy decision.
62
+ - **`classifyError()`** — internal error classifier that maps RPC/network/signing errors to typed `EdgeErrorCode` values for programmatic handling.
63
+ - **`fetchPass()` validation** — validates objectId format before hitting the RPC. Throws with a clear message for malformed IDs rather than a cryptic RPC error.
64
+ - **Config validation on `create()`** — prevents impossible EdgePass configurations (e.g. autoThreshold >= escalateThreshold) at creation time rather than at execution time.
65
+
66
+ ---
67
+
68
+ ## [0.5.0] — 2026-06-16
69
+
70
+ ### Added
71
+
72
+ - **Events system** — `sdk.on('approved')`, `sdk.on('escalated')`, `sdk.on('blocked')`. React to transaction outcomes without polling. Chain-able.
73
+ - `sdk.off()` and `sdk.removeAllListeners()` for cleanup.
74
+ - 34 comprehensive tests — PolicyEngine, fromTemplate, constants, events system.
75
+
76
+ ### Changed
77
+
78
+ - Events fire for policy outcomes only (`approved`, `escalated`, `blocked`). Infrastructure errors (`status: 'error'`) do not fire events — check `outcome.status === 'error'` explicitly.
79
+
80
+ ---
81
+
82
+ ## [0.4.7] — 2026-06-15
83
+
84
+ ### Added
85
+
86
+ - Comprehensive `DOCS.md` — full API reference, examples, types, architecture.
87
+ - `maxPerTransaction` field on `EdgePassConfig` — optional per-transaction cap independent of escalation threshold.
88
+
89
+ ---
90
+
91
+ ## [0.4.6] — 2026-06-14
92
+
93
+ ### Added
94
+
95
+ - 27 comprehensive tests — PolicyEngine validation, `fromTemplate()`, constants.
96
+ - `EDGE_TEMPLATES` constants for festival, gaming, subscription, defi, enterprise.
97
+ - `EdgePass.fromTemplate()` static helper.
98
+
99
+ ---
100
+
101
+ ## [0.4.0] — 2026-06-13
102
+
103
+ ### Added
104
+
105
+ - Initial public release.
106
+ - `EdgePass` class with `create()`, `execute()`, `validate()`, `fetch()`, `revoke()`.
107
+ - `PolicyEngine` with 7-rule validation chain.
108
+ - `ExecutionEngine` with on-chain PTB construction.
109
+ - Mainnet + testnet support.
110
+ - zkLogin compatible signer interface.
@@ -0,0 +1,29 @@
1
+ import { Transaction } from '@mysten/sui/transactions';
2
+ import { EdgePass } from '../core/EdgePass';
3
+ import { EdgePassObject, TransactionRequest, TransactionOutcome, SimulationResult, BudgetStatus, Network } from '../utils/types';
4
+ export interface UseEdgePassConfig {
5
+ passId: string;
6
+ network: Network;
7
+ enokiApiKey: string;
8
+ signer?: {
9
+ signAndExecute: (tx: Transaction) => Promise<{
10
+ digest: string;
11
+ }>;
12
+ };
13
+ autoRefresh?: boolean;
14
+ pollInterval?: number;
15
+ }
16
+ export interface UseEdgePassResult {
17
+ pass: EdgePassObject | null;
18
+ loading: boolean;
19
+ error: Error | null;
20
+ execute: (request: TransactionRequest) => Promise<TransactionOutcome>;
21
+ simulate: (requests: TransactionRequest[]) => SimulationResult | null;
22
+ budgetStatus: BudgetStatus | null;
23
+ refresh: () => Promise<void>;
24
+ sdk: EdgePass;
25
+ }
26
+ export declare function useEdgePass({ passId, network, enokiApiKey, signer, autoRefresh, pollInterval, }: UseEdgePassConfig): UseEdgePassResult;
27
+ export declare function useBudgetStatus(config: UseEdgePassConfig): BudgetStatus | null;
28
+ export declare function useSimulate(config: UseEdgePassConfig, requests: TransactionRequest[]): SimulationResult | null;
29
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/react/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AACvD,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAC5C,OAAO,EACL,cAAc,EACd,kBAAkB,EAClB,kBAAkB,EAClB,gBAAgB,EAChB,YAAY,EACZ,OAAO,EACR,MAAM,gBAAgB,CAAC;AAExB,MAAM,WAAW,iBAAiB;IAChC,MAAM,EAAS,MAAM,CAAC;IACtB,OAAO,EAAQ,OAAO,CAAC;IACvB,WAAW,EAAI,MAAM,CAAC;IACtB,MAAM,CAAC,EAAQ;QAAE,cAAc,EAAE,CAAC,EAAE,EAAE,WAAW,KAAK,OAAO,CAAC;YAAE,MAAM,EAAE,MAAM,CAAA;SAAE,CAAC,CAAA;KAAE,CAAC;IACpF,WAAW,CAAC,EAAG,OAAO,CAAC;IACvB,YAAY,CAAC,EAAE,MAAM,CAAC;CACvB;AAED,MAAM,WAAW,iBAAiB;IAChC,IAAI,EAAU,cAAc,GAAG,IAAI,CAAC;IACpC,OAAO,EAAO,OAAO,CAAC;IACtB,KAAK,EAAS,KAAK,GAAG,IAAI,CAAC;IAC3B,OAAO,EAAO,CAAC,OAAO,EAAE,kBAAkB,KAAK,OAAO,CAAC,kBAAkB,CAAC,CAAC;IAC3E,QAAQ,EAAM,CAAC,QAAQ,EAAE,kBAAkB,EAAE,KAAK,gBAAgB,GAAG,IAAI,CAAC;IAC1E,YAAY,EAAE,YAAY,GAAG,IAAI,CAAC;IAClC,OAAO,EAAO,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAClC,GAAG,EAAW,QAAQ,CAAC;CACxB;AAED,wBAAgB,WAAW,CAAC,EAC1B,MAAM,EACN,OAAO,EACP,WAAW,EACX,MAAM,EACN,WAAkB,EAClB,YAAgB,GACjB,EAAE,iBAAiB,GAAG,iBAAiB,CAsDvC;AAED,wBAAgB,eAAe,CAAC,MAAM,EAAE,iBAAiB,GAAG,YAAY,GAAG,IAAI,CAG9E;AAED,wBAAgB,WAAW,CACzB,MAAM,EAAE,iBAAiB,EACzB,QAAQ,EAAE,kBAAkB,EAAE,GAC7B,gBAAgB,GAAG,IAAI,CAGzB"}
@@ -0,0 +1,74 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.useEdgePass = useEdgePass;
4
+ exports.useBudgetStatus = useBudgetStatus;
5
+ exports.useSimulate = useSimulate;
6
+ const react_1 = require("react");
7
+ const EdgePass_1 = require("../core/EdgePass");
8
+ function useEdgePass({ passId, network, enokiApiKey, signer, autoRefresh = true, pollInterval = 0, }) {
9
+ const [pass, setPass] = (0, react_1.useState)(null);
10
+ const [loading, setLoading] = (0, react_1.useState)(true);
11
+ const [error, setError] = (0, react_1.useState)(null);
12
+ const sdkRef = (0, react_1.useRef)(new EdgePass_1.EdgePass({ network, enokiApiKey }));
13
+ (0, react_1.useEffect)(() => {
14
+ sdkRef.current = new EdgePass_1.EdgePass({ network, enokiApiKey });
15
+ }, [network, enokiApiKey]);
16
+ const refresh = (0, react_1.useCallback)(async () => {
17
+ if (!passId)
18
+ return;
19
+ try {
20
+ setError(null);
21
+ const fetched = await sdkRef.current.fetch(passId);
22
+ setPass(fetched);
23
+ }
24
+ catch (e) {
25
+ setError(e instanceof Error ? e : new Error(String(e)));
26
+ }
27
+ }, [passId]);
28
+ (0, react_1.useEffect)(() => {
29
+ let cancelled = false;
30
+ setLoading(true);
31
+ sdkRef.current.fetch(passId)
32
+ .then(fetched => { if (!cancelled) {
33
+ setPass(fetched);
34
+ setError(null);
35
+ } })
36
+ .catch(e => { if (!cancelled)
37
+ setError(e instanceof Error ? e : new Error(String(e))); })
38
+ .finally(() => { if (!cancelled)
39
+ setLoading(false); });
40
+ return () => { cancelled = true; };
41
+ }, [passId]);
42
+ (0, react_1.useEffect)(() => {
43
+ if (!pollInterval || pollInterval <= 0)
44
+ return;
45
+ const interval = setInterval(refresh, pollInterval);
46
+ return () => clearInterval(interval);
47
+ }, [refresh, pollInterval]);
48
+ const execute = (0, react_1.useCallback)(async (request) => {
49
+ if (!pass)
50
+ throw new Error('EdgePass not loaded');
51
+ if (!signer)
52
+ throw new Error('No signer provided');
53
+ const outcome = await sdkRef.current.execute(pass, request, signer);
54
+ if (outcome.status === 'approved' && autoRefresh)
55
+ await refresh();
56
+ return outcome;
57
+ }, [pass, signer, autoRefresh, refresh]);
58
+ const simulate = (0, react_1.useCallback)((requests) => {
59
+ if (!pass)
60
+ return null;
61
+ return sdkRef.current.simulate(pass, requests);
62
+ }, [pass]);
63
+ const budgetStatus = pass ? sdkRef.current.budgetStatus(pass) : null;
64
+ return { pass, loading, error, execute, simulate, budgetStatus, refresh, sdk: sdkRef.current };
65
+ }
66
+ function useBudgetStatus(config) {
67
+ const { budgetStatus } = useEdgePass(config);
68
+ return budgetStatus;
69
+ }
70
+ function useSimulate(config, requests) {
71
+ const { simulate } = useEdgePass(config);
72
+ return simulate(requests);
73
+ }
74
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/react/index.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,13 +1,24 @@
1
1
  {
2
2
  "name": "@edge-protocol/sdk",
3
- "version": "0.8.0",
3
+ "version": "0.9.0",
4
4
  "description": "Programmable trust infrastructure for autonomous AI agents on Sui. Give agents your rules, not your keys.",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
7
+ "exports": {
8
+ ".": {
9
+ "require": "./dist/index.js",
10
+ "types": "./dist/index.d.ts"
11
+ },
12
+ "./react": {
13
+ "require": "./dist/react/index.js",
14
+ "types": "./dist/react/index.d.ts"
15
+ }
16
+ },
7
17
  "files": [
8
18
  "dist",
9
19
  "README.md",
10
- "DOCS.md"
20
+ "DOCS.md",
21
+ "CHANGELOG.md"
11
22
  ],
12
23
  "scripts": {
13
24
  "build": "tsc",
@@ -15,51 +26,22 @@
15
26
  "test": "ts-node --compiler-options '{\"module\":\"CommonJS\"}' src/test.ts",
16
27
  "prepublishOnly": "pnpm build"
17
28
  },
18
- "keywords": [
19
- "sui",
20
- "sui-sdk",
21
- "zklogin",
22
- "autonomous-agents",
23
- "ai-agents",
24
- "trust-delegation",
25
- "edgepass",
26
- "walrus",
27
- "defi",
28
- "web3",
29
- "blockchain",
30
- "move",
31
- "move-language",
32
- "ptb",
33
- "programmable-transaction",
34
- "agent-policy",
35
- "spending-limits",
36
- "crypto-agents",
37
- "agentic-web",
38
- "autonomous",
39
- "trust",
40
- "delegation",
41
- "agent",
42
- "mysten",
43
- "enoki",
44
- "sponsored-transactions"
45
- ],
46
- "author": "fluturecode",
47
- "license": "MIT",
48
- "repository": {
49
- "type": "git",
50
- "url": "https://github.com/fluturecode/edge"
51
- },
52
- "homepage": "https://github.com/fluturecode/edge#readme",
53
- "bugs": {
54
- "url": "https://github.com/fluturecode/edge/issues"
55
- },
56
29
  "dependencies": {
57
30
  "@mysten/sui": "^1.30.0",
58
31
  "@mysten/zklogin": "^0.8.1"
59
32
  },
33
+ "peerDependencies": {
34
+ "react": ">=18.0.0"
35
+ },
36
+ "peerDependenciesMeta": {
37
+ "react": {
38
+ "optional": true
39
+ }
40
+ },
60
41
  "devDependencies": {
61
42
  "@types/node": "^20.19.41",
43
+ "@types/react": "^18.3.31",
62
44
  "ts-node": "^10.9.2",
63
45
  "typescript": "^5.9.3"
64
46
  }
65
- }
47
+ }