@parity/product-sdk 0.1.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.
Files changed (66) hide show
  1. package/LICENSE +201 -0
  2. package/dist/address/index.d.ts +8 -0
  3. package/dist/address/index.js +3 -0
  4. package/dist/address/index.js.map +1 -0
  5. package/dist/bulletin/index.d.ts +1 -0
  6. package/dist/bulletin/index.js +3 -0
  7. package/dist/bulletin/index.js.map +1 -0
  8. package/dist/chain/index.d.ts +1 -0
  9. package/dist/chain/index.js +3 -0
  10. package/dist/chain/index.js.map +1 -0
  11. package/dist/chunk-NVGSGXGH.js +177 -0
  12. package/dist/chunk-NVGSGXGH.js.map +1 -0
  13. package/dist/chunk-XSKBA5SR.js +8 -0
  14. package/dist/chunk-XSKBA5SR.js.map +1 -0
  15. package/dist/contracts/index.d.ts +1 -0
  16. package/dist/contracts/index.js +3 -0
  17. package/dist/contracts/index.js.map +1 -0
  18. package/dist/core/index.d.ts +9 -0
  19. package/dist/core/index.js +13 -0
  20. package/dist/core/index.js.map +1 -0
  21. package/dist/crypto/index.d.ts +1 -0
  22. package/dist/crypto/index.js +3 -0
  23. package/dist/crypto/index.js.map +1 -0
  24. package/dist/host/index.d.ts +1 -0
  25. package/dist/host/index.js +3 -0
  26. package/dist/host/index.js.map +1 -0
  27. package/dist/identity/index.d.ts +186 -0
  28. package/dist/identity/index.js +109 -0
  29. package/dist/identity/index.js.map +1 -0
  30. package/dist/index.d.ts +59 -0
  31. package/dist/index.js +27 -0
  32. package/dist/index.js.map +1 -0
  33. package/dist/react/index.d.ts +177 -0
  34. package/dist/react/index.js +213 -0
  35. package/dist/react/index.js.map +1 -0
  36. package/dist/storage/index.d.ts +1 -0
  37. package/dist/storage/index.js +3 -0
  38. package/dist/storage/index.js.map +1 -0
  39. package/dist/types-CZQDzQ53.d.ts +142 -0
  40. package/dist/wallet/index.d.ts +1 -0
  41. package/dist/wallet/index.js +3 -0
  42. package/dist/wallet/index.js.map +1 -0
  43. package/package.json +105 -0
  44. package/src/address/index.ts +6 -0
  45. package/src/bulletin/index.ts +6 -0
  46. package/src/chain/index.ts +6 -0
  47. package/src/contracts/index.ts +6 -0
  48. package/src/core/createApp.ts +284 -0
  49. package/src/core/index.ts +10 -0
  50. package/src/core/logger.ts +13 -0
  51. package/src/core/types.ts +155 -0
  52. package/src/crypto/index.ts +6 -0
  53. package/src/host/index.ts +6 -0
  54. package/src/identity/dotns.ts +96 -0
  55. package/src/identity/index.ts +34 -0
  56. package/src/identity/product-account.ts +158 -0
  57. package/src/identity/types.ts +75 -0
  58. package/src/index.ts +49 -0
  59. package/src/react/context.ts +33 -0
  60. package/src/react/index.ts +41 -0
  61. package/src/react/provider.tsx +76 -0
  62. package/src/react/useChain.ts +33 -0
  63. package/src/react/useStorage.ts +125 -0
  64. package/src/react/useWallet.ts +138 -0
  65. package/src/storage/index.ts +6 -0
  66. package/src/wallet/index.ts +9 -0
@@ -0,0 +1,284 @@
1
+ /**
2
+ * createApp - Main entry point for the Product SDK
3
+ *
4
+ * Creates an App instance with wallet, storage, chain, and bulletin APIs.
5
+ */
6
+
7
+ import type { ChainDefinition } from "polkadot-api";
8
+ import type {
9
+ App,
10
+ AppConfig,
11
+ WalletApi,
12
+ StorageApi,
13
+ ChainApi,
14
+ BulletinApi,
15
+ Account,
16
+ } from "./types.js";
17
+ import { configure, createLogger } from "@parity/product-sdk-logger";
18
+ import { createKvStore } from "@parity/product-sdk-storage";
19
+ import { SignerManager } from "@parity/product-sdk-signer";
20
+ import { BulletinClient, computeCid } from "@parity/product-sdk-bulletin";
21
+ import {
22
+ createChainClient,
23
+ getClient,
24
+ isConnected,
25
+ destroyAll,
26
+ } from "@parity/product-sdk-chain-client";
27
+
28
+ const log = createLogger("app");
29
+
30
+ /**
31
+ * Create a new Product SDK app instance
32
+ *
33
+ * @param config - Application configuration
34
+ * @returns App instance with all APIs
35
+ *
36
+ * @example
37
+ * ```ts
38
+ * import { createApp } from '@parity/product-sdk';
39
+ *
40
+ * // Default: bulletin enabled with paseo environment
41
+ * const app = await createApp({
42
+ * name: 'my-app',
43
+ * logLevel: 'info',
44
+ * });
45
+ *
46
+ * // Custom bulletin environment
47
+ * const prodApp = await createApp({
48
+ * name: 'my-app',
49
+ * bulletin: { environment: 'polkadot' },
50
+ * });
51
+ *
52
+ * // Disable bulletin entirely
53
+ * const noBulletinApp = await createApp({
54
+ * name: 'my-app',
55
+ * bulletin: false,
56
+ * });
57
+ *
58
+ * // Connect wallet
59
+ * const { accounts } = await app.wallet.connect();
60
+ *
61
+ * // Use storage
62
+ * await app.storage.set('key', 'value');
63
+ *
64
+ * // Use bulletin (check for null if it might be disabled)
65
+ * if (app.bulletin) {
66
+ * const cid = await app.bulletin.upload('hello world');
67
+ * }
68
+ * ```
69
+ */
70
+ export async function createApp(config: AppConfig): Promise<App> {
71
+ // Set log level if specified
72
+ if (config.logLevel) {
73
+ configure({ level: config.logLevel });
74
+ }
75
+
76
+ log.info("Creating Product SDK app", { name: config.name });
77
+
78
+ // Initialize storage (container-only - will throw if not in container)
79
+ const kvStore = await createKvStore({ prefix: config.name });
80
+
81
+ // Initialize signer manager
82
+ const signerManager = new SignerManager({
83
+ dappName: config.name,
84
+ });
85
+
86
+ // Initialize bulletin client (configurable, defaults to paseo)
87
+ const bulletinEnabled = config.bulletin !== false;
88
+ const bulletinEnvironment =
89
+ typeof config.bulletin === "object" ? config.bulletin.environment : "paseo";
90
+ const bulletinClient = bulletinEnabled
91
+ ? await BulletinClient.create(bulletinEnvironment)
92
+ : null;
93
+
94
+ if (bulletinEnabled) {
95
+ log.debug("Bulletin client initialized", { environment: bulletinEnvironment });
96
+ } else {
97
+ log.debug("Bulletin client disabled");
98
+ }
99
+
100
+ // Create storage API adapter
101
+ const storageApi: StorageApi = {
102
+ get: (key) => kvStore.get(key),
103
+ set: (key, value) => kvStore.set(key, value),
104
+ getJSON: <T>(key: string) => kvStore.getJSON<T>(key),
105
+ setJSON: <T>(key: string, value: T) => kvStore.setJSON(key, value),
106
+ remove: (key) => kvStore.remove(key),
107
+ clear: async () => {
108
+ // KvStore doesn't have clear - this is a no-op
109
+ log.debug("clear() is not supported in container storage mode");
110
+ },
111
+ };
112
+
113
+ // Create wallet API adapter
114
+ const walletApi = createWalletApi(signerManager);
115
+
116
+ // Create chain API
117
+ const chainApi: ChainApi = {
118
+ getClient(descriptor) {
119
+ log.debug("getClient called", { genesis: descriptor.genesis });
120
+ const client = getClient(descriptor);
121
+ return client.getTypedApi(descriptor);
122
+ },
123
+
124
+ getRawClient(descriptor) {
125
+ log.debug("getRawClient called", { genesis: descriptor.genesis });
126
+ return getClient(descriptor);
127
+ },
128
+
129
+ async connect<T extends Record<string, ChainDefinition>>(chains: T) {
130
+ log.debug("connect called", { chains: Object.keys(chains) });
131
+ // Build empty rpcs object (required by API but unused - host routes connections)
132
+ const rpcs = Object.fromEntries(
133
+ Object.keys(chains).map((k) => [k, [] as readonly string[]]),
134
+ ) as { [K in keyof T]: readonly string[] };
135
+ return createChainClient({ chains, rpcs });
136
+ },
137
+
138
+ isConnected(descriptor) {
139
+ return isConnected(descriptor);
140
+ },
141
+
142
+ destroyAll() {
143
+ log.debug("destroyAll called");
144
+ destroyAll();
145
+ },
146
+ };
147
+
148
+ // Create bulletin API adapter (null if disabled)
149
+ const bulletinApi: BulletinApi | null = bulletinClient
150
+ ? {
151
+ upload: async (data) => {
152
+ const bytes = typeof data === "string" ? new TextEncoder().encode(data) : data;
153
+ const result = await bulletinClient.upload(bytes);
154
+ return result.cid;
155
+ },
156
+ fetch: (cid) => bulletinClient.fetchBytes(cid),
157
+ computeCid: (data) => {
158
+ const bytes = typeof data === "string" ? new TextEncoder().encode(data) : data;
159
+ return computeCid(bytes);
160
+ },
161
+ }
162
+ : null;
163
+
164
+ log.info("Product SDK app created", {
165
+ name: config.name,
166
+ bulletin: bulletinEnabled ? bulletinEnvironment : "disabled",
167
+ });
168
+
169
+ return {
170
+ wallet: walletApi,
171
+ storage: storageApi,
172
+ chain: chainApi,
173
+ bulletin: bulletinApi,
174
+ getAppInfo: () => ({ ...config }),
175
+ };
176
+ }
177
+
178
+ /**
179
+ * Create wallet API adapter using SignerManager from leaf package
180
+ */
181
+ function createWalletApi(signerManager: SignerManager): WalletApi {
182
+ // Track account change subscribers
183
+ const accountChangeSubscribers = new Set<(account: Account | null) => void>();
184
+
185
+ // Subscribe to signer manager state changes
186
+ signerManager.subscribe((state) => {
187
+ const account = state.selectedAccount
188
+ ? {
189
+ address: state.selectedAccount.address,
190
+ name: state.selectedAccount.name ?? undefined,
191
+ source: state.selectedAccount.source,
192
+ }
193
+ : null;
194
+ for (const callback of accountChangeSubscribers) {
195
+ try {
196
+ callback(account);
197
+ } catch (e) {
198
+ log.warn("Account change callback threw", { error: e });
199
+ }
200
+ }
201
+ });
202
+
203
+ return {
204
+ async connect(): Promise<{ accounts: Account[] }> {
205
+ const result = await signerManager.connect();
206
+ if (!result.ok) {
207
+ throw new Error(result.error.message);
208
+ }
209
+ return {
210
+ accounts: result.value.map((a) => ({
211
+ address: a.address,
212
+ name: a.name ?? undefined,
213
+ source: a.source,
214
+ })),
215
+ };
216
+ },
217
+
218
+ async disconnect(): Promise<void> {
219
+ signerManager.disconnect();
220
+ },
221
+
222
+ getAccounts(): Account[] {
223
+ return signerManager.getState().accounts.map((a) => ({
224
+ address: a.address,
225
+ name: a.name ?? undefined,
226
+ source: a.source,
227
+ }));
228
+ },
229
+
230
+ getSelectedAccount(): Account | null {
231
+ const selected = signerManager.getState().selectedAccount;
232
+ if (!selected) return null;
233
+ return {
234
+ address: selected.address,
235
+ name: selected.name ?? undefined,
236
+ source: selected.source,
237
+ };
238
+ },
239
+
240
+ selectAccount(address: string): void {
241
+ signerManager.selectAccount(address);
242
+ },
243
+
244
+ async signMessage(message: string | Uint8Array): Promise<Uint8Array> {
245
+ const bytes = typeof message === "string" ? new TextEncoder().encode(message) : message;
246
+ const result = await signerManager.signRaw(bytes);
247
+ if (!result.ok) {
248
+ throw new Error(result.error.message);
249
+ }
250
+ return result.value;
251
+ },
252
+
253
+ onAccountChange(callback: (account: Account | null) => void): () => void {
254
+ accountChangeSubscribers.add(callback);
255
+ return () => accountChangeSubscribers.delete(callback);
256
+ },
257
+
258
+ getProductAccount(): Account | null {
259
+ // Product accounts require async call - this sync API can't support it properly
260
+ // Users should use SignerManager.getProductAccount() directly
261
+ log.warn(
262
+ "getProductAccount() is deprecated - use SignerManager.getProductAccount() directly",
263
+ );
264
+ return null;
265
+ },
266
+
267
+ getAnonymousAlias(): string | null {
268
+ // Anonymous aliases require async call - this sync API can't support it properly
269
+ // Users should use SignerManager.getProductAccountAlias() directly
270
+ log.warn(
271
+ "getAnonymousAlias() is deprecated - use SignerManager.getProductAccountAlias() directly",
272
+ );
273
+ return null;
274
+ },
275
+
276
+ async createProof(_message: Uint8Array): Promise<Uint8Array> {
277
+ // Ring VRF proofs require SignerManager.createRingVRFProof() directly
278
+ throw new Error(
279
+ "createProof() is not implemented in the App API. " +
280
+ "Use SignerManager.createRingVRFProof() directly.",
281
+ );
282
+ },
283
+ };
284
+ }
@@ -0,0 +1,10 @@
1
+ /**
2
+ * @parity/product-sdk core module
3
+ *
4
+ * Core functionality including createApp, logger, and type definitions.
5
+ */
6
+
7
+ export { createApp } from "./createApp.js";
8
+ export { configure, createLogger } from "./logger.js";
9
+ export type { LogEntry, LogHandler, LoggerConfig, Logger } from "./logger.js";
10
+ export * from "./types.js";
@@ -0,0 +1,13 @@
1
+ /**
2
+ * Logger module for @parity/product-sdk
3
+ *
4
+ * Re-exports from @parity/product-sdk-logger.
5
+ */
6
+ export { configure, createLogger } from "@parity/product-sdk-logger";
7
+ export type {
8
+ LogLevel,
9
+ LogEntry,
10
+ LogHandler,
11
+ LoggerConfig,
12
+ Logger,
13
+ } from "@parity/product-sdk-logger";
@@ -0,0 +1,155 @@
1
+ /**
2
+ * Core types for @parity/product-sdk
3
+ */
4
+
5
+ import type { LogLevel } from "@parity/product-sdk-logger";
6
+ import type { Environment as BulletinEnvironment } from "@parity/product-sdk-bulletin";
7
+ import type { ChainClient } from "@parity/product-sdk-chain-client";
8
+ import type { ChainDefinition, TypedApi, PolkadotClient } from "polkadot-api";
9
+
10
+ export type { LogLevel };
11
+ export type { ChainClient };
12
+
13
+ /** Bulletin configuration options */
14
+ export interface BulletinConfig {
15
+ /** Bulletin environment to connect to */
16
+ environment: BulletinEnvironment;
17
+ }
18
+
19
+ /** Configuration for createApp */
20
+ export interface AppConfig {
21
+ /** Application name - used to derive product accounts and namespace storage */
22
+ name: string;
23
+ /** Log level for SDK operations (default: 'info') */
24
+ logLevel?: LogLevel;
25
+ /**
26
+ * Bulletin Chain configuration.
27
+ * - Omit or pass config object to enable (default: { environment: "paseo" })
28
+ * - Pass `false` to disable bulletin initialization
29
+ */
30
+ bulletin?: BulletinConfig | false;
31
+ }
32
+
33
+ /** Wallet API exposed by the SDK */
34
+ export interface WalletApi {
35
+ /** Connect to available wallet providers */
36
+ connect(): Promise<{ accounts: Account[] }>;
37
+ /** Disconnect from wallet */
38
+ disconnect(): Promise<void>;
39
+ /** Get all available accounts */
40
+ getAccounts(): Account[];
41
+ /** Get currently selected account */
42
+ getSelectedAccount(): Account | null;
43
+ /** Select an account by address */
44
+ selectAccount(address: string): void;
45
+ /** Sign an arbitrary message */
46
+ signMessage(message: string | Uint8Array): Promise<Uint8Array>;
47
+ /** Subscribe to account changes */
48
+ onAccountChange(callback: (account: Account | null) => void): () => void;
49
+ /** Get product-scoped account (container mode only) */
50
+ getProductAccount(): Account | null;
51
+ /** Get anonymous alias via Ring VRF (container mode only) */
52
+ getAnonymousAlias(): string | null;
53
+ /** Create Ring VRF proof (container mode only) */
54
+ createProof(message: Uint8Array): Promise<Uint8Array>;
55
+ }
56
+
57
+ /** Storage API exposed by the SDK */
58
+ export interface StorageApi {
59
+ /** Get a value by key */
60
+ get(key: string): Promise<string | null>;
61
+ /** Set a value by key */
62
+ set(key: string, value: string): Promise<void>;
63
+ /** Get a JSON value by key */
64
+ getJSON<T = unknown>(key: string): Promise<T | null>;
65
+ /** Set a JSON value by key */
66
+ setJSON<T = unknown>(key: string, value: T): Promise<void>;
67
+ /** Remove a value by key */
68
+ remove(key: string): Promise<void>;
69
+ /** Clear all values */
70
+ clear(): Promise<void>;
71
+ }
72
+
73
+ /** Chain API exposed by the SDK */
74
+ export interface ChainApi {
75
+ /**
76
+ * Get a typed PAPI client for a chain.
77
+ *
78
+ * Connections are routed through the host provider. The chain must be
79
+ * connected first via {@link connect}.
80
+ *
81
+ * @param descriptor - PAPI chain descriptor (from @parity/product-sdk-descriptors or custom)
82
+ * @returns Typed API for the chain
83
+ * @throws If the chain is not connected
84
+ */
85
+ getClient<T extends ChainDefinition>(descriptor: T): TypedApi<T>;
86
+
87
+ /**
88
+ * Get the raw PolkadotClient for a chain.
89
+ *
90
+ * Use this for advanced APIs like `createInkSdk` from `@polkadot-api/sdk-ink`.
91
+ *
92
+ * @param descriptor - PAPI chain descriptor
93
+ * @returns Raw PolkadotClient instance
94
+ * @throws If the chain is not connected
95
+ */
96
+ getRawClient(descriptor: ChainDefinition): PolkadotClient;
97
+
98
+ /**
99
+ * Connect to one or more chains.
100
+ *
101
+ * Connections are routed through the host provider (container-only).
102
+ * Results are cached - calling with the same descriptors returns existing connections.
103
+ *
104
+ * @param chains - Record of named chain descriptors
105
+ * @returns Connected chain client with typed APIs
106
+ */
107
+ connect<T extends Record<string, ChainDefinition>>(chains: T): Promise<ChainClient<T>>;
108
+
109
+ /**
110
+ * Check if a chain is currently connected.
111
+ */
112
+ isConnected(descriptor: ChainDefinition): boolean;
113
+
114
+ /**
115
+ * Destroy all chain connections.
116
+ */
117
+ destroyAll(): void;
118
+ }
119
+
120
+ /** Bulletin Chain API exposed by the SDK */
121
+ export interface BulletinApi {
122
+ /** Upload data to Bulletin Chain */
123
+ upload(data: string | Uint8Array): Promise<string>;
124
+ /** Fetch data by CID */
125
+ fetch(cid: string): Promise<Uint8Array>;
126
+ /** Compute CID for data without uploading */
127
+ computeCid(data: string | Uint8Array): string;
128
+ }
129
+
130
+ /** The main App instance returned by createApp */
131
+ export interface App {
132
+ /** Wallet/signing operations */
133
+ wallet: WalletApi;
134
+ /** Key-value storage operations */
135
+ storage: StorageApi;
136
+ /** Chain interaction operations */
137
+ chain: ChainApi;
138
+ /** Bulletin Chain operations (null if disabled via config) */
139
+ bulletin: BulletinApi | null;
140
+ /** Get app configuration */
141
+ getAppInfo(): AppConfig;
142
+ }
143
+
144
+ /** Account information */
145
+ export interface Account {
146
+ /** Account address (SS58 format) */
147
+ address: string;
148
+ /** Account name/label (if available) */
149
+ name?: string;
150
+ /** Source of the account (extension name, host, etc.) */
151
+ source: string;
152
+ }
153
+
154
+ // Re-export ChainDefinition from polkadot-api for convenience
155
+ export type { ChainDefinition, TypedApi, PolkadotClient } from "polkadot-api";
@@ -0,0 +1,6 @@
1
+ /**
2
+ * @parity/product-sdk/crypto
3
+ *
4
+ * Re-exports from @parity/product-sdk-crypto.
5
+ */
6
+ export * from "@parity/product-sdk-crypto";
@@ -0,0 +1,6 @@
1
+ /**
2
+ * @parity/product-sdk/host
3
+ *
4
+ * Re-exports from @parity/product-sdk-host.
5
+ */
6
+ export * from "@parity/product-sdk-host";
@@ -0,0 +1,96 @@
1
+ /**
2
+ * DotNS (Polkadot Name Service) utilities
3
+ *
4
+ * Provides name resolution for .dot domains
5
+ */
6
+
7
+ import { createLogger } from "@parity/product-sdk-logger";
8
+ import type { DotNsRecord } from "./types.js";
9
+
10
+ const log = createLogger("identity");
11
+
12
+ /**
13
+ * Check if a string is a valid DotNS name
14
+ *
15
+ * @param name - Name to validate
16
+ * @returns True if valid DotNS name
17
+ */
18
+ export function isValidDotNsName(name: string): boolean {
19
+ // Basic validation: alphanumeric, hyphens, ends with .dot
20
+ if (!name.endsWith(".dot")) return false;
21
+ const label = name.slice(0, -4);
22
+ if (label.length < 3 || label.length > 63) return false;
23
+ return /^[a-z0-9]([a-z0-9-]*[a-z0-9])?$/.test(label);
24
+ }
25
+
26
+ /**
27
+ * Normalize a DotNS name (lowercase, trim whitespace)
28
+ *
29
+ * @param name - Name to normalize
30
+ * @returns Normalized name
31
+ */
32
+ export function normalizeDotNsName(name: string): string {
33
+ let normalized = name.toLowerCase().trim();
34
+ if (!normalized.endsWith(".dot")) {
35
+ normalized += ".dot";
36
+ }
37
+ return normalized;
38
+ }
39
+
40
+ /**
41
+ * Resolve a DotNS name to an address
42
+ *
43
+ * @param name - DotNS name (e.g., "alice.dot")
44
+ * @returns Resolved record or null if not found
45
+ *
46
+ * @example
47
+ * ```ts
48
+ * const record = await resolveDotNs('alice.dot');
49
+ * if (record) {
50
+ * console.log('Address:', record.address);
51
+ * }
52
+ * ```
53
+ */
54
+ export async function resolveDotNs(name: string): Promise<DotNsRecord | null> {
55
+ const normalized = normalizeDotNsName(name);
56
+
57
+ if (!isValidDotNsName(normalized)) {
58
+ log.warn("Invalid DotNS name", { name });
59
+ return null;
60
+ }
61
+
62
+ log.debug("Resolving DotNS name", { name: normalized });
63
+
64
+ // TODO: Implement via PAPI query to DotNS pallet
65
+ throw new Error(
66
+ "resolveDotNs() is not yet implemented. " +
67
+ "This is a skeleton for the Product SDK structure.",
68
+ );
69
+ }
70
+
71
+ /**
72
+ * Reverse resolve an address to a DotNS name
73
+ *
74
+ * @param address - SS58 address
75
+ * @returns Primary name or null if none set
76
+ */
77
+ export async function reverseDotNs(address: string): Promise<string | null> {
78
+ log.debug("Reverse resolving address", { address });
79
+
80
+ // TODO: Implement via PAPI query to DotNS pallet
81
+ throw new Error(
82
+ "reverseDotNs() is not yet implemented. " +
83
+ "This is a skeleton for the Product SDK structure.",
84
+ );
85
+ }
86
+
87
+ /**
88
+ * Check if a DotNS name is available for registration
89
+ *
90
+ * @param name - Name to check
91
+ * @returns True if available
92
+ */
93
+ export async function isDotNsAvailable(name: string): Promise<boolean> {
94
+ const record = await resolveDotNs(name).catch(() => null);
95
+ return record === null;
96
+ }
@@ -0,0 +1,34 @@
1
+ /**
2
+ * @parity/product-sdk/identity
3
+ *
4
+ * Identity utilities including DotNS name resolution,
5
+ * product account derivation, and Ring VRF anonymous aliases.
6
+ */
7
+
8
+ // DotNS utilities
9
+ export {
10
+ isValidDotNsName,
11
+ normalizeDotNsName,
12
+ resolveDotNs,
13
+ reverseDotNs,
14
+ isDotNsAvailable,
15
+ } from "./dotns.js";
16
+
17
+ // Product account utilities
18
+ export {
19
+ deriveProductAccount,
20
+ verifyProductAccount,
21
+ deriveAnonymousAlias,
22
+ createRingProof,
23
+ verifyRingProof,
24
+ } from "./product-account.js";
25
+
26
+ // Types
27
+ export type {
28
+ DotNsRecord,
29
+ ProductAccountInfo,
30
+ AnonymousAliasInfo,
31
+ RingLocation,
32
+ VerificationResult,
33
+ OnChainIdentity,
34
+ } from "./types.js";