@thru/abi 0.1.29 → 0.1.33
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/README.md +72 -135
- package/dist/index.d.ts +67 -181
- package/dist/index.js +150 -1058
- package/dist/index.js.map +1 -1
- package/package.json +9 -9
- package/scripts/copy-wasm.mjs +20 -0
- package/scripts/sync-wasm.mjs +24 -0
- package/scripts/update-layout-ir.ts +132 -0
- package/src/index.ts +12 -15
- package/src/types.ts +27 -0
- package/src/utils/bytes.ts +38 -0
- package/src/utils/runtime.ts +3 -0
- package/src/wasmBridge.ts +245 -0
- package/test/wasm/bridge.test.ts +134 -0
- package/tsconfig.json +2 -2
- package/src/abiSchema.ts +0 -525
- package/src/decodedValue.ts +0 -69
- package/src/decoder.ts +0 -572
- package/src/errors.ts +0 -32
- package/src/expression.ts +0 -165
- package/src/index.test.ts +0 -249
- package/src/typeRegistry.ts +0 -172
- package/test/decode-examples.ts +0 -109
package/README.md
CHANGED
|
@@ -1,174 +1,111 @@
|
|
|
1
|
-
# @thru/abi –
|
|
1
|
+
# @thru/abi – WASM-backed ABI reflection
|
|
2
2
|
|
|
3
|
-
This package
|
|
4
|
-
|
|
5
|
-
|
|
3
|
+
This package is now a thin TypeScript wrapper around the Rust `abi_reflect`
|
|
4
|
+
runtime. We compile the Rust crate to WebAssembly, ship both Node + bundler
|
|
5
|
+
targets, and expose a small async API for reflecting ABI YAML + binary payloads.
|
|
6
|
+
All layout math and validation run inside the Rust engine so TypeScript stays
|
|
7
|
+
lightweight and automatically inherits IR upgrades.
|
|
6
8
|
|
|
7
9
|
---
|
|
8
10
|
|
|
9
|
-
## Quick
|
|
11
|
+
## Quick start
|
|
10
12
|
|
|
11
13
|
```ts
|
|
12
|
-
import {
|
|
13
|
-
import
|
|
14
|
+
import { ensureWasmLoaded, formatReflection, reflect } from "@thru/abi";
|
|
15
|
+
import tokenAbi from "./abi/token_program.abi.yaml?raw";
|
|
14
16
|
|
|
15
|
-
|
|
17
|
+
async function example() {
|
|
18
|
+
await ensureWasmLoaded(); // formatter + reflector live inside WASM
|
|
16
19
|
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
20
|
+
const payload = new Uint8Array([0x01, 0, 0, 0, 0, 0, 0, 0]);
|
|
21
|
+
const reflection = await reflect(tokenAbi, "TokenInstruction", {
|
|
22
|
+
type: "binary",
|
|
23
|
+
value: payload,
|
|
24
|
+
});
|
|
21
25
|
|
|
22
|
-
|
|
23
|
-
* `yamlText` **must be flattened** (imports already resolved). This is enforced at parse time.
|
|
24
|
-
* The returned `DecodedValue` tree contains both semantic data and raw byte slices for UI inspection.
|
|
26
|
+
console.log(reflection.value); // JSON emitted by abi_reflect
|
|
25
27
|
|
|
26
|
-
|
|
28
|
+
// Collapse the verbose JSON tree into something human-readable
|
|
29
|
+
const formatted = formatReflection(reflection);
|
|
30
|
+
console.log(formatted.value.payload.variant); // "initialize_mint"
|
|
31
|
+
}
|
|
27
32
|
|
|
28
|
-
|
|
33
|
+
example();
|
|
34
|
+
```
|
|
29
35
|
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
| `src/decoder.ts` | Core reflection engine. Handles arrays, structs, unions, enums, SDUs, padding, f16, etc. |
|
|
35
|
-
| `src/expression.ts` | Evaluates ABI expressions (field refs, arithmetic, bitwise, sizeof/alignof). |
|
|
36
|
-
| `src/decodedValue.ts` | Canonical decoded shape consumed by Explorer UI. |
|
|
37
|
-
| `test/` | Hand-authored fixtures mirroring Rust compliance tests (e.g., `structs.abi.yaml`). |
|
|
36
|
+
* The ABI text **must already be flattened** (imports resolved). The Rust
|
|
37
|
+
resolver enforces this.
|
|
38
|
+
* Results are JSON blobs straight from `serde_json`. They include the full type
|
|
39
|
+
info + value trees used by the CLI tooling.
|
|
38
40
|
|
|
39
41
|
---
|
|
40
42
|
|
|
41
|
-
##
|
|
42
|
-
|
|
43
|
-
### ✅ Implemented
|
|
44
|
-
|
|
45
|
-
* **Schema Parsing**
|
|
46
|
-
* Matches the thru-net ABI AST (primitives, structs, arrays, unions, enums, size-discriminated unions, type-refs).
|
|
47
|
-
* Validates flattened files (no `imports`), duplicate names, dangling refs, type cycles.
|
|
48
|
-
|
|
49
|
-
* **Expression Engine**
|
|
50
|
-
* Literals (u/i 8–64), field references with lexical scopes (`["..","parent"]` supported).
|
|
51
|
-
* Arithmetic: `add`, `sub`, `mul`, `div`, `mod`.
|
|
52
|
-
* Bitwise: `bit-and`, `bit-or`, `bit-xor`, `bit-not`, `left-shift`, `right-shift`.
|
|
53
|
-
* Meta: `sizeof(type-name)`, `alignof(type-name)` leveraging shared footprint helpers.
|
|
54
|
-
|
|
55
|
-
* **Decoding Semantics**
|
|
56
|
-
* **Structs:** assumes `packed: true` containers (our blockchain layout never inserts padding). `aligned` overrides are reserved for future use.
|
|
57
|
-
* **Arrays:** dynamic element count via expressions referencing previously decoded fields.
|
|
58
|
-
* **Enums:** tag derived from expressions; variant payload decoded inline.
|
|
59
|
-
* **Unions:** best-effort “preview all variants” strategy—each variant is decoded in isolation, results presented side-by-side (important for Explorer UX).
|
|
60
|
-
* **Size-Discriminated Unions:** tries each variant with byte budgets, supports placement mid-struct by reserving trailing fixed sizes.
|
|
61
|
-
* **Type-Refs:** recursion-safe (cycle detection done in registry); `decodeKind` transparently resolves nested refs.
|
|
62
|
-
* **Primitives:** all integer + float types from ABI spec, including `f16` (returned as `number` representing raw `u16` for now).
|
|
63
|
-
|
|
64
|
-
* **DecodedValue Shape**
|
|
65
|
-
* Each node exposes `kind`, `typeName`, `byteOffset`, `byteLength`, `rawHex`.
|
|
66
|
-
* Structs provide both `fields` (object) and `fieldOrder` (array preserving declaration order).
|
|
67
|
-
* Arrays expose `length`, `elements`.
|
|
68
|
-
* Enums/Unions/SDUs capture tag or variant metadata.
|
|
69
|
-
* When something can’t be safely decoded (e.g., ambiguous union variant), an `opaque` node contains context + `rawHex`.
|
|
70
|
-
|
|
71
|
-
* **Testing Harness**
|
|
72
|
-
* Uses `tsx`/`vitest`. The repo includes sample fixture script `test/verify-rectangle.ts` showing end-to-end usage.
|
|
73
|
-
* Additional tests exist under `src/index.test.ts` covering primitives, arrays, expressions, unions, etc.
|
|
74
|
-
|
|
75
|
-
### ⚠️ Known Limitations (as of this snapshot)
|
|
76
|
-
|
|
77
|
-
* **Runtime Performance**
|
|
78
|
-
* YAML is parsed on every `decodeData` call. No caching or schema memoization yet.
|
|
79
|
-
* Expressions evaluate with BigInt math. That’s correct but slower than precomputed constants.
|
|
80
|
-
|
|
81
|
-
* **Instruction Decoding**
|
|
82
|
-
* Current focus is account data. Instruction decoding isn’t implemented yet (needs call-site context + discriminants).
|
|
83
|
-
|
|
84
|
-
* **Union Heuristics**
|
|
85
|
-
* Unlike Rust (which requires external hints), we decode *every* variant. That’s user-friendly but does not pick a “canonical” variant automatically. Upstream UI must choose how to present ambiguous unions.
|
|
43
|
+
## Public API
|
|
86
44
|
|
|
87
|
-
|
|
88
|
-
|
|
45
|
+
| Function | Description |
|
|
46
|
+
| --- | --- |
|
|
47
|
+
| `reflect(abi: string, typeName: string, payload: { type: "binary", value: BinaryLike } \| { type: "hex", value: string })` | Reflects binary data (or hex) and returns the parsed JSON payload. |
|
|
48
|
+
| `formatReflection(raw: JsonValue)` | Delegates to the WASM formatter to collapse verbose JSON trees. Requires `ensureWasmLoaded()` (or any prior call to `reflect`) before use. |
|
|
49
|
+
| `buildLayoutIr(abi: string)` | Runs the shared Layout IR builder and returns the serialized IR document (schema version, per-type expressions, parameters). |
|
|
50
|
+
| `ensureWasmLoaded()` | Preloads the WASM bindings for callers that want to pay the initialization cost up-front. `reflect` calls it lazily. |
|
|
89
51
|
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
* **Security / Untrusted ABIs**
|
|
94
|
-
* The parser enforces flattened files and forbids unknown fields, but we still assume ABIs come from trusted sources. Malicious ABIs could attempt to trick UIs (e.g., wrong type names). A future enhancement could add allow-lists or signatures.
|
|
52
|
+
All helpers are async, because loading + instantiating the WASM module can touch
|
|
53
|
+
the filesystem (Node) or issue dynamic imports (bundlers).
|
|
95
54
|
|
|
96
55
|
---
|
|
97
56
|
|
|
98
|
-
##
|
|
99
|
-
|
|
100
|
-
1. **Parse & Validate**
|
|
101
|
-
* `parseAbiDocument` -> `AbiDocument`.
|
|
102
|
-
* `buildTypeRegistry` indexes types, verifies refs, catches cycles.
|
|
57
|
+
## WASM workflow
|
|
103
58
|
|
|
104
|
-
|
|
105
|
-
|
|
59
|
+
The generated artifacts live under `web/packages/abi/wasm/{bundler,node}` and are
|
|
60
|
+
checked in so the package works without a local Rust toolchain. When
|
|
61
|
+
`abi_reflect` or the shared IR changes, rebuild everything with:
|
|
106
62
|
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
4. **Field Scope & Expressions**
|
|
112
|
-
* After each field decode, `addFieldToScope` records the result so later `field-ref`s can use it.
|
|
113
|
-
* Expressions are evaluated lazily during decoding (e.g., array lengths, enum tags).
|
|
63
|
+
```bash
|
|
64
|
+
# From repo root
|
|
65
|
+
pnpm --filter @thru/abi run build:wasm
|
|
66
|
+
```
|
|
114
67
|
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
68
|
+
That script runs `wasm-pack build` twice (bundler + node targets) inside
|
|
69
|
+
`abi/abi_reflect_wasm`, then copies the fresh outputs into
|
|
70
|
+
`web/packages/abi/wasm`. The regular `pnpm --filter @thru/abi build` step runs
|
|
71
|
+
`tsup` and copies those WASM folders into `dist/wasm` so published packages
|
|
72
|
+
resolve the dynamic imports automatically.
|
|
118
73
|
|
|
119
|
-
|
|
120
|
-
|
|
74
|
+
When developing inside the monorepo, Vitest loads the TypeScript sources
|
|
75
|
+
directly. The runtime detects when it is executing from `src/` and reaches for
|
|
76
|
+
`../wasm`, so make sure the synced artifacts exist before running the tests.
|
|
121
77
|
|
|
122
78
|
---
|
|
123
79
|
|
|
124
|
-
##
|
|
80
|
+
## Testing
|
|
125
81
|
|
|
126
82
|
```bash
|
|
127
|
-
# Install deps
|
|
128
|
-
pnpm install
|
|
129
|
-
|
|
130
|
-
# Build ESM bundle + type declarations
|
|
131
|
-
pnpm --filter @thru/abi build
|
|
132
|
-
|
|
133
|
-
# Run test suite (vitest)
|
|
134
83
|
pnpm --filter @thru/abi test
|
|
135
|
-
|
|
136
|
-
# One-off verification script example
|
|
137
|
-
npx tsx web/packages/abi/test/verify-rectangle.ts
|
|
138
84
|
```
|
|
139
85
|
|
|
140
|
-
|
|
86
|
+
Vitest exercises both `reflectHex` and `reflectBinary` against the
|
|
87
|
+
`SimpleStruct` compliance ABI plus `buildLayoutIr` to ensure the WASM bridge is
|
|
88
|
+
wired correctly. If you tweak the Rust runtime, rerun `pnpm build:wasm` so the
|
|
89
|
+
tests pick up the updated binaries.
|
|
141
90
|
|
|
142
91
|
---
|
|
143
92
|
|
|
144
|
-
##
|
|
93
|
+
## Development notes
|
|
145
94
|
|
|
146
|
-
*
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
*
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
## Future Roadmap Ideas
|
|
158
|
-
|
|
159
|
-
1. **Schema Caching** – hash YAML text and reuse parsed `AbiDocument`/`TypeRegistry`.
|
|
160
|
-
2. **Instruction Decoding** – need discriminants + context (program ID, variant mapping).
|
|
161
|
-
3. **Float16 Conversion Helper** – convert raw u16 to JS number with proper rounding.
|
|
162
|
-
4. **Diagnostics API** – return warnings for ambiguous unions, unsupported expressions, etc., instead of throwing.
|
|
163
|
-
5. **Web Worker Integration** – offload heavy decodes to worker threads for large accounts.
|
|
95
|
+
* The TypeScript surface intentionally stays tiny; we no longer export the old
|
|
96
|
+
decoder/resolver classes. Future code should talk to the WASM bridge instead
|
|
97
|
+
of re-implementing reflection logic in JS.
|
|
98
|
+
* Browser vs. Node detection happens in `src/wasmBridge.ts`. Node loads the
|
|
99
|
+
`wasm/node` build via `createRequire`, while bundlers dynamically import the
|
|
100
|
+
`wasm/bundler` module.
|
|
101
|
+
* The JSON shape returned by `reflect*` matches `abi_reflect`'s CLI output, so
|
|
102
|
+
parity debugging can use `abi/scripts/show_reflection.py`.
|
|
103
|
+
* Layout IR consumers can feed `buildLayoutIr` into caches or ship a prebuilt
|
|
104
|
+
snapshot alongside the WASM runtime to guard against future schema changes.
|
|
164
105
|
|
|
165
106
|
---
|
|
166
107
|
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
* When adding new ABI features, update both this README and `GAPS_AND_PLAN.md` so future iterations know the exact capability boundaries.
|
|
172
|
-
|
|
173
|
-
Happy decoding! 🎯
|
|
174
|
-
|
|
108
|
+
Questions? Ping the thru-net ABI team (same folks maintaining
|
|
109
|
+
`abi/abi_reflect`). Whenever you extend the Rust reflection engine or shared IR,
|
|
110
|
+
regenerate the WASM artifacts and mention the change in `enums-fam-impl.md` so
|
|
111
|
+
tooling consumers know which version to depend on.
|
package/dist/index.d.ts
CHANGED
|
@@ -1,185 +1,71 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
interface
|
|
23
|
-
kind: "primitive";
|
|
24
|
-
primitive: PrimitiveName;
|
|
25
|
-
}
|
|
26
|
-
interface StructField {
|
|
27
|
-
name: string;
|
|
28
|
-
type: TypeKind;
|
|
29
|
-
}
|
|
30
|
-
interface StructType {
|
|
31
|
-
kind: "struct";
|
|
32
|
-
attributes: ContainerAttributes;
|
|
33
|
-
fields: StructField[];
|
|
34
|
-
}
|
|
35
|
-
interface ArrayType {
|
|
36
|
-
kind: "array";
|
|
37
|
-
attributes: ContainerAttributes;
|
|
38
|
-
elementType: TypeKind;
|
|
39
|
-
size: Expression;
|
|
40
|
-
}
|
|
41
|
-
interface EnumVariant {
|
|
42
|
-
name: string;
|
|
43
|
-
tagValue: number;
|
|
44
|
-
type: TypeKind;
|
|
45
|
-
}
|
|
46
|
-
interface EnumType {
|
|
47
|
-
kind: "enum";
|
|
48
|
-
attributes: ContainerAttributes;
|
|
49
|
-
tagExpression: Expression;
|
|
50
|
-
variants: EnumVariant[];
|
|
51
|
-
}
|
|
52
|
-
interface UnionVariant {
|
|
53
|
-
name: string;
|
|
54
|
-
type: TypeKind;
|
|
55
|
-
}
|
|
56
|
-
interface UnionType {
|
|
57
|
-
kind: "union";
|
|
58
|
-
attributes: ContainerAttributes;
|
|
59
|
-
variants: UnionVariant[];
|
|
60
|
-
}
|
|
61
|
-
interface SizeDiscriminatedVariant {
|
|
62
|
-
name: string;
|
|
63
|
-
expectedSize: number;
|
|
64
|
-
type: TypeKind;
|
|
65
|
-
}
|
|
66
|
-
interface SizeDiscriminatedUnionType {
|
|
67
|
-
kind: "size-discriminated-union";
|
|
68
|
-
attributes: ContainerAttributes;
|
|
69
|
-
variants: SizeDiscriminatedVariant[];
|
|
70
|
-
}
|
|
71
|
-
interface TypeRefType {
|
|
72
|
-
kind: "type-ref";
|
|
73
|
-
name: string;
|
|
74
|
-
}
|
|
75
|
-
type Expression = LiteralExpression | FieldRefExpression | BinaryExpression | UnaryExpression | SizeOfExpression | AlignOfExpression;
|
|
76
|
-
interface LiteralExpression {
|
|
77
|
-
type: "literal";
|
|
78
|
-
literalType: PrimitiveName;
|
|
79
|
-
value: bigint;
|
|
80
|
-
}
|
|
81
|
-
interface FieldRefExpression {
|
|
82
|
-
type: "field-ref";
|
|
83
|
-
path: string[];
|
|
84
|
-
}
|
|
85
|
-
type BinaryOperator = "add" | "sub" | "mul" | "div" | "mod" | "bit-and" | "bit-or" | "bit-xor" | "left-shift" | "right-shift";
|
|
86
|
-
interface BinaryExpression {
|
|
87
|
-
type: "binary";
|
|
88
|
-
op: BinaryOperator;
|
|
89
|
-
left: Expression;
|
|
90
|
-
right: Expression;
|
|
91
|
-
}
|
|
92
|
-
type UnaryOperator = "bit-not";
|
|
93
|
-
interface UnaryExpression {
|
|
94
|
-
type: "unary";
|
|
95
|
-
op: UnaryOperator;
|
|
96
|
-
operand: Expression;
|
|
97
|
-
}
|
|
98
|
-
interface SizeOfExpression {
|
|
99
|
-
type: "sizeof";
|
|
1
|
+
interface ByteRange {
|
|
2
|
+
offset: number;
|
|
3
|
+
size: number;
|
|
4
|
+
}
|
|
5
|
+
type FormattedValue = null | string | number | boolean | bigint | FormattedValue[] | {
|
|
6
|
+
[key: string]: FormattedValue;
|
|
7
|
+
} | {
|
|
8
|
+
variant: string;
|
|
9
|
+
value: FormattedValue | null;
|
|
10
|
+
};
|
|
11
|
+
type FormattedValueWithByteRange = {
|
|
12
|
+
value: FormattedValue;
|
|
13
|
+
_byteRange: ByteRange;
|
|
14
|
+
} | {
|
|
15
|
+
hex: string;
|
|
16
|
+
_byteRange: ByteRange;
|
|
17
|
+
} | {
|
|
18
|
+
variant: string;
|
|
19
|
+
value: FormattedValue | null;
|
|
20
|
+
_byteRange: ByteRange;
|
|
21
|
+
};
|
|
22
|
+
interface FormattedReflection {
|
|
100
23
|
typeName: string;
|
|
24
|
+
kind: string | null | undefined;
|
|
25
|
+
value: FormattedValue;
|
|
26
|
+
byteRange?: ByteRange;
|
|
101
27
|
}
|
|
102
|
-
interface AlignOfExpression {
|
|
103
|
-
type: "alignof";
|
|
104
|
-
typeName: string;
|
|
105
|
-
}
|
|
106
|
-
declare function parseAbiDocument(yamlText: string): AbiDocument;
|
|
107
28
|
|
|
108
|
-
type
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
}
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
value:
|
|
140
|
-
}
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
expectedSize: number;
|
|
150
|
-
value: DecodedValue;
|
|
151
|
-
}
|
|
152
|
-
interface DecodedOpaqueValue extends BaseDecodedValue {
|
|
153
|
-
kind: "opaque";
|
|
154
|
-
description: string;
|
|
155
|
-
}
|
|
156
|
-
type DecodedValue = DecodedPrimitiveValue | DecodedStructValue | DecodedArrayValue | DecodedEnumValue | DecodedUnionValue | DecodedSizeDiscriminatedUnionValue | DecodedOpaqueValue;
|
|
157
|
-
|
|
158
|
-
declare class TypeRegistry {
|
|
159
|
-
private readonly types;
|
|
160
|
-
constructor(definitions: Iterable<TypeDefinition>);
|
|
161
|
-
get(typeName: string): TypeDefinition;
|
|
162
|
-
has(typeName: string): boolean;
|
|
163
|
-
entries(): IterableIterator<[string, TypeDefinition]>;
|
|
164
|
-
}
|
|
165
|
-
declare function buildTypeRegistry(document: AbiDocument): TypeRegistry;
|
|
166
|
-
|
|
167
|
-
declare function decodeData(yamlText: string, typeName: string, data: Uint8Array): DecodedValue;
|
|
168
|
-
|
|
169
|
-
type AbiErrorCode = "PARSE_ERROR" | "VALIDATION_ERROR" | "DECODE_ERROR";
|
|
170
|
-
declare class AbiError extends Error {
|
|
171
|
-
readonly code: AbiErrorCode;
|
|
172
|
-
readonly details?: Record<string, unknown>;
|
|
173
|
-
constructor(code: AbiErrorCode, message: string, details?: Record<string, unknown>);
|
|
174
|
-
}
|
|
175
|
-
declare class AbiParseError extends AbiError {
|
|
176
|
-
constructor(message: string, details?: Record<string, unknown>);
|
|
177
|
-
}
|
|
178
|
-
declare class AbiValidationError extends AbiError {
|
|
179
|
-
constructor(message: string, details?: Record<string, unknown>);
|
|
180
|
-
}
|
|
181
|
-
declare class AbiDecodeError extends AbiError {
|
|
182
|
-
constructor(message: string, details?: Record<string, unknown>);
|
|
183
|
-
}
|
|
29
|
+
type JsonValue = unknown;
|
|
30
|
+
/**
|
|
31
|
+
* Configure the URL from which to load the WASM file.
|
|
32
|
+
* Must be called before any reflection functions are used.
|
|
33
|
+
*
|
|
34
|
+
* This is useful for environments like Next.js where bundler-based WASM loading
|
|
35
|
+
* doesn't work. Instead, copy the WASM file to your public directory and call:
|
|
36
|
+
*
|
|
37
|
+
* @example
|
|
38
|
+
* ```ts
|
|
39
|
+
* import { configureWasm } from "@thru/abi";
|
|
40
|
+
* configureWasm("/wasm/abi_reflect_wasm_bg.wasm");
|
|
41
|
+
* ```
|
|
42
|
+
*
|
|
43
|
+
* @param url - URL or path to the WASM file (e.g., "/wasm/abi_reflect_wasm_bg.wasm")
|
|
44
|
+
*/
|
|
45
|
+
declare function configureWasm(url: string): void;
|
|
46
|
+
type BinaryLike = Uint8Array | ArrayBuffer | ArrayBufferView | number[];
|
|
47
|
+
declare function reflect(abiYaml: string, typeName: string, payload: {
|
|
48
|
+
type: 'binary';
|
|
49
|
+
value: BinaryLike;
|
|
50
|
+
} | {
|
|
51
|
+
type: 'hex';
|
|
52
|
+
value: string;
|
|
53
|
+
}): Promise<JsonValue>;
|
|
54
|
+
declare function buildLayoutIr(abiYaml: string): Promise<JsonValue>;
|
|
55
|
+
type ReflectRootPayload = {
|
|
56
|
+
type: 'binary';
|
|
57
|
+
value: BinaryLike;
|
|
58
|
+
} | {
|
|
59
|
+
type: 'hex';
|
|
60
|
+
value: string;
|
|
61
|
+
};
|
|
62
|
+
declare function reflectInstruction(abiYaml: string, payload: ReflectRootPayload): Promise<JsonValue>;
|
|
63
|
+
declare function reflectAccount(abiYaml: string, payload: ReflectRootPayload): Promise<JsonValue>;
|
|
64
|
+
declare function reflectEvent(abiYaml: string, payload: ReflectRootPayload): Promise<JsonValue>;
|
|
65
|
+
declare function ensureWasmLoaded(): Promise<void>;
|
|
66
|
+
interface FormatOptions {
|
|
67
|
+
includeByteOffsets?: boolean;
|
|
68
|
+
}
|
|
69
|
+
declare function formatReflection(raw: JsonValue, options?: FormatOptions): FormattedReflection;
|
|
184
70
|
|
|
185
|
-
export {
|
|
71
|
+
export { type ByteRange, type FormatOptions, type FormattedReflection, type FormattedValue, type FormattedValueWithByteRange, buildLayoutIr, configureWasm, ensureWasmLoaded, formatReflection, reflect, reflectAccount, reflectEvent, reflectInstruction };
|