@terminal3/t3n-sdk 0.13.1 → 1.0.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.
@@ -0,0 +1,59 @@
1
+ /**
2
+ * Contract response decoding for {@link T3nClient.execute}.
3
+ *
4
+ * ## On-wire shape
5
+ *
6
+ * Trinity contracts are declared as `result<list<u8>, string>` in WIT and
7
+ * return JSON-encoded bytes. The server-side pipeline is:
8
+ *
9
+ * 1. `node/wasm/src/dynamic.rs:component_val_to_json` deserializes those
10
+ * bytes to a JSON `Value` (the contract's decoded return value).
11
+ * 2. `node/wasm/src/runner.rs:run_dynamic` wraps that value in a
12
+ * `ContractResponse` struct internally for host-side bookkeeping —
13
+ * it carries an extracted `otp_state` alongside the response.
14
+ * 3. **`node/app/src/services/wasm.rs:200`** then unwraps the struct with
15
+ * `Ok((response.response, tx_back))`, discarding the `otp_state` field
16
+ * and returning only the inner `Value` across the `WasmExecutor` trait
17
+ * boundary.
18
+ * 4. `node/service/src/action.rs` serialises that plain `Value` through
19
+ * the session channel.
20
+ *
21
+ * The client therefore receives the contract's **decoded JSON value
22
+ * directly** — no `{response, otp_state}` envelope, despite what the
23
+ * struct name suggests. `parseContractResponse` reflects that reality:
24
+ * it does a typed `JSON.parse` with optional schema validation, nothing
25
+ * more. OTP flows read their `otp_status` / OTP fields directly off the
26
+ * contract's response body; there is no separate envelope field for them
27
+ * on this path.
28
+ */
29
+ import { T3nError } from "../utils/errors";
30
+ /**
31
+ * Minimal validator interface. Any library that exposes `.parse(value) -> T`
32
+ * (zod, valibot, superstruct, custom) is compatible.
33
+ */
34
+ export interface ContractResponseSchema<T> {
35
+ parse(value: unknown): T;
36
+ }
37
+ /**
38
+ * Thrown when the response string from {@link T3nClient.execute} cannot
39
+ * be parsed as JSON.
40
+ *
41
+ * Schema-validation failures are NOT wrapped — they surface as whatever
42
+ * error the caller's validator throws, preserving the rich diagnostics
43
+ * those libraries already provide.
44
+ */
45
+ export declare class ContractResponseError extends T3nError {
46
+ readonly raw?: string | undefined;
47
+ constructor(message: string, raw?: string | undefined);
48
+ }
49
+ /**
50
+ * Parse the JSON-encoded response returned by {@link T3nClient.execute}
51
+ * into a typed value.
52
+ *
53
+ * @param raw - the string returned by {@link T3nClient.execute}
54
+ * @param schema - optional validator applied to the parsed value
55
+ * @returns the decoded response, typed as `T`
56
+ * @throws {ContractResponseError} when `raw` is not valid JSON
57
+ * @throws whatever the schema throws on validation failure (e.g. `ZodError`)
58
+ */
59
+ export declare function parseContractResponse<T = unknown>(raw: string, schema?: ContractResponseSchema<T>): T;
@@ -8,3 +8,4 @@ export * from "./handlers";
8
8
  export * from "./encryption";
9
9
  export * from "./actions";
10
10
  export * from "./request-parser";
11
+ export * from "./contract-response";
@@ -5,6 +5,7 @@
5
5
  * All cryptographic complexity is handled in WASM components.
6
6
  */
7
7
  import { T3nClientConfig } from "./config";
8
+ import { type ContractResponseSchema } from "./contract-response";
8
9
  import { SessionId, Did, SessionStatus, AuthInput, HandshakeResult } from "../types";
9
10
  /**
10
11
  * Main T3n SDK Client
@@ -83,9 +84,48 @@ export declare class T3nClient {
83
84
  */
84
85
  private authenticateOidc;
85
86
  /**
86
- * Execute an action on the T3n node
87
+ * Execute an action on the T3n node.
88
+ *
89
+ * Returns the JSON-stringified contract response. Most callers should
90
+ * prefer {@link executeAndDecode}, which JSON-parses the response and
91
+ * optionally validates it with a schema.
87
92
  */
88
93
  execute(payload: unknown): Promise<string>;
94
+ /**
95
+ * Execute an action and JSON-decode the response.
96
+ *
97
+ * The server strips its internal `ContractResponse` wrapper at
98
+ * `node/app/src/services/wasm.rs` before sending — the string returned
99
+ * by {@link execute} is the contract's decoded return value directly
100
+ * (no `{response, otp_state}` envelope). This helper is a typed
101
+ * `JSON.parse` with optional schema validation so callers stop
102
+ * reimplementing it at every call site.
103
+ *
104
+ * @param payload - action payload, identical to {@link execute}
105
+ * @param schema - optional validator applied to the parsed value
106
+ * (e.g. a zod schema); anything exposing `.parse(value)` is accepted
107
+ * @returns the decoded response, typed as `T`
108
+ * @throws {ContractResponseError} when the response is not valid JSON
109
+ */
110
+ executeAndDecode<T = unknown>(payload: unknown, schema?: ContractResponseSchema<T>): Promise<T>;
111
+ /**
112
+ * Return the authenticated user's Ethereum address from their
113
+ * T3N-hosted per-user wallet, as a 0x-prefixed lowercase hex string.
114
+ * Returns `null` if the user has no wallet yet (pre-backfill edge
115
+ * case — `tee:user` has not yet been migrated for this DID).
116
+ *
117
+ * Backed by the `tee:user/get-self-eth-address` contract function,
118
+ * which delegates to the signing host's `get-user-eth-address`
119
+ * primitive (T3-TS-027 §7.1). The request carries no body; the
120
+ * authenticated user's DID is read from session context by the host.
121
+ *
122
+ * Requires the session to be Authenticated (same precondition as
123
+ * {@link execute}).
124
+ *
125
+ * @throws if unauthenticated, if the node rejects the action, or if
126
+ * the response is not a JSON string / `null`.
127
+ */
128
+ getSelfEthAddress(): Promise<string | null>;
89
129
  /**
90
130
  * The server-minted session ID once handshake has completed, or
91
131
  * `null` beforehand (pentest M-1 / MAT-983).
@@ -8,6 +8,8 @@
8
8
  export { T3nClient } from "./client";
9
9
  export type { T3nClientConfig } from "./client";
10
10
  export type { HandshakeResult } from "./types";
11
+ export { parseContractResponse, ContractResponseError, } from "./client";
12
+ export type { ContractResponseSchema, } from "./client";
11
13
  export type { Logger } from "./utils/logger";
12
14
  export { LogLevel, createLogger, getLogger, setGlobalLogLevel, getGlobalLogLevel, } from "./utils/logger";
13
15
  export type { Transport, JsonRpcRequest, JsonRpcResponse } from "./client";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@terminal3/t3n-sdk",
3
- "version": "0.13.1",
3
+ "version": "1.0.0",
4
4
  "type": "module",
5
5
  "description": "T3n TypeScript SDK - A minimal SDK that mirrors the server's RPC handler approach",
6
6
  "main": "dist/index.js",