@lukso/transaction-view-headless 0.2.2-dev.a8c9315
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/.turbo/turbo-build.log +51 -0
- package/CHANGELOG.md +88 -0
- package/COMPONENT_ARCHITECTURE.md +190 -0
- package/COMPONENT_CONVERSION_ANALYSIS.md +371 -0
- package/CONTEXT_VARIANT_GUIDE.md +425 -0
- package/LAZY_LOADING_GUIDE.md +534 -0
- package/LICENSE +201 -0
- package/PLAYBACK_EXAMPLES.md +658 -0
- package/PLAYBACK_GUIDE.md +402 -0
- package/README.md +43 -0
- package/REGISTRY_SUMMARY.md +638 -0
- package/SUFFERING_ECONOMICS.md +346 -0
- package/SUFFERING_ECONOMICS.zip +0 -0
- package/VIEW_REGISTRATION_GUIDE.md +795 -0
- package/dist/composables/index.cjs +1321 -0
- package/dist/composables/index.cjs.map +1 -0
- package/dist/composables/index.d.cts +6 -0
- package/dist/composables/index.d.ts +6 -0
- package/dist/composables/index.js +1276 -0
- package/dist/composables/index.js.map +1 -0
- package/dist/index-CMLU1hKL.d.ts +374 -0
- package/dist/index-CSDjhiKV.d.cts +374 -0
- package/dist/index.cjs +1534 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +93 -0
- package/dist/index.d.ts +93 -0
- package/dist/index.js +1463 -0
- package/dist/index.js.map +1 -0
- package/dist/registry/index.cjs +522 -0
- package/dist/registry/index.cjs.map +1 -0
- package/dist/registry/index.d.cts +46 -0
- package/dist/registry/index.d.ts +46 -0
- package/dist/registry/index.js +487 -0
- package/dist/registry/index.js.map +1 -0
- package/dist/types/index.cjs +19 -0
- package/dist/types/index.cjs.map +1 -0
- package/dist/types/index.d.cts +203 -0
- package/dist/types/index.d.ts +203 -0
- package/dist/types/index.js +1 -0
- package/dist/types/index.js.map +1 -0
- package/dist/utils/index.cjs +217 -0
- package/dist/utils/index.cjs.map +1 -0
- package/dist/utils/index.d.cts +47 -0
- package/dist/utils/index.d.ts +47 -0
- package/dist/utils/index.js +188 -0
- package/dist/utils/index.js.map +1 -0
- package/dist/view-loader-dD86QAlQ.d.cts +121 -0
- package/dist/view-loader-ii8AxiQR.d.ts +121 -0
- package/package.json +64 -0
- package/publish.log +0 -0
- package/src/composables/index.ts +59 -0
- package/src/composables/use-image-loader.ts +315 -0
- package/src/composables/use-transaction-playback.ts +396 -0
- package/src/composables/use-transaction-view.ts +309 -0
- package/src/config/lukso-config.ts +171 -0
- package/src/examples/context-aware-views.ts +300 -0
- package/src/examples/example-views.ts +197 -0
- package/src/examples/lit-plus-rn-strategy.ts +448 -0
- package/src/examples/lsp7-custom-matcher-examples.ts +174 -0
- package/src/examples/opt-in-context-examples.ts +372 -0
- package/src/examples/optimized-view-definitions.ts +408 -0
- package/src/examples/vue-to-lit-compilation.ts +358 -0
- package/src/hooks/useAddressQuery.ts +135 -0
- package/src/hooks/useAddressResolution.ts +437 -0
- package/src/index.ts +36 -0
- package/src/registry/index.ts +13 -0
- package/src/registry/view-loader.ts +305 -0
- package/src/registry/view-registry.ts +135 -0
- package/src/types/index.ts +16 -0
- package/src/types/view-contexts.ts +72 -0
- package/src/types/view-matching.ts +173 -0
- package/src/utils/context-matcher.ts +165 -0
- package/src/utils/index.ts +5 -0
- package/src/utils/view-matcher.ts +338 -0
- package/tsconfig.json +20 -0
- package/tsup.config.ts +34 -0
package/dist/index.cjs
ADDED
|
@@ -0,0 +1,1534 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __create = Object.create;
|
|
3
|
+
var __defProp = Object.defineProperty;
|
|
4
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
5
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
6
|
+
var __getProtoOf = Object.getPrototypeOf;
|
|
7
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
8
|
+
var __esm = (fn, res) => function __init() {
|
|
9
|
+
return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
|
|
10
|
+
};
|
|
11
|
+
var __export = (target, all) => {
|
|
12
|
+
for (var name in all)
|
|
13
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
14
|
+
};
|
|
15
|
+
var __copyProps = (to, from, except, desc) => {
|
|
16
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
17
|
+
for (let key of __getOwnPropNames(from))
|
|
18
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
19
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
20
|
+
}
|
|
21
|
+
return to;
|
|
22
|
+
};
|
|
23
|
+
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
|
|
24
|
+
// If the importer is in node compatibility mode or this is not an ESM
|
|
25
|
+
// file that has been converted to a CommonJS file using a Babel-
|
|
26
|
+
// compatible transform (i.e. "__esModule" has not been set), then set
|
|
27
|
+
// "default" to the CommonJS "module.exports" for node compatibility.
|
|
28
|
+
isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
|
|
29
|
+
mod
|
|
30
|
+
));
|
|
31
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
32
|
+
|
|
33
|
+
// src/config/lukso-config.ts
|
|
34
|
+
function setLuksoConfig(config) {
|
|
35
|
+
globalConfig = { ...globalConfig, ...config };
|
|
36
|
+
clearAddressCache();
|
|
37
|
+
if (typeof window !== "undefined" && window.console) {
|
|
38
|
+
console.log("\u{1F310} LUKSO Config Updated:", {
|
|
39
|
+
chainId: globalConfig.chainId,
|
|
40
|
+
network: globalConfig.chainId === 42 ? "mainnet" : globalConfig.chainId === 4201 ? "testnet" : "custom",
|
|
41
|
+
addressResolution: globalConfig.enableAddressResolution
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
function getLuksoConfig() {
|
|
46
|
+
return { ...globalConfig };
|
|
47
|
+
}
|
|
48
|
+
function useLuksoMainnet() {
|
|
49
|
+
setLuksoConfig({
|
|
50
|
+
chainId: 42,
|
|
51
|
+
rpcUrl: "https://rpc.lukso.network"
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
function useLuksoTestnet() {
|
|
55
|
+
setLuksoConfig({
|
|
56
|
+
chainId: 4201,
|
|
57
|
+
rpcUrl: "https://rpc.testnet.lukso.network"
|
|
58
|
+
});
|
|
59
|
+
}
|
|
60
|
+
function cacheAddress(address, data) {
|
|
61
|
+
if (!globalConfig.enableAddressResolution) return;
|
|
62
|
+
const key = address.toLowerCase();
|
|
63
|
+
addressCache.set(key, data);
|
|
64
|
+
cacheTimestamps.set(key, Date.now());
|
|
65
|
+
}
|
|
66
|
+
function getCachedAddress(address) {
|
|
67
|
+
if (!globalConfig.enableAddressResolution) return null;
|
|
68
|
+
const key = address.toLowerCase();
|
|
69
|
+
const data = addressCache.get(key);
|
|
70
|
+
const timestamp = cacheTimestamps.get(key);
|
|
71
|
+
if (!data || !timestamp) return null;
|
|
72
|
+
if (Date.now() - timestamp > globalConfig.cacheDuration) {
|
|
73
|
+
addressCache.delete(key);
|
|
74
|
+
cacheTimestamps.delete(key);
|
|
75
|
+
return null;
|
|
76
|
+
}
|
|
77
|
+
return data;
|
|
78
|
+
}
|
|
79
|
+
function clearAddressCache() {
|
|
80
|
+
addressCache.clear();
|
|
81
|
+
cacheTimestamps.clear();
|
|
82
|
+
}
|
|
83
|
+
function isAddressResolutionEnabled() {
|
|
84
|
+
return globalConfig.enableAddressResolution ?? true;
|
|
85
|
+
}
|
|
86
|
+
function setCurrentChain(chain) {
|
|
87
|
+
currentChainSignal.value = chain;
|
|
88
|
+
setLuksoConfig({
|
|
89
|
+
chainId: chain.id,
|
|
90
|
+
rpcUrl: chain.rpcUrls.default.http[0]
|
|
91
|
+
});
|
|
92
|
+
}
|
|
93
|
+
function getCurrentChain() {
|
|
94
|
+
return currentChainSignal.value;
|
|
95
|
+
}
|
|
96
|
+
async function initializeChainSignal() {
|
|
97
|
+
if (currentChainSignal.value) return;
|
|
98
|
+
try {
|
|
99
|
+
const { lukso, luksoTestnet } = await import("viem/chains");
|
|
100
|
+
const config = getLuksoConfig();
|
|
101
|
+
const chain = config.chainId === 42 ? lukso : luksoTestnet;
|
|
102
|
+
currentChainSignal.value = chain;
|
|
103
|
+
} catch (error) {
|
|
104
|
+
console.warn("Failed to initialize chain signal:", error);
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
var import_signals_core, DEFAULT_CONFIG, globalConfig, addressCache, cacheTimestamps, currentChainSignal;
|
|
108
|
+
var init_lukso_config = __esm({
|
|
109
|
+
"src/config/lukso-config.ts"() {
|
|
110
|
+
"use strict";
|
|
111
|
+
import_signals_core = require("@preact/signals-core");
|
|
112
|
+
DEFAULT_CONFIG = {
|
|
113
|
+
chainId: 42,
|
|
114
|
+
// LUKSO mainnet
|
|
115
|
+
rpcUrl: "https://rpc.lukso.network",
|
|
116
|
+
graphqlEndpoint: "/api/graphql",
|
|
117
|
+
// Use local API proxy
|
|
118
|
+
ipfsGateway: "https://api.universalprofile.cloud/ipfs",
|
|
119
|
+
enableAddressResolution: true,
|
|
120
|
+
cacheDuration: 5 * 60 * 1e3
|
|
121
|
+
// 5 minutes
|
|
122
|
+
};
|
|
123
|
+
globalConfig = { ...DEFAULT_CONFIG };
|
|
124
|
+
addressCache = /* @__PURE__ */ new Map();
|
|
125
|
+
cacheTimestamps = /* @__PURE__ */ new Map();
|
|
126
|
+
currentChainSignal = (0, import_signals_core.signal)(null);
|
|
127
|
+
}
|
|
128
|
+
});
|
|
129
|
+
|
|
130
|
+
// src/hooks/useAddressResolution.ts
|
|
131
|
+
var useAddressResolution_exports = {};
|
|
132
|
+
__export(useAddressResolution_exports, {
|
|
133
|
+
createAddressResolutionState: () => createAddressResolutionState,
|
|
134
|
+
resolveAddress: () => resolveAddress,
|
|
135
|
+
resolveAddressWithState: () => resolveAddressWithState,
|
|
136
|
+
resolveAddresses: () => resolveAddresses
|
|
137
|
+
});
|
|
138
|
+
function truncateAddress(address, prefixLength = 5, suffixLength = 4) {
|
|
139
|
+
if (!address || address.length <= prefixLength + suffixLength + 2) {
|
|
140
|
+
return address;
|
|
141
|
+
}
|
|
142
|
+
const prefix = address.slice(0, 2 + prefixLength);
|
|
143
|
+
const suffix = address.slice(-suffixLength);
|
|
144
|
+
return `${prefix}...${suffix}`;
|
|
145
|
+
}
|
|
146
|
+
function getBatchState(chainId) {
|
|
147
|
+
let state = chainBatchStates.get(chainId);
|
|
148
|
+
if (!state) {
|
|
149
|
+
state = {
|
|
150
|
+
batchTimeout: null,
|
|
151
|
+
batchQueue: /* @__PURE__ */ new Set(),
|
|
152
|
+
batchResolvers: /* @__PURE__ */ new Map(),
|
|
153
|
+
pendingResolutions: /* @__PURE__ */ new Map(),
|
|
154
|
+
isProcessing: false
|
|
155
|
+
};
|
|
156
|
+
chainBatchStates.set(chainId, state);
|
|
157
|
+
}
|
|
158
|
+
return state;
|
|
159
|
+
}
|
|
160
|
+
async function processBatch(chainId) {
|
|
161
|
+
const state = getBatchState(chainId);
|
|
162
|
+
if (state.batchQueue.size === 0 || state.isProcessing) return;
|
|
163
|
+
state.isProcessing = true;
|
|
164
|
+
const addresses = Array.from(state.batchQueue);
|
|
165
|
+
state.batchQueue.clear();
|
|
166
|
+
try {
|
|
167
|
+
const { fetchMultipleAddresses: fetchMultipleAddresses2, getGraphQLEndpoint: getGraphQLEndpoint2 } = await import("@lukso/transaction-decoder");
|
|
168
|
+
const { lukso, luksoTestnet } = await import("viem/chains");
|
|
169
|
+
const chain = chainId === 42 ? lukso : luksoTestnet;
|
|
170
|
+
const graphqlEndpoint = getGraphQLEndpoint2(chain);
|
|
171
|
+
const dataKeys = addresses;
|
|
172
|
+
const results = await fetchMultipleAddresses2(dataKeys, graphqlEndpoint);
|
|
173
|
+
for (const address of addresses) {
|
|
174
|
+
const normalizedAddress = address.toLowerCase();
|
|
175
|
+
const enhanced = results.get(normalizedAddress);
|
|
176
|
+
let result;
|
|
177
|
+
if (enhanced) {
|
|
178
|
+
const profileImages = enhanced.profileImages;
|
|
179
|
+
const resolvedData = {
|
|
180
|
+
...enhanced,
|
|
181
|
+
hasProfile: !!(enhanced.name || profileImages?.length)
|
|
182
|
+
};
|
|
183
|
+
cacheAddressForChain(address, resolvedData, chainId);
|
|
184
|
+
result = {
|
|
185
|
+
...resolvedData,
|
|
186
|
+
address,
|
|
187
|
+
truncatedAddress: truncateAddress(address)
|
|
188
|
+
};
|
|
189
|
+
} else {
|
|
190
|
+
result = {
|
|
191
|
+
address,
|
|
192
|
+
truncatedAddress: truncateAddress(address),
|
|
193
|
+
hasProfile: false
|
|
194
|
+
};
|
|
195
|
+
cacheAddressForChain(address, { hasProfile: false }, chainId);
|
|
196
|
+
}
|
|
197
|
+
const resolver = state.batchResolvers.get(normalizedAddress);
|
|
198
|
+
if (resolver) {
|
|
199
|
+
resolver(result);
|
|
200
|
+
state.batchResolvers.delete(normalizedAddress);
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
} catch (error) {
|
|
204
|
+
console.warn(
|
|
205
|
+
"Batch address resolution failed (falling back to API):",
|
|
206
|
+
error
|
|
207
|
+
);
|
|
208
|
+
try {
|
|
209
|
+
const response = await fetch("/api/resolveAddresses", {
|
|
210
|
+
method: "POST",
|
|
211
|
+
headers: { "Content-Type": "application/json" },
|
|
212
|
+
body: JSON.stringify({
|
|
213
|
+
addresses,
|
|
214
|
+
chainId
|
|
215
|
+
})
|
|
216
|
+
});
|
|
217
|
+
if (!response.ok) {
|
|
218
|
+
throw new Error(`API fallback failed: ${response.status}`);
|
|
219
|
+
}
|
|
220
|
+
const data = await response.json();
|
|
221
|
+
for (const address of addresses) {
|
|
222
|
+
const normalizedAddress = address.toLowerCase();
|
|
223
|
+
const resolved = data.resolved?.[normalizedAddress];
|
|
224
|
+
let result;
|
|
225
|
+
if (resolved) {
|
|
226
|
+
const resolvedData = {
|
|
227
|
+
name: resolved.name,
|
|
228
|
+
profileImage: resolved.profileImage,
|
|
229
|
+
hasProfile: !!(resolved.name || resolved.profileImage)
|
|
230
|
+
};
|
|
231
|
+
cacheAddressForChain(address, resolvedData, chainId);
|
|
232
|
+
result = {
|
|
233
|
+
address,
|
|
234
|
+
truncatedAddress: truncateAddress(address),
|
|
235
|
+
...resolvedData
|
|
236
|
+
};
|
|
237
|
+
} else {
|
|
238
|
+
result = {
|
|
239
|
+
address,
|
|
240
|
+
truncatedAddress: truncateAddress(address),
|
|
241
|
+
hasProfile: false
|
|
242
|
+
};
|
|
243
|
+
cacheAddressForChain(address, { hasProfile: false }, chainId);
|
|
244
|
+
}
|
|
245
|
+
const resolver = state.batchResolvers.get(normalizedAddress);
|
|
246
|
+
if (resolver) {
|
|
247
|
+
resolver(result);
|
|
248
|
+
state.batchResolvers.delete(normalizedAddress);
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
} catch (fallbackError) {
|
|
252
|
+
console.warn("Both GraphQL and API resolution failed:", fallbackError);
|
|
253
|
+
for (const address of addresses) {
|
|
254
|
+
const fallback = {
|
|
255
|
+
address,
|
|
256
|
+
truncatedAddress: truncateAddress(address),
|
|
257
|
+
hasProfile: false
|
|
258
|
+
};
|
|
259
|
+
cacheAddressForChain(address, { hasProfile: false }, chainId);
|
|
260
|
+
const resolver = state.batchResolvers.get(address.toLowerCase());
|
|
261
|
+
if (resolver) {
|
|
262
|
+
resolver(fallback);
|
|
263
|
+
state.batchResolvers.delete(address.toLowerCase());
|
|
264
|
+
}
|
|
265
|
+
}
|
|
266
|
+
}
|
|
267
|
+
} finally {
|
|
268
|
+
state.isProcessing = false;
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
function cacheAddressForChain(address, data, chainId) {
|
|
272
|
+
const key = `${address.toLowerCase()}:${chainId}`;
|
|
273
|
+
cacheAddress(key, data);
|
|
274
|
+
}
|
|
275
|
+
function getCachedAddressForChain(address, chainId) {
|
|
276
|
+
const key = `${address.toLowerCase()}:${chainId}`;
|
|
277
|
+
return getCachedAddress(key);
|
|
278
|
+
}
|
|
279
|
+
async function getEffectiveChainId(chainId) {
|
|
280
|
+
if (chainId !== void 0) return chainId;
|
|
281
|
+
await initializeChainSignal();
|
|
282
|
+
const currentChain = currentChainSignal.value;
|
|
283
|
+
if (currentChain) {
|
|
284
|
+
return currentChain.id;
|
|
285
|
+
}
|
|
286
|
+
const config = getLuksoConfig();
|
|
287
|
+
return config.chainId;
|
|
288
|
+
}
|
|
289
|
+
async function resolveAddress(address, chainId) {
|
|
290
|
+
const effectiveChainId = await getEffectiveChainId(chainId);
|
|
291
|
+
const normalizedAddress = address.toLowerCase();
|
|
292
|
+
const fallback = {
|
|
293
|
+
address,
|
|
294
|
+
truncatedAddress: truncateAddress(address),
|
|
295
|
+
hasProfile: false
|
|
296
|
+
};
|
|
297
|
+
if (!isAddressResolutionEnabled()) {
|
|
298
|
+
return fallback;
|
|
299
|
+
}
|
|
300
|
+
const cached = getCachedAddressForChain(address, effectiveChainId);
|
|
301
|
+
if (cached) {
|
|
302
|
+
return {
|
|
303
|
+
...fallback,
|
|
304
|
+
...cached,
|
|
305
|
+
hasProfile: !!(cached.name || cached.profileImage)
|
|
306
|
+
};
|
|
307
|
+
}
|
|
308
|
+
const state = getBatchState(effectiveChainId);
|
|
309
|
+
const existingPromise = state.pendingResolutions.get(normalizedAddress);
|
|
310
|
+
if (existingPromise) {
|
|
311
|
+
return existingPromise;
|
|
312
|
+
}
|
|
313
|
+
if (state.batchQueue.has(normalizedAddress)) {
|
|
314
|
+
return Promise.resolve(fallback);
|
|
315
|
+
}
|
|
316
|
+
const resolutionPromise = new Promise((resolve) => {
|
|
317
|
+
state.batchQueue.add(normalizedAddress);
|
|
318
|
+
state.batchResolvers.set(normalizedAddress, resolve);
|
|
319
|
+
if (state.batchTimeout) {
|
|
320
|
+
clearTimeout(state.batchTimeout);
|
|
321
|
+
}
|
|
322
|
+
if (!state.isProcessing) {
|
|
323
|
+
state.batchTimeout = setTimeout(() => {
|
|
324
|
+
state.batchTimeout = null;
|
|
325
|
+
processBatch(effectiveChainId);
|
|
326
|
+
}, BATCH_DELAY);
|
|
327
|
+
if (state.batchQueue.size >= BATCH_SIZE) {
|
|
328
|
+
if (state.batchTimeout) {
|
|
329
|
+
clearTimeout(state.batchTimeout);
|
|
330
|
+
state.batchTimeout = null;
|
|
331
|
+
}
|
|
332
|
+
processBatch(effectiveChainId);
|
|
333
|
+
}
|
|
334
|
+
}
|
|
335
|
+
});
|
|
336
|
+
state.pendingResolutions.set(normalizedAddress, resolutionPromise);
|
|
337
|
+
resolutionPromise.finally(() => {
|
|
338
|
+
state.pendingResolutions.delete(normalizedAddress);
|
|
339
|
+
});
|
|
340
|
+
return resolutionPromise;
|
|
341
|
+
}
|
|
342
|
+
async function resolveAddresses(addresses, chainId) {
|
|
343
|
+
const results = /* @__PURE__ */ new Map();
|
|
344
|
+
const resolutionPromises = addresses.map(async (address) => {
|
|
345
|
+
const resolved = await resolveAddress(address, chainId);
|
|
346
|
+
results.set(address.toLowerCase(), resolved);
|
|
347
|
+
});
|
|
348
|
+
await Promise.all(resolutionPromises);
|
|
349
|
+
return results;
|
|
350
|
+
}
|
|
351
|
+
function createAddressResolutionState() {
|
|
352
|
+
return {
|
|
353
|
+
resolved: null,
|
|
354
|
+
loading: false,
|
|
355
|
+
error: null
|
|
356
|
+
};
|
|
357
|
+
}
|
|
358
|
+
async function resolveAddressWithState(address, _state, updateCallback, chainId) {
|
|
359
|
+
updateCallback({ loading: true, error: null });
|
|
360
|
+
try {
|
|
361
|
+
const resolved = await resolveAddress(address, chainId);
|
|
362
|
+
updateCallback({
|
|
363
|
+
resolved,
|
|
364
|
+
loading: false,
|
|
365
|
+
error: null
|
|
366
|
+
});
|
|
367
|
+
} catch (error) {
|
|
368
|
+
updateCallback({
|
|
369
|
+
loading: false,
|
|
370
|
+
error: error instanceof Error ? error.message : "Resolution failed"
|
|
371
|
+
});
|
|
372
|
+
}
|
|
373
|
+
}
|
|
374
|
+
var chainBatchStates, BATCH_DELAY, BATCH_SIZE;
|
|
375
|
+
var init_useAddressResolution = __esm({
|
|
376
|
+
"src/hooks/useAddressResolution.ts"() {
|
|
377
|
+
"use strict";
|
|
378
|
+
init_lukso_config();
|
|
379
|
+
chainBatchStates = /* @__PURE__ */ new Map();
|
|
380
|
+
BATCH_DELAY = 0;
|
|
381
|
+
BATCH_SIZE = 50;
|
|
382
|
+
}
|
|
383
|
+
});
|
|
384
|
+
|
|
385
|
+
// src/index.ts
|
|
386
|
+
var src_exports = {};
|
|
387
|
+
__export(src_exports, {
|
|
388
|
+
CRITERIA_WEIGHTS: () => CRITERIA_WEIGHTS,
|
|
389
|
+
DefaultViewRegistry: () => DefaultViewRegistry,
|
|
390
|
+
LoaderHelpers: () => LoaderHelpers,
|
|
391
|
+
UniversalViewLoader: () => UniversalViewLoader,
|
|
392
|
+
ViewLoadingError: () => ViewLoadingError,
|
|
393
|
+
addressQueryOptions: () => addressQueryOptions,
|
|
394
|
+
addressQueryOptionsVue: () => addressQueryOptionsVue,
|
|
395
|
+
cacheAddress: () => cacheAddress,
|
|
396
|
+
calculateMatchScore: () => calculateMatchScore,
|
|
397
|
+
clearAddressCache: () => clearAddressCache,
|
|
398
|
+
createAddressResolutionState: () => createAddressResolutionState,
|
|
399
|
+
createTransactionPlayback: () => createTransactionPlayback,
|
|
400
|
+
currentChainSignal: () => currentChainSignal,
|
|
401
|
+
findAllTransactionViews: () => findAllTransactionViews,
|
|
402
|
+
findBestTransactionView: () => findBestTransactionView,
|
|
403
|
+
findMatchingViews: () => findMatchingViews,
|
|
404
|
+
getAddressQueryKey: () => getAddressQueryKey,
|
|
405
|
+
getAddressesQueryKey: () => getAddressesQueryKey,
|
|
406
|
+
getAllAddressQueryKeys: () => getAllAddressQueryKeys,
|
|
407
|
+
getCachedAddress: () => getCachedAddress,
|
|
408
|
+
getCurrentChain: () => getCurrentChain,
|
|
409
|
+
getGlobalLoader: () => getGlobalLoader,
|
|
410
|
+
getGlobalRegistry: () => getGlobalRegistry,
|
|
411
|
+
getInvalidateAddressesPattern: () => getInvalidateAddressesPattern,
|
|
412
|
+
getLuksoConfig: () => getLuksoConfig,
|
|
413
|
+
getValidPlaybackIndices: () => getValidPlaybackIndices,
|
|
414
|
+
initializeChainSignal: () => initializeChainSignal,
|
|
415
|
+
isAddressResolutionEnabled: () => isAddressResolutionEnabled,
|
|
416
|
+
isValidPlaybackIndex: () => isValidPlaybackIndex,
|
|
417
|
+
queryAddress: () => queryAddress,
|
|
418
|
+
queryAddresses: () => queryAddresses,
|
|
419
|
+
resetGlobalRegistry: () => resetGlobalRegistry,
|
|
420
|
+
resolveAddress: () => resolveAddress,
|
|
421
|
+
resolveAddressWithState: () => resolveAddressWithState,
|
|
422
|
+
resolveAddresses: () => resolveAddresses,
|
|
423
|
+
setCurrentChain: () => setCurrentChain,
|
|
424
|
+
setGlobalLoader: () => setGlobalLoader,
|
|
425
|
+
setGlobalRegistry: () => setGlobalRegistry,
|
|
426
|
+
setLuksoConfig: () => setLuksoConfig,
|
|
427
|
+
useAddressResolver: () => useAddressResolver,
|
|
428
|
+
useImageLoader: () => useImageLoader,
|
|
429
|
+
useLuksoMainnet: () => useLuksoMainnet,
|
|
430
|
+
useLuksoTestnet: () => useLuksoTestnet,
|
|
431
|
+
useTransactionPlayback: () => useTransactionPlayback,
|
|
432
|
+
useTransactionView: () => useTransactionView
|
|
433
|
+
});
|
|
434
|
+
module.exports = __toCommonJS(src_exports);
|
|
435
|
+
|
|
436
|
+
// src/composables/index.ts
|
|
437
|
+
init_lukso_config();
|
|
438
|
+
init_useAddressResolution();
|
|
439
|
+
|
|
440
|
+
// src/composables/use-image-loader.ts
|
|
441
|
+
console.log(
|
|
442
|
+
"\u{1F525} LOADING NEW useAddressResolver CODE - should see GraphQL integration"
|
|
443
|
+
);
|
|
444
|
+
var imageLoadCache = /* @__PURE__ */ new Map();
|
|
445
|
+
function getImageCacheKey(imageData, options) {
|
|
446
|
+
const imageUrls = imageData.filter((img) => img?.url || img?.src).map((img) => img.url || img.src).sort().join(",");
|
|
447
|
+
const sizeKey = `${options.width || 32}x${options.height || options.width || 32}@${options.dpr || 1}`;
|
|
448
|
+
return `${imageUrls}-${sizeKey}`;
|
|
449
|
+
}
|
|
450
|
+
function useImageLoader() {
|
|
451
|
+
async function loadImage(imageData, options = {}) {
|
|
452
|
+
try {
|
|
453
|
+
if (!imageData || imageData.length === 0) {
|
|
454
|
+
return null;
|
|
455
|
+
}
|
|
456
|
+
const loadOptions = {
|
|
457
|
+
width: options.width || 32,
|
|
458
|
+
height: options.height || options.width || 32,
|
|
459
|
+
dpr: options.dpr || (typeof window !== "undefined" ? window.devicePixelRatio : 1),
|
|
460
|
+
ignoreHead: true
|
|
461
|
+
// Skip HEAD requests in component context
|
|
462
|
+
};
|
|
463
|
+
const cacheKey = getImageCacheKey(imageData, loadOptions);
|
|
464
|
+
const cachedPromise = imageLoadCache.get(cacheKey);
|
|
465
|
+
if (cachedPromise) {
|
|
466
|
+
console.log("\u{1F4F8} loadImage: Using cached promise for", cacheKey);
|
|
467
|
+
return cachedPromise;
|
|
468
|
+
}
|
|
469
|
+
console.log(
|
|
470
|
+
"\u{1F4F8} loadImage: Creating new request for",
|
|
471
|
+
imageData.length,
|
|
472
|
+
"options:",
|
|
473
|
+
loadOptions
|
|
474
|
+
);
|
|
475
|
+
const loadingPromise = (async () => {
|
|
476
|
+
const { getImage } = await import("@lukso/transaction-decoder");
|
|
477
|
+
const result = await getImage(imageData, loadOptions);
|
|
478
|
+
if (result?.src) {
|
|
479
|
+
console.log("\u{1F4F8} loadImage: Selected image:", result.src);
|
|
480
|
+
return {
|
|
481
|
+
src: result.src,
|
|
482
|
+
width: result.width,
|
|
483
|
+
height: result.height
|
|
484
|
+
};
|
|
485
|
+
}
|
|
486
|
+
return null;
|
|
487
|
+
})();
|
|
488
|
+
imageLoadCache.set(cacheKey, loadingPromise);
|
|
489
|
+
loadingPromise.finally(() => {
|
|
490
|
+
loadingPromise.then((result) => {
|
|
491
|
+
if (!result) {
|
|
492
|
+
imageLoadCache.delete(cacheKey);
|
|
493
|
+
}
|
|
494
|
+
}).catch(() => {
|
|
495
|
+
imageLoadCache.delete(cacheKey);
|
|
496
|
+
});
|
|
497
|
+
});
|
|
498
|
+
return loadingPromise;
|
|
499
|
+
} catch (error) {
|
|
500
|
+
console.warn("Failed to load image:", error);
|
|
501
|
+
return null;
|
|
502
|
+
}
|
|
503
|
+
}
|
|
504
|
+
async function loadProfileImage(addressData, options = {}) {
|
|
505
|
+
if (addressData.__gqltype === "Profile") {
|
|
506
|
+
if (addressData.profileImages?.length) {
|
|
507
|
+
const result = await loadImage(addressData.profileImages, options);
|
|
508
|
+
if (result) return result;
|
|
509
|
+
}
|
|
510
|
+
if (addressData.icons?.length) {
|
|
511
|
+
const result = await loadImage(addressData.icons, options);
|
|
512
|
+
if (result) return result;
|
|
513
|
+
}
|
|
514
|
+
if (addressData.images?.length) {
|
|
515
|
+
return loadImage(addressData.images, options);
|
|
516
|
+
}
|
|
517
|
+
return null;
|
|
518
|
+
}
|
|
519
|
+
if (addressData.icons?.length) {
|
|
520
|
+
const result = await loadImage(addressData.icons, options);
|
|
521
|
+
if (result) return result;
|
|
522
|
+
}
|
|
523
|
+
if (addressData.images?.length) {
|
|
524
|
+
return loadImage(addressData.images, options);
|
|
525
|
+
}
|
|
526
|
+
return null;
|
|
527
|
+
}
|
|
528
|
+
async function loadBackgroundImage(addressData, options = {}) {
|
|
529
|
+
const imageGroup = addressData.backgroundImages || [];
|
|
530
|
+
return loadImage(imageGroup, options);
|
|
531
|
+
}
|
|
532
|
+
function getFallbackImage(addressData) {
|
|
533
|
+
const isProfile = addressData.__gqltype === "Profile";
|
|
534
|
+
return {
|
|
535
|
+
src: isProfile ? "/assets/images/profile-default.svg" : "/assets/images/token-default.svg"
|
|
536
|
+
};
|
|
537
|
+
}
|
|
538
|
+
function isContractAddress(addressData) {
|
|
539
|
+
return addressData.__gqltype !== "Profile";
|
|
540
|
+
}
|
|
541
|
+
return {
|
|
542
|
+
loadImage,
|
|
543
|
+
loadProfileImage,
|
|
544
|
+
loadBackgroundImage,
|
|
545
|
+
getFallbackImage,
|
|
546
|
+
isContractAddress
|
|
547
|
+
};
|
|
548
|
+
}
|
|
549
|
+
function useAddressResolver() {
|
|
550
|
+
async function resolveAddress2(address) {
|
|
551
|
+
console.log("\u{1F525} useAddressResolver.resolveAddress called with:", address);
|
|
552
|
+
try {
|
|
553
|
+
const { resolveAddress: batchedResolve } = await Promise.resolve().then(() => (init_useAddressResolution(), useAddressResolution_exports));
|
|
554
|
+
console.log("\u{1F525} useAddressResolver: calling batchedResolve...");
|
|
555
|
+
const resolved = await batchedResolve(address);
|
|
556
|
+
console.log("\u{1F525} useAddressResolver: batchedResolve returned:", resolved);
|
|
557
|
+
const result = {
|
|
558
|
+
// Preserve all image arrays from GraphQL
|
|
559
|
+
...resolved,
|
|
560
|
+
// Override with computed values only if not already set by GraphQL
|
|
561
|
+
address: resolved.address,
|
|
562
|
+
name: resolved.name || "",
|
|
563
|
+
__gqltype: resolved.__gqltype || (resolved.hasProfile ? "Profile" : "Contract")
|
|
564
|
+
};
|
|
565
|
+
console.log("\u{1F525} useAddressResolver: returning result:", result);
|
|
566
|
+
return result;
|
|
567
|
+
} catch (error) {
|
|
568
|
+
console.error("\u{1F525} useAddressResolver: Failed to resolve address:", error);
|
|
569
|
+
return {
|
|
570
|
+
address,
|
|
571
|
+
name: "",
|
|
572
|
+
__gqltype: "Contract",
|
|
573
|
+
profileImages: [],
|
|
574
|
+
avatar: [],
|
|
575
|
+
icon: []
|
|
576
|
+
};
|
|
577
|
+
}
|
|
578
|
+
}
|
|
579
|
+
function formatDisplayName(addressData) {
|
|
580
|
+
const baseName = addressData.name?.toLowerCase?.() || addressData.lsp4TokenName || addressData.baseAsset?.lsp4TokenName || "";
|
|
581
|
+
const symbol = addressData.lsp4TokenSymbol || addressData.baseAsset?.lsp4TokenSymbol || "";
|
|
582
|
+
return symbol ? `${baseName} (${symbol})` : baseName;
|
|
583
|
+
}
|
|
584
|
+
function getAddressPrefix(addressData) {
|
|
585
|
+
return addressData.__gqltype !== "Profile" ? "\u{1FA99} " : "@";
|
|
586
|
+
}
|
|
587
|
+
function shouldShowNameColor(addressData) {
|
|
588
|
+
return addressData.__gqltype === "Profile";
|
|
589
|
+
}
|
|
590
|
+
return {
|
|
591
|
+
resolveAddress: resolveAddress2,
|
|
592
|
+
formatDisplayName,
|
|
593
|
+
getAddressPrefix,
|
|
594
|
+
shouldShowNameColor
|
|
595
|
+
};
|
|
596
|
+
}
|
|
597
|
+
|
|
598
|
+
// src/utils/view-matcher.ts
|
|
599
|
+
var CRITERIA_WEIGHTS = {
|
|
600
|
+
recordType: 0.25,
|
|
601
|
+
// Most specific to transaction type
|
|
602
|
+
functionName: 0.2,
|
|
603
|
+
// Function-level specificity
|
|
604
|
+
context: 0.2,
|
|
605
|
+
// Context specificity (when opt-in)
|
|
606
|
+
standard: 0.15,
|
|
607
|
+
// LSP standard specificity
|
|
608
|
+
contractAddress: 0.1,
|
|
609
|
+
// Contract-specific logic
|
|
610
|
+
contextRequirements: 0.05,
|
|
611
|
+
// Context requirement matching
|
|
612
|
+
chainId: 0.03,
|
|
613
|
+
// Network-specific behavior
|
|
614
|
+
customMatcher: 0.02
|
|
615
|
+
// Custom logic (lowest weight due to unpredictability)
|
|
616
|
+
};
|
|
617
|
+
function calculateMatchScore(transaction, view, options) {
|
|
618
|
+
const { criteria } = view;
|
|
619
|
+
const matchedCriteria = [];
|
|
620
|
+
let totalWeight = 0;
|
|
621
|
+
let matchedWeight = 0;
|
|
622
|
+
for (const [criterion, weight] of Object.entries(CRITERIA_WEIGHTS)) {
|
|
623
|
+
const criterionKey = criterion;
|
|
624
|
+
const criterionValue = criteria[criterionKey];
|
|
625
|
+
if (criterionValue === void 0) continue;
|
|
626
|
+
totalWeight += weight;
|
|
627
|
+
if (criterionKey === "customMatcher" && typeof criterionValue === "function") {
|
|
628
|
+
try {
|
|
629
|
+
const matchCount = criterionValue(transaction);
|
|
630
|
+
if (matchCount > 0) {
|
|
631
|
+
matchedCriteria.push(criterionKey);
|
|
632
|
+
const normalizedScore = Math.min(matchCount / 10, 1);
|
|
633
|
+
matchedWeight += weight * normalizedScore;
|
|
634
|
+
}
|
|
635
|
+
} catch (error) {
|
|
636
|
+
console.warn("Custom matcher threw error:", error);
|
|
637
|
+
}
|
|
638
|
+
continue;
|
|
639
|
+
}
|
|
640
|
+
if (doesCriterionMatch(transaction, criterionKey, criterionValue, options)) {
|
|
641
|
+
matchedCriteria.push(criterionKey);
|
|
642
|
+
matchedWeight += weight;
|
|
643
|
+
}
|
|
644
|
+
}
|
|
645
|
+
const viewHasContext = criteria.context !== void 0;
|
|
646
|
+
const requestHasContext = options?.context !== void 0;
|
|
647
|
+
if (viewHasContext && !requestHasContext) {
|
|
648
|
+
matchedWeight *= 0.1;
|
|
649
|
+
} else if (!viewHasContext && requestHasContext) {
|
|
650
|
+
matchedWeight *= 0.9;
|
|
651
|
+
}
|
|
652
|
+
if (totalWeight === 0) return { score: 0, matchedCriteria: [] };
|
|
653
|
+
const score = matchedWeight / totalWeight;
|
|
654
|
+
return { score, matchedCriteria };
|
|
655
|
+
}
|
|
656
|
+
function doesCriterionMatch(transaction, criterion, criterionValue, options) {
|
|
657
|
+
switch (criterion) {
|
|
658
|
+
case "recordType":
|
|
659
|
+
return matchesStringOrArray(
|
|
660
|
+
transaction.recordType,
|
|
661
|
+
criterionValue
|
|
662
|
+
);
|
|
663
|
+
case "functionName":
|
|
664
|
+
return matchesStringOrArray(
|
|
665
|
+
transaction.functionName,
|
|
666
|
+
criterionValue
|
|
667
|
+
);
|
|
668
|
+
case "standard":
|
|
669
|
+
return matchesStringOrArray(
|
|
670
|
+
transaction.standard,
|
|
671
|
+
criterionValue
|
|
672
|
+
);
|
|
673
|
+
case "contractAddress":
|
|
674
|
+
return matchesStringOrArray(
|
|
675
|
+
transaction.contractAddress,
|
|
676
|
+
criterionValue
|
|
677
|
+
);
|
|
678
|
+
case "chainId":
|
|
679
|
+
return matchesNumberOrArray(transaction.chainId, criterionValue);
|
|
680
|
+
case "context":
|
|
681
|
+
if (!options?.context) return false;
|
|
682
|
+
return matchesStringOrArray(options.context, criterionValue);
|
|
683
|
+
case "contextRequirements":
|
|
684
|
+
if (!options?.contextRequirements || !criterionValue) return false;
|
|
685
|
+
return areContextRequirementsCompatible(
|
|
686
|
+
options.contextRequirements,
|
|
687
|
+
criterionValue
|
|
688
|
+
);
|
|
689
|
+
case "customMatcher":
|
|
690
|
+
if (typeof criterionValue === "function") {
|
|
691
|
+
try {
|
|
692
|
+
const matchCount = criterionValue(transaction);
|
|
693
|
+
return matchCount > 0;
|
|
694
|
+
} catch (error) {
|
|
695
|
+
console.warn("Custom matcher threw error:", error);
|
|
696
|
+
return false;
|
|
697
|
+
}
|
|
698
|
+
}
|
|
699
|
+
return false;
|
|
700
|
+
default:
|
|
701
|
+
return false;
|
|
702
|
+
}
|
|
703
|
+
}
|
|
704
|
+
function matchesStringOrArray(value, criteria) {
|
|
705
|
+
if (!value || !criteria) return false;
|
|
706
|
+
if (Array.isArray(criteria)) {
|
|
707
|
+
return criteria.includes(value);
|
|
708
|
+
}
|
|
709
|
+
return value === criteria;
|
|
710
|
+
}
|
|
711
|
+
function matchesNumberOrArray(value, criteria) {
|
|
712
|
+
if (value === void 0 || criteria === void 0) return false;
|
|
713
|
+
if (Array.isArray(criteria)) {
|
|
714
|
+
return criteria.includes(value);
|
|
715
|
+
}
|
|
716
|
+
return value === criteria;
|
|
717
|
+
}
|
|
718
|
+
function areContextRequirementsCompatible(requested, viewRequirements) {
|
|
719
|
+
if (requested.detailLevel && viewRequirements.detailLevel) {
|
|
720
|
+
const detailOrder = ["minimal", "summary", "full", "debug"];
|
|
721
|
+
const requestedLevel = detailOrder.indexOf(requested.detailLevel);
|
|
722
|
+
const viewLevel = detailOrder.indexOf(viewRequirements.detailLevel);
|
|
723
|
+
if (viewLevel < requestedLevel) return false;
|
|
724
|
+
}
|
|
725
|
+
if (requested.maxHeight && viewRequirements.maxHeight) {
|
|
726
|
+
if (viewRequirements.maxHeight > requested.maxHeight) return false;
|
|
727
|
+
}
|
|
728
|
+
return true;
|
|
729
|
+
}
|
|
730
|
+
function calculateNativeFrameworkBonus(view, requestedFramework) {
|
|
731
|
+
if (requestedFramework === "lit") {
|
|
732
|
+
return 0;
|
|
733
|
+
}
|
|
734
|
+
if (requestedFramework === "vue" && view.frameworks.vue) {
|
|
735
|
+
return 0.15;
|
|
736
|
+
}
|
|
737
|
+
if (requestedFramework === "rn" && view.frameworks.rn) {
|
|
738
|
+
return 0.15;
|
|
739
|
+
}
|
|
740
|
+
return 0;
|
|
741
|
+
}
|
|
742
|
+
function findMatchingViews(transaction, views, options) {
|
|
743
|
+
const matches = [];
|
|
744
|
+
const minScore = options.minScore ?? 0;
|
|
745
|
+
for (const view of views) {
|
|
746
|
+
if (!view.frameworks[options.framework]) {
|
|
747
|
+
continue;
|
|
748
|
+
}
|
|
749
|
+
const { score, matchedCriteria } = calculateMatchScore(transaction, view, {
|
|
750
|
+
context: options.context,
|
|
751
|
+
contextRequirements: options.contextRequirements
|
|
752
|
+
});
|
|
753
|
+
if (score < minScore) {
|
|
754
|
+
continue;
|
|
755
|
+
}
|
|
756
|
+
const frameworkBonus = calculateNativeFrameworkBonus(
|
|
757
|
+
view,
|
|
758
|
+
options.framework
|
|
759
|
+
);
|
|
760
|
+
const finalScore = Math.min(1, score + frameworkBonus);
|
|
761
|
+
const match = {
|
|
762
|
+
view,
|
|
763
|
+
score: finalScore,
|
|
764
|
+
matchedCriteria,
|
|
765
|
+
frameworkConfig: options.includeFrameworkConfig ? view.frameworks[options.framework] : void 0
|
|
766
|
+
};
|
|
767
|
+
matches.push(match);
|
|
768
|
+
}
|
|
769
|
+
matches.sort((a, b) => {
|
|
770
|
+
if (a.score !== b.score) {
|
|
771
|
+
return b.score - a.score;
|
|
772
|
+
}
|
|
773
|
+
return b.view.priority - a.view.priority;
|
|
774
|
+
});
|
|
775
|
+
if (options.maxMatches) {
|
|
776
|
+
return matches.slice(0, options.maxMatches);
|
|
777
|
+
}
|
|
778
|
+
return matches;
|
|
779
|
+
}
|
|
780
|
+
|
|
781
|
+
// src/registry/view-registry.ts
|
|
782
|
+
var DefaultViewRegistry = class {
|
|
783
|
+
views = /* @__PURE__ */ new Map();
|
|
784
|
+
register(view) {
|
|
785
|
+
if (this.views.has(view.id)) {
|
|
786
|
+
console.warn(
|
|
787
|
+
`View with id "${view.id}" is already registered. Overwriting.`
|
|
788
|
+
);
|
|
789
|
+
}
|
|
790
|
+
this.views.set(view.id, view);
|
|
791
|
+
}
|
|
792
|
+
unregister(viewId) {
|
|
793
|
+
this.views.delete(viewId);
|
|
794
|
+
}
|
|
795
|
+
getAllViews() {
|
|
796
|
+
return Array.from(this.views.values());
|
|
797
|
+
}
|
|
798
|
+
findMatches(transaction, options) {
|
|
799
|
+
const allViews = this.getAllViews();
|
|
800
|
+
return findMatchingViews(transaction, allViews, options);
|
|
801
|
+
}
|
|
802
|
+
getView(viewId) {
|
|
803
|
+
return this.views.get(viewId);
|
|
804
|
+
}
|
|
805
|
+
clear() {
|
|
806
|
+
this.views.clear();
|
|
807
|
+
}
|
|
808
|
+
/**
|
|
809
|
+
* Get the best matching view (highest score) for a transaction
|
|
810
|
+
*/
|
|
811
|
+
getBestMatch(transaction, options) {
|
|
812
|
+
const matches = this.findMatches(transaction, { ...options, maxMatches: 1 });
|
|
813
|
+
return matches[0] || null;
|
|
814
|
+
}
|
|
815
|
+
/**
|
|
816
|
+
* Bulk register multiple views
|
|
817
|
+
*/
|
|
818
|
+
registerMany(views) {
|
|
819
|
+
for (const view of views) {
|
|
820
|
+
this.register(view);
|
|
821
|
+
}
|
|
822
|
+
}
|
|
823
|
+
/**
|
|
824
|
+
* Get stats about registered views
|
|
825
|
+
*/
|
|
826
|
+
getStats() {
|
|
827
|
+
const allViews = this.getAllViews();
|
|
828
|
+
const totalViews = allViews.length;
|
|
829
|
+
const viewsByFramework = {};
|
|
830
|
+
const viewsByRecordType = {};
|
|
831
|
+
for (const view of allViews) {
|
|
832
|
+
for (const framework of Object.keys(view.frameworks)) {
|
|
833
|
+
viewsByFramework[framework] = (viewsByFramework[framework] || 0) + 1;
|
|
834
|
+
}
|
|
835
|
+
const recordType = view.criteria.recordType;
|
|
836
|
+
if (recordType) {
|
|
837
|
+
const types = Array.isArray(recordType) ? recordType : [recordType];
|
|
838
|
+
for (const type of types) {
|
|
839
|
+
viewsByRecordType[type] = (viewsByRecordType[type] || 0) + 1;
|
|
840
|
+
}
|
|
841
|
+
}
|
|
842
|
+
}
|
|
843
|
+
return {
|
|
844
|
+
totalViews,
|
|
845
|
+
viewsByFramework,
|
|
846
|
+
viewsByRecordType
|
|
847
|
+
};
|
|
848
|
+
}
|
|
849
|
+
};
|
|
850
|
+
var globalRegistry = null;
|
|
851
|
+
function getGlobalRegistry() {
|
|
852
|
+
if (!globalRegistry) {
|
|
853
|
+
globalRegistry = new DefaultViewRegistry();
|
|
854
|
+
}
|
|
855
|
+
return globalRegistry;
|
|
856
|
+
}
|
|
857
|
+
function setGlobalRegistry(registry) {
|
|
858
|
+
globalRegistry = registry;
|
|
859
|
+
}
|
|
860
|
+
function resetGlobalRegistry() {
|
|
861
|
+
globalRegistry = null;
|
|
862
|
+
}
|
|
863
|
+
|
|
864
|
+
// src/composables/use-transaction-playback.ts
|
|
865
|
+
function isBatchTransaction(transaction) {
|
|
866
|
+
return transaction.resultType === "executeBatch" || transaction.resultType === "setDataBatch" || !!transaction.children?.length;
|
|
867
|
+
}
|
|
868
|
+
function getBatchChildren(transaction) {
|
|
869
|
+
if (!isBatchTransaction(transaction)) {
|
|
870
|
+
return [];
|
|
871
|
+
}
|
|
872
|
+
return transaction.children || [];
|
|
873
|
+
}
|
|
874
|
+
function selectViewAtIndex(rootTransaction, index, options) {
|
|
875
|
+
const {
|
|
876
|
+
registry = getGlobalRegistry(),
|
|
877
|
+
framework = "lit",
|
|
878
|
+
fallbackViewId,
|
|
879
|
+
minScore = 0,
|
|
880
|
+
includeFrameworkConfig = true
|
|
881
|
+
} = options;
|
|
882
|
+
const isBatch = isBatchTransaction(rootTransaction);
|
|
883
|
+
const children = getBatchChildren(rootTransaction);
|
|
884
|
+
const childCount = children.length;
|
|
885
|
+
const result = {
|
|
886
|
+
match: null,
|
|
887
|
+
transaction: null,
|
|
888
|
+
indexInfo: {
|
|
889
|
+
requested: index,
|
|
890
|
+
childIndex: null,
|
|
891
|
+
isBatchSummary: false,
|
|
892
|
+
isValid: false
|
|
893
|
+
},
|
|
894
|
+
batchInfo: {
|
|
895
|
+
isBatch,
|
|
896
|
+
childCount,
|
|
897
|
+
availableIndices: []
|
|
898
|
+
}
|
|
899
|
+
};
|
|
900
|
+
if (isBatch) {
|
|
901
|
+
result.batchInfo.availableIndices = Array.from(
|
|
902
|
+
{ length: childCount + 1 },
|
|
903
|
+
(_, i) => i
|
|
904
|
+
);
|
|
905
|
+
} else {
|
|
906
|
+
result.batchInfo.availableIndices = [0, 1];
|
|
907
|
+
}
|
|
908
|
+
if (index < 0) {
|
|
909
|
+
return result;
|
|
910
|
+
}
|
|
911
|
+
if (!isBatch) {
|
|
912
|
+
if (index === 0 || index === 1) {
|
|
913
|
+
result.indexInfo.isValid = true;
|
|
914
|
+
result.transaction = rootTransaction;
|
|
915
|
+
const matchOptions = {
|
|
916
|
+
framework,
|
|
917
|
+
minScore,
|
|
918
|
+
maxMatches: 1,
|
|
919
|
+
includeFrameworkConfig
|
|
920
|
+
};
|
|
921
|
+
const matches = registry.findMatches(rootTransaction, matchOptions);
|
|
922
|
+
result.match = matches[0] || null;
|
|
923
|
+
if (!result.match && fallbackViewId) {
|
|
924
|
+
const fallbackView = registry.getView(fallbackViewId);
|
|
925
|
+
if (fallbackView && fallbackView.frameworks[framework]) {
|
|
926
|
+
result.match = {
|
|
927
|
+
view: fallbackView,
|
|
928
|
+
score: 0,
|
|
929
|
+
matchedCriteria: [],
|
|
930
|
+
frameworkConfig: includeFrameworkConfig ? fallbackView.frameworks[framework] : void 0
|
|
931
|
+
};
|
|
932
|
+
}
|
|
933
|
+
}
|
|
934
|
+
return result;
|
|
935
|
+
}
|
|
936
|
+
return result;
|
|
937
|
+
}
|
|
938
|
+
if (index === 0) {
|
|
939
|
+
result.indexInfo.isValid = true;
|
|
940
|
+
result.indexInfo.isBatchSummary = true;
|
|
941
|
+
result.transaction = rootTransaction;
|
|
942
|
+
const matchOptions = {
|
|
943
|
+
framework,
|
|
944
|
+
minScore,
|
|
945
|
+
maxMatches: 1,
|
|
946
|
+
includeFrameworkConfig
|
|
947
|
+
};
|
|
948
|
+
const matches = registry.findMatches(rootTransaction, matchOptions);
|
|
949
|
+
result.match = matches[0] || null;
|
|
950
|
+
if (!result.match && fallbackViewId) {
|
|
951
|
+
const fallbackView = registry.getView(fallbackViewId);
|
|
952
|
+
if (fallbackView && fallbackView.frameworks[framework]) {
|
|
953
|
+
result.match = {
|
|
954
|
+
view: fallbackView,
|
|
955
|
+
score: 0,
|
|
956
|
+
matchedCriteria: [],
|
|
957
|
+
frameworkConfig: includeFrameworkConfig ? fallbackView.frameworks[framework] : void 0
|
|
958
|
+
};
|
|
959
|
+
}
|
|
960
|
+
}
|
|
961
|
+
return result;
|
|
962
|
+
}
|
|
963
|
+
const childIndex = index - 1;
|
|
964
|
+
if (childIndex >= 0 && childIndex < childCount) {
|
|
965
|
+
result.indexInfo.isValid = true;
|
|
966
|
+
result.indexInfo.childIndex = childIndex;
|
|
967
|
+
result.transaction = children[childIndex];
|
|
968
|
+
const matchOptions = {
|
|
969
|
+
framework,
|
|
970
|
+
minScore,
|
|
971
|
+
maxMatches: 1,
|
|
972
|
+
includeFrameworkConfig
|
|
973
|
+
};
|
|
974
|
+
const matches = registry.findMatches(result.transaction, matchOptions);
|
|
975
|
+
result.match = matches[0] || null;
|
|
976
|
+
if (!result.match && fallbackViewId) {
|
|
977
|
+
const fallbackView = registry.getView(fallbackViewId);
|
|
978
|
+
if (fallbackView && fallbackView.frameworks[framework]) {
|
|
979
|
+
result.match = {
|
|
980
|
+
view: fallbackView,
|
|
981
|
+
score: 0,
|
|
982
|
+
matchedCriteria: [],
|
|
983
|
+
frameworkConfig: includeFrameworkConfig ? fallbackView.frameworks[framework] : void 0
|
|
984
|
+
};
|
|
985
|
+
}
|
|
986
|
+
}
|
|
987
|
+
return result;
|
|
988
|
+
}
|
|
989
|
+
return result;
|
|
990
|
+
}
|
|
991
|
+
function createTransactionPlayback(rootTransaction, options = {}) {
|
|
992
|
+
const isBatch = isBatchTransaction(rootTransaction);
|
|
993
|
+
const children = getBatchChildren(rootTransaction);
|
|
994
|
+
const childCount = children.length;
|
|
995
|
+
const indexCount = isBatch ? childCount + 1 : 2;
|
|
996
|
+
const availableIndices = isBatch ? Array.from({ length: childCount + 1 }, (_, i) => i) : [0, 1];
|
|
997
|
+
return {
|
|
998
|
+
rootTransaction,
|
|
999
|
+
isBatch,
|
|
1000
|
+
children,
|
|
1001
|
+
indexCount,
|
|
1002
|
+
batchInfo: {
|
|
1003
|
+
isBatch,
|
|
1004
|
+
childCount,
|
|
1005
|
+
availableIndices
|
|
1006
|
+
},
|
|
1007
|
+
getViewAtIndex: (index) => selectViewAtIndex(rootTransaction, index, options),
|
|
1008
|
+
getAllViews: () => {
|
|
1009
|
+
const views = [];
|
|
1010
|
+
for (let i = 0; i < indexCount; i++) {
|
|
1011
|
+
views.push(selectViewAtIndex(rootTransaction, i, options));
|
|
1012
|
+
}
|
|
1013
|
+
return views;
|
|
1014
|
+
}
|
|
1015
|
+
};
|
|
1016
|
+
}
|
|
1017
|
+
function useTransactionPlayback(rootTransaction, index, options = {}) {
|
|
1018
|
+
return selectViewAtIndex(rootTransaction, index, options);
|
|
1019
|
+
}
|
|
1020
|
+
function isValidPlaybackIndex(transaction, index) {
|
|
1021
|
+
const isBatch = isBatchTransaction(transaction);
|
|
1022
|
+
if (!isBatch) {
|
|
1023
|
+
return index === 0 || index === 1;
|
|
1024
|
+
}
|
|
1025
|
+
const childCount = getBatchChildren(transaction).length;
|
|
1026
|
+
return index >= 0 && index <= childCount;
|
|
1027
|
+
}
|
|
1028
|
+
function getValidPlaybackIndices(transaction) {
|
|
1029
|
+
const isBatch = isBatchTransaction(transaction);
|
|
1030
|
+
if (!isBatch) {
|
|
1031
|
+
return [0, 1];
|
|
1032
|
+
}
|
|
1033
|
+
const childCount = getBatchChildren(transaction).length;
|
|
1034
|
+
return Array.from({ length: childCount + 1 }, (_, i) => i);
|
|
1035
|
+
}
|
|
1036
|
+
|
|
1037
|
+
// src/composables/use-transaction-view.ts
|
|
1038
|
+
var import_transaction_decoder = require("@lukso/transaction-decoder");
|
|
1039
|
+
|
|
1040
|
+
// src/registry/view-loader.ts
|
|
1041
|
+
var ViewLoadingError = class extends Error {
|
|
1042
|
+
loader;
|
|
1043
|
+
config;
|
|
1044
|
+
cause;
|
|
1045
|
+
constructor(message, loader, config, cause) {
|
|
1046
|
+
super(message);
|
|
1047
|
+
this.name = "ViewLoadingError";
|
|
1048
|
+
this.loader = loader;
|
|
1049
|
+
this.config = config;
|
|
1050
|
+
this.cause = cause;
|
|
1051
|
+
}
|
|
1052
|
+
};
|
|
1053
|
+
var UniversalViewLoader = class {
|
|
1054
|
+
cache = /* @__PURE__ */ new Map();
|
|
1055
|
+
/**
|
|
1056
|
+
* Load a component based on the framework configuration
|
|
1057
|
+
*/
|
|
1058
|
+
async loadComponent(config) {
|
|
1059
|
+
const cacheKey = this.getCacheKey(config);
|
|
1060
|
+
if (this.cache.has(cacheKey)) {
|
|
1061
|
+
return this.cache.get(cacheKey);
|
|
1062
|
+
}
|
|
1063
|
+
try {
|
|
1064
|
+
const component = await this.loadByStrategy(config.loader);
|
|
1065
|
+
this.cache.set(cacheKey, component);
|
|
1066
|
+
return component;
|
|
1067
|
+
} catch (error) {
|
|
1068
|
+
throw new ViewLoadingError(
|
|
1069
|
+
`Failed to load component "${config.component}"`,
|
|
1070
|
+
config.loader,
|
|
1071
|
+
config,
|
|
1072
|
+
error instanceof Error ? error : new Error(String(error))
|
|
1073
|
+
);
|
|
1074
|
+
}
|
|
1075
|
+
}
|
|
1076
|
+
/**
|
|
1077
|
+
* Load a component from a view match
|
|
1078
|
+
*/
|
|
1079
|
+
async loadFromMatch(match) {
|
|
1080
|
+
if (!match.frameworkConfig) {
|
|
1081
|
+
throw new ViewLoadingError(
|
|
1082
|
+
`No framework config available for view "${match.view.id}"`,
|
|
1083
|
+
{ type: "dynamic-import", path: "" },
|
|
1084
|
+
{}
|
|
1085
|
+
);
|
|
1086
|
+
}
|
|
1087
|
+
return this.loadComponent(match.frameworkConfig);
|
|
1088
|
+
}
|
|
1089
|
+
/**
|
|
1090
|
+
* Load component using the specific strategy
|
|
1091
|
+
*/
|
|
1092
|
+
async loadByStrategy(loader) {
|
|
1093
|
+
switch (loader.type) {
|
|
1094
|
+
case "dynamic-import":
|
|
1095
|
+
return this.loadDynamicImport(loader.path);
|
|
1096
|
+
case "static-import":
|
|
1097
|
+
return this.loadStaticImport(loader.path);
|
|
1098
|
+
case "custom-element":
|
|
1099
|
+
return this.loadCustomElement(loader.tagName);
|
|
1100
|
+
case "registry-lookup":
|
|
1101
|
+
return this.loadFromRegistry(loader.registryKey);
|
|
1102
|
+
case "custom":
|
|
1103
|
+
return loader.loader({});
|
|
1104
|
+
// Will be passed proper config in real usage
|
|
1105
|
+
default:
|
|
1106
|
+
throw new Error(`Unknown loader type: ${loader.type}`);
|
|
1107
|
+
}
|
|
1108
|
+
}
|
|
1109
|
+
/**
|
|
1110
|
+
* Dynamic import strategy (most common)
|
|
1111
|
+
* Supports both static strings and lazy-loaded callbacks
|
|
1112
|
+
*/
|
|
1113
|
+
async loadDynamicImport(path) {
|
|
1114
|
+
if (typeof path === "function") {
|
|
1115
|
+
const module3 = await path();
|
|
1116
|
+
if (module3.default) {
|
|
1117
|
+
return module3.default;
|
|
1118
|
+
}
|
|
1119
|
+
return module3;
|
|
1120
|
+
}
|
|
1121
|
+
const module2 = await import(path);
|
|
1122
|
+
if (module2.default) {
|
|
1123
|
+
return module2.default;
|
|
1124
|
+
}
|
|
1125
|
+
return module2;
|
|
1126
|
+
}
|
|
1127
|
+
/**
|
|
1128
|
+
* Static import strategy (requires bundler support)
|
|
1129
|
+
* Supports both static strings and lazy-loaded callbacks
|
|
1130
|
+
*/
|
|
1131
|
+
async loadStaticImport(path) {
|
|
1132
|
+
if (typeof path === "function") {
|
|
1133
|
+
const module2 = await path();
|
|
1134
|
+
if (module2.default) {
|
|
1135
|
+
return module2.default;
|
|
1136
|
+
}
|
|
1137
|
+
return module2;
|
|
1138
|
+
}
|
|
1139
|
+
console.warn(
|
|
1140
|
+
"Static import not implemented, falling back to dynamic import"
|
|
1141
|
+
);
|
|
1142
|
+
return this.loadDynamicImport(path);
|
|
1143
|
+
}
|
|
1144
|
+
/**
|
|
1145
|
+
* Custom element strategy (for Lit components)
|
|
1146
|
+
*/
|
|
1147
|
+
async loadCustomElement(tagName) {
|
|
1148
|
+
if (typeof window !== "undefined" && window.customElements) {
|
|
1149
|
+
await window.customElements.whenDefined(tagName);
|
|
1150
|
+
return { tagName, type: "custom-element" };
|
|
1151
|
+
}
|
|
1152
|
+
throw new Error("Custom elements not available in this environment");
|
|
1153
|
+
}
|
|
1154
|
+
/**
|
|
1155
|
+
* Registry lookup strategy (for pre-registered components)
|
|
1156
|
+
*/
|
|
1157
|
+
async loadFromRegistry(registryKey) {
|
|
1158
|
+
throw new Error(`Registry lookup not implemented for key: ${registryKey}`);
|
|
1159
|
+
}
|
|
1160
|
+
/**
|
|
1161
|
+
* Generate cache key for component config
|
|
1162
|
+
*/
|
|
1163
|
+
getCacheKey(config) {
|
|
1164
|
+
const { loader, component, package: pkg } = config;
|
|
1165
|
+
return JSON.stringify({ loader, component, package: pkg });
|
|
1166
|
+
}
|
|
1167
|
+
/**
|
|
1168
|
+
* Clear the component cache
|
|
1169
|
+
*/
|
|
1170
|
+
clearCache() {
|
|
1171
|
+
this.cache.clear();
|
|
1172
|
+
}
|
|
1173
|
+
/**
|
|
1174
|
+
* Get cache statistics
|
|
1175
|
+
*/
|
|
1176
|
+
getCacheStats() {
|
|
1177
|
+
return {
|
|
1178
|
+
size: this.cache.size,
|
|
1179
|
+
keys: Array.from(this.cache.keys())
|
|
1180
|
+
};
|
|
1181
|
+
}
|
|
1182
|
+
};
|
|
1183
|
+
var globalLoader = null;
|
|
1184
|
+
function getGlobalLoader() {
|
|
1185
|
+
if (!globalLoader) {
|
|
1186
|
+
globalLoader = new UniversalViewLoader();
|
|
1187
|
+
}
|
|
1188
|
+
return globalLoader;
|
|
1189
|
+
}
|
|
1190
|
+
function setGlobalLoader(loader) {
|
|
1191
|
+
globalLoader = loader;
|
|
1192
|
+
}
|
|
1193
|
+
var LoaderHelpers = {
|
|
1194
|
+
/**
|
|
1195
|
+
* Create a Lit custom element loader (universal web compatibility)
|
|
1196
|
+
*/
|
|
1197
|
+
litComponent(tagName) {
|
|
1198
|
+
return { type: "custom-element", tagName };
|
|
1199
|
+
},
|
|
1200
|
+
/**
|
|
1201
|
+
* Create a Vue component loader (native Vue, optional)
|
|
1202
|
+
* Supports both static paths and lazy-loaded callbacks
|
|
1203
|
+
*/
|
|
1204
|
+
vueComponent(path) {
|
|
1205
|
+
return { type: "dynamic-import", path };
|
|
1206
|
+
},
|
|
1207
|
+
/**
|
|
1208
|
+
* Create a React Native JSX dynamic import loader (mobile-native, optional)
|
|
1209
|
+
* Supports both static paths and lazy-loaded callbacks
|
|
1210
|
+
*/
|
|
1211
|
+
rnComponent(path) {
|
|
1212
|
+
return { type: "dynamic-import", path };
|
|
1213
|
+
},
|
|
1214
|
+
/**
|
|
1215
|
+
* Create a custom loader function for advanced use cases
|
|
1216
|
+
*/
|
|
1217
|
+
custom(loader) {
|
|
1218
|
+
return { type: "custom", loader };
|
|
1219
|
+
},
|
|
1220
|
+
// Legacy helpers for compilation pipelines (Vue/React → Lit)
|
|
1221
|
+
/**
|
|
1222
|
+
* @deprecated Use litComponent() instead. This exists for compilation pipeline compatibility.
|
|
1223
|
+
*/
|
|
1224
|
+
vueToLitCompiled(tagName) {
|
|
1225
|
+
console.warn(
|
|
1226
|
+
"vueToLitCompiled is deprecated. Use litComponent() - the output is the same."
|
|
1227
|
+
);
|
|
1228
|
+
return { type: "custom-element", tagName };
|
|
1229
|
+
},
|
|
1230
|
+
/**
|
|
1231
|
+
* @deprecated Use litComponent() instead. This exists for compilation pipeline compatibility.
|
|
1232
|
+
*/
|
|
1233
|
+
reactToLitCompiled(tagName) {
|
|
1234
|
+
console.warn(
|
|
1235
|
+
"reactToLitCompiled is deprecated. Use litComponent() - the output is the same."
|
|
1236
|
+
);
|
|
1237
|
+
return { type: "custom-element", tagName };
|
|
1238
|
+
},
|
|
1239
|
+
/**
|
|
1240
|
+
* @deprecated Use rnComponent() instead. Updated for better TypeScript support.
|
|
1241
|
+
*/
|
|
1242
|
+
reactNativeComponent(path) {
|
|
1243
|
+
console.warn(
|
|
1244
|
+
"reactNativeComponent is deprecated. Use rnComponent() instead."
|
|
1245
|
+
);
|
|
1246
|
+
return { type: "dynamic-import", path };
|
|
1247
|
+
}
|
|
1248
|
+
};
|
|
1249
|
+
|
|
1250
|
+
// src/composables/use-transaction-view.ts
|
|
1251
|
+
function useTransactionView(transaction, options) {
|
|
1252
|
+
const {
|
|
1253
|
+
registry = getGlobalRegistry(),
|
|
1254
|
+
autoLoad = false,
|
|
1255
|
+
fallbackViewId,
|
|
1256
|
+
framework = "lit",
|
|
1257
|
+
minScore = 0,
|
|
1258
|
+
maxMatches,
|
|
1259
|
+
includeFrameworkConfig = true,
|
|
1260
|
+
resolve = false,
|
|
1261
|
+
chain,
|
|
1262
|
+
addressCache: addressCache2
|
|
1263
|
+
} = options;
|
|
1264
|
+
const loader = getGlobalLoader();
|
|
1265
|
+
let matches = [];
|
|
1266
|
+
let bestMatch = null;
|
|
1267
|
+
let component = null;
|
|
1268
|
+
let isLoading = false;
|
|
1269
|
+
let error = null;
|
|
1270
|
+
let isResolvingAddresses = false;
|
|
1271
|
+
let resolvedAddresses = {};
|
|
1272
|
+
const refreshMatches = () => {
|
|
1273
|
+
const matchOptions = {
|
|
1274
|
+
framework,
|
|
1275
|
+
minScore,
|
|
1276
|
+
maxMatches,
|
|
1277
|
+
includeFrameworkConfig
|
|
1278
|
+
};
|
|
1279
|
+
matches = registry.findMatches(transaction, matchOptions);
|
|
1280
|
+
bestMatch = matches[0] || null;
|
|
1281
|
+
if (!bestMatch && fallbackViewId) {
|
|
1282
|
+
const fallbackView = registry.getView(fallbackViewId);
|
|
1283
|
+
if (fallbackView && fallbackView.frameworks[framework]) {
|
|
1284
|
+
bestMatch = {
|
|
1285
|
+
view: fallbackView,
|
|
1286
|
+
score: 0,
|
|
1287
|
+
matchedCriteria: [],
|
|
1288
|
+
frameworkConfig: includeFrameworkConfig ? fallbackView.frameworks[framework] : void 0
|
|
1289
|
+
};
|
|
1290
|
+
}
|
|
1291
|
+
}
|
|
1292
|
+
};
|
|
1293
|
+
const loadMatch = async (match) => {
|
|
1294
|
+
if (!match.frameworkConfig) {
|
|
1295
|
+
throw new ViewLoadingError(
|
|
1296
|
+
`No framework config for view "${match.view.id}" and framework "${framework}"`,
|
|
1297
|
+
{ type: "dynamic-import", path: "" },
|
|
1298
|
+
{}
|
|
1299
|
+
);
|
|
1300
|
+
}
|
|
1301
|
+
isLoading = true;
|
|
1302
|
+
error = null;
|
|
1303
|
+
try {
|
|
1304
|
+
const loadedComponent = await loader.loadFromMatch(match);
|
|
1305
|
+
component = loadedComponent;
|
|
1306
|
+
return loadedComponent;
|
|
1307
|
+
} catch (err) {
|
|
1308
|
+
error = err instanceof ViewLoadingError ? err : new ViewLoadingError(
|
|
1309
|
+
"Unknown loading error",
|
|
1310
|
+
match.frameworkConfig.loader,
|
|
1311
|
+
match.frameworkConfig,
|
|
1312
|
+
err instanceof Error ? err : new Error(String(err))
|
|
1313
|
+
);
|
|
1314
|
+
throw error;
|
|
1315
|
+
} finally {
|
|
1316
|
+
isLoading = false;
|
|
1317
|
+
}
|
|
1318
|
+
};
|
|
1319
|
+
const loadBestMatch = async () => {
|
|
1320
|
+
if (!bestMatch) {
|
|
1321
|
+
throw new Error("No matching view found for transaction");
|
|
1322
|
+
}
|
|
1323
|
+
return loadMatch(bestMatch);
|
|
1324
|
+
};
|
|
1325
|
+
const resolveAddressesFunc = async () => {
|
|
1326
|
+
if (!resolve || !transaction.addresses || transaction.addresses.length === 0) {
|
|
1327
|
+
return;
|
|
1328
|
+
}
|
|
1329
|
+
if (!chain) {
|
|
1330
|
+
console.warn(
|
|
1331
|
+
"Address resolution requested but no chain provided. Pass chain option to resolve addresses."
|
|
1332
|
+
);
|
|
1333
|
+
return;
|
|
1334
|
+
}
|
|
1335
|
+
isResolvingAddresses = true;
|
|
1336
|
+
try {
|
|
1337
|
+
const dataKeys = transaction.addresses.filter((addr) => addr && typeof addr === "string").map((addr) => addr.toLowerCase());
|
|
1338
|
+
if (dataKeys.length === 0) {
|
|
1339
|
+
return;
|
|
1340
|
+
}
|
|
1341
|
+
const endpoint = (0, import_transaction_decoder.getGraphQLEndpoint)(chain);
|
|
1342
|
+
const resolvedMap = await (0, import_transaction_decoder.fetchMultipleAddresses)(
|
|
1343
|
+
dataKeys,
|
|
1344
|
+
endpoint,
|
|
1345
|
+
addressCache2
|
|
1346
|
+
);
|
|
1347
|
+
const resolved = {};
|
|
1348
|
+
resolvedMap.forEach((enhancedInfo, dataKey) => {
|
|
1349
|
+
resolved[dataKey] = enhancedInfo;
|
|
1350
|
+
});
|
|
1351
|
+
resolvedAddresses = resolved;
|
|
1352
|
+
} catch (err) {
|
|
1353
|
+
console.error("Address resolution failed:", err);
|
|
1354
|
+
} finally {
|
|
1355
|
+
isResolvingAddresses = false;
|
|
1356
|
+
}
|
|
1357
|
+
};
|
|
1358
|
+
refreshMatches();
|
|
1359
|
+
if (resolve) {
|
|
1360
|
+
resolveAddressesFunc().catch((err) => {
|
|
1361
|
+
console.error("Auto address resolution failed:", err);
|
|
1362
|
+
});
|
|
1363
|
+
}
|
|
1364
|
+
if (autoLoad && bestMatch) {
|
|
1365
|
+
loadBestMatch().catch((err) => {
|
|
1366
|
+
console.error("Auto-load failed:", err);
|
|
1367
|
+
});
|
|
1368
|
+
}
|
|
1369
|
+
return {
|
|
1370
|
+
matches,
|
|
1371
|
+
bestMatch,
|
|
1372
|
+
component,
|
|
1373
|
+
isLoading,
|
|
1374
|
+
error,
|
|
1375
|
+
isResolvingAddresses,
|
|
1376
|
+
resolvedAddresses,
|
|
1377
|
+
loadMatch,
|
|
1378
|
+
loadBestMatch,
|
|
1379
|
+
refreshMatches,
|
|
1380
|
+
resolveAddresses: resolveAddressesFunc
|
|
1381
|
+
};
|
|
1382
|
+
}
|
|
1383
|
+
function findBestTransactionView(transaction, framework, registry) {
|
|
1384
|
+
const reg = registry || getGlobalRegistry();
|
|
1385
|
+
const matches = reg.findMatches(transaction, {
|
|
1386
|
+
framework,
|
|
1387
|
+
includeFrameworkConfig: true
|
|
1388
|
+
});
|
|
1389
|
+
return matches.length > 0 ? matches[0] : null;
|
|
1390
|
+
}
|
|
1391
|
+
function findAllTransactionViews(transaction, framework, registry) {
|
|
1392
|
+
const reg = registry || getGlobalRegistry();
|
|
1393
|
+
return reg.findMatches(transaction, {
|
|
1394
|
+
framework,
|
|
1395
|
+
includeFrameworkConfig: true
|
|
1396
|
+
});
|
|
1397
|
+
}
|
|
1398
|
+
|
|
1399
|
+
// src/index.ts
|
|
1400
|
+
init_lukso_config();
|
|
1401
|
+
|
|
1402
|
+
// src/hooks/useAddressQuery.ts
|
|
1403
|
+
init_useAddressResolution();
|
|
1404
|
+
function getAddressQueryKey(address, chainId) {
|
|
1405
|
+
return ["address", address.toLowerCase(), chainId || "current"];
|
|
1406
|
+
}
|
|
1407
|
+
function getAddressesQueryKey(addresses, chainId) {
|
|
1408
|
+
const sortedAddresses = [...addresses].map((addr) => addr.toLowerCase()).sort();
|
|
1409
|
+
return ["addresses", sortedAddresses.join(","), chainId || "current"];
|
|
1410
|
+
}
|
|
1411
|
+
async function queryAddress({
|
|
1412
|
+
queryKey
|
|
1413
|
+
}) {
|
|
1414
|
+
const [, address, chainIdOrCurrent] = queryKey;
|
|
1415
|
+
const chainId = chainIdOrCurrent === "current" ? void 0 : chainIdOrCurrent;
|
|
1416
|
+
return resolveAddress(address, chainId);
|
|
1417
|
+
}
|
|
1418
|
+
async function queryAddresses({
|
|
1419
|
+
queryKey
|
|
1420
|
+
}) {
|
|
1421
|
+
const [, addressesStr, chainIdOrCurrent] = queryKey;
|
|
1422
|
+
const chainId = chainIdOrCurrent === "current" ? void 0 : chainIdOrCurrent;
|
|
1423
|
+
const addresses = addressesStr.split(",");
|
|
1424
|
+
return resolveAddresses(addresses, chainId);
|
|
1425
|
+
}
|
|
1426
|
+
var addressQueryOptions = {
|
|
1427
|
+
/**
|
|
1428
|
+
* Single address query options
|
|
1429
|
+
*/
|
|
1430
|
+
single: (address, chainId) => ({
|
|
1431
|
+
queryKey: getAddressQueryKey(address, chainId),
|
|
1432
|
+
queryFn: queryAddress,
|
|
1433
|
+
staleTime: 5 * 60 * 1e3,
|
|
1434
|
+
// 5 minutes
|
|
1435
|
+
gcTime: 10 * 60 * 1e3
|
|
1436
|
+
// 10 minutes (formerly cacheTime)
|
|
1437
|
+
}),
|
|
1438
|
+
/**
|
|
1439
|
+
* Batch addresses query options
|
|
1440
|
+
*/
|
|
1441
|
+
batch: (addresses, chainId) => ({
|
|
1442
|
+
queryKey: getAddressesQueryKey(addresses, chainId),
|
|
1443
|
+
queryFn: queryAddresses,
|
|
1444
|
+
staleTime: 5 * 60 * 1e3,
|
|
1445
|
+
// 5 minutes
|
|
1446
|
+
gcTime: 10 * 60 * 1e3
|
|
1447
|
+
// 10 minutes
|
|
1448
|
+
})
|
|
1449
|
+
};
|
|
1450
|
+
var addressQueryOptionsVue = {
|
|
1451
|
+
/**
|
|
1452
|
+
* Single address query options for Vue Query
|
|
1453
|
+
*/
|
|
1454
|
+
single: (address, chainId) => ({
|
|
1455
|
+
queryKey: getAddressQueryKey(address, chainId),
|
|
1456
|
+
queryFn: queryAddress,
|
|
1457
|
+
staleTime: 5 * 60 * 1e3,
|
|
1458
|
+
cacheTime: 10 * 60 * 1e3
|
|
1459
|
+
// Vue Query still uses cacheTime
|
|
1460
|
+
}),
|
|
1461
|
+
/**
|
|
1462
|
+
* Batch addresses query options for Vue Query
|
|
1463
|
+
*/
|
|
1464
|
+
batch: (addresses, chainId) => ({
|
|
1465
|
+
queryKey: getAddressesQueryKey(addresses, chainId),
|
|
1466
|
+
queryFn: queryAddresses,
|
|
1467
|
+
staleTime: 5 * 60 * 1e3,
|
|
1468
|
+
cacheTime: 10 * 60 * 1e3
|
|
1469
|
+
})
|
|
1470
|
+
};
|
|
1471
|
+
function getInvalidateAddressesPattern(chainId) {
|
|
1472
|
+
return ["address", chainId || "current"];
|
|
1473
|
+
}
|
|
1474
|
+
function getAllAddressQueryKeys(address) {
|
|
1475
|
+
return [
|
|
1476
|
+
["address", address.toLowerCase(), "current"],
|
|
1477
|
+
["address", address.toLowerCase(), 42],
|
|
1478
|
+
// mainnet
|
|
1479
|
+
["address", address.toLowerCase(), 4201]
|
|
1480
|
+
// testnet
|
|
1481
|
+
];
|
|
1482
|
+
}
|
|
1483
|
+
|
|
1484
|
+
// src/index.ts
|
|
1485
|
+
init_useAddressResolution();
|
|
1486
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
1487
|
+
0 && (module.exports = {
|
|
1488
|
+
CRITERIA_WEIGHTS,
|
|
1489
|
+
DefaultViewRegistry,
|
|
1490
|
+
LoaderHelpers,
|
|
1491
|
+
UniversalViewLoader,
|
|
1492
|
+
ViewLoadingError,
|
|
1493
|
+
addressQueryOptions,
|
|
1494
|
+
addressQueryOptionsVue,
|
|
1495
|
+
cacheAddress,
|
|
1496
|
+
calculateMatchScore,
|
|
1497
|
+
clearAddressCache,
|
|
1498
|
+
createAddressResolutionState,
|
|
1499
|
+
createTransactionPlayback,
|
|
1500
|
+
currentChainSignal,
|
|
1501
|
+
findAllTransactionViews,
|
|
1502
|
+
findBestTransactionView,
|
|
1503
|
+
findMatchingViews,
|
|
1504
|
+
getAddressQueryKey,
|
|
1505
|
+
getAddressesQueryKey,
|
|
1506
|
+
getAllAddressQueryKeys,
|
|
1507
|
+
getCachedAddress,
|
|
1508
|
+
getCurrentChain,
|
|
1509
|
+
getGlobalLoader,
|
|
1510
|
+
getGlobalRegistry,
|
|
1511
|
+
getInvalidateAddressesPattern,
|
|
1512
|
+
getLuksoConfig,
|
|
1513
|
+
getValidPlaybackIndices,
|
|
1514
|
+
initializeChainSignal,
|
|
1515
|
+
isAddressResolutionEnabled,
|
|
1516
|
+
isValidPlaybackIndex,
|
|
1517
|
+
queryAddress,
|
|
1518
|
+
queryAddresses,
|
|
1519
|
+
resetGlobalRegistry,
|
|
1520
|
+
resolveAddress,
|
|
1521
|
+
resolveAddressWithState,
|
|
1522
|
+
resolveAddresses,
|
|
1523
|
+
setCurrentChain,
|
|
1524
|
+
setGlobalLoader,
|
|
1525
|
+
setGlobalRegistry,
|
|
1526
|
+
setLuksoConfig,
|
|
1527
|
+
useAddressResolver,
|
|
1528
|
+
useImageLoader,
|
|
1529
|
+
useLuksoMainnet,
|
|
1530
|
+
useLuksoTestnet,
|
|
1531
|
+
useTransactionPlayback,
|
|
1532
|
+
useTransactionView
|
|
1533
|
+
});
|
|
1534
|
+
//# sourceMappingURL=index.cjs.map
|