@liberfi.io/ui-perpetuals 0.2.1 → 0.2.3

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/dist/index.d.mts CHANGED
@@ -12,7 +12,7 @@ declare global {
12
12
  };
13
13
  }
14
14
  }
15
- declare const _default: "0.2.1";
15
+ declare const _default: "0.2.3";
16
16
 
17
17
  /**
18
18
  * Trading pair symbol format
@@ -755,6 +755,244 @@ declare class HyperliquidApiError extends Error {
755
755
  constructor(message: string, statusCode: number, responseBody: string);
756
756
  }
757
757
 
758
+ /**
759
+ * Hyperliquid Setup Adapter
760
+ *
761
+ * Hyperliquid account-state changes (approve builder fee, set referrer,
762
+ * update leverage) are EIP-712 signed actions sent to /exchange. Encoding
763
+ * the canonical action hash (msgpack + phantom agent + chain-id-aware
764
+ * domain) is non-trivial and there are several vetted client libraries
765
+ * already (@deeeed/hyperliquid, @nktkas/hyperliquid, @hyperliquid-rust-sdk
766
+ * via wasm, etc.).
767
+ *
768
+ * Rather than inlining that logic into this SDK — which would force a
769
+ * specific dependency on every consumer and bloat the bundle — this
770
+ * package defines a thin adapter contract. Consumers wire in whichever
771
+ * implementation they prefer; this SDK only knows the input/output shape
772
+ * and the idempotency story.
773
+ *
774
+ * Design principles:
775
+ * - First principles: the SDK does not need to know how the action is
776
+ * signed, only that the consumer can read state and perform each
777
+ * setup step. Signing & encoding live with the wallet integration.
778
+ * - Open-Closed: new setup steps (e.g. sub-account, vault) can be added
779
+ * by extending the adapter interface — existing consumers don't break.
780
+ * - Liskov: every method returns the same shape so the orchestrator
781
+ * can treat all steps uniformly in its state machine.
782
+ */
783
+
784
+ /**
785
+ * Snapshot of the user's relevant Hyperliquid account state.
786
+ *
787
+ * Returned by `getAccountState` and used by `useHyperliquidSetup` to
788
+ * decide which steps still need to run. All fields are optional because
789
+ * a fresh account may have none of them set.
790
+ */
791
+ interface HyperliquidAccountState {
792
+ /**
793
+ * The builder address (typically the platform's relayer) and the
794
+ * approved fee in tenths-of-a-basis-point. If `null`, the builder has
795
+ * not been approved yet.
796
+ *
797
+ * Hyperliquid encodes builder fees as integers in 0.001%; e.g. `45`
798
+ * means 0.045% — a common Axiom-style default.
799
+ */
800
+ builderApproval: {
801
+ builder: string;
802
+ /** Tenths of a basis point (0.001%). */
803
+ maxFeeRate: number;
804
+ } | null;
805
+ /**
806
+ * The referrer code currently bound to this account, or `null` if the
807
+ * user has never set one. Hyperliquid only accepts a referrer once;
808
+ * subsequent calls must be skipped.
809
+ */
810
+ referrer: string | null;
811
+ /**
812
+ * Per-asset leverage configuration. Keyed by Hyperliquid asset name
813
+ * (e.g. `"BTC"`, `"ETH"`), value is the user's currently selected
814
+ * leverage. Empty when the user has not customised any asset.
815
+ */
816
+ leverage: Record<string, number>;
817
+ }
818
+ /**
819
+ * Parameters for `approveBuilderFee`. The maximum fee is expressed in
820
+ * tenths of a basis point to match Hyperliquid's wire format and avoid
821
+ * floating-point drift.
822
+ */
823
+ interface ApproveBuilderFeeParams {
824
+ builder: string;
825
+ /** Tenths of a basis point (0.001%). 45 = 0.045% (Axiom default). */
826
+ maxFeeRate: number;
827
+ }
828
+ interface SetReferrerParams {
829
+ /** Hyperliquid referrer code (e.g. "AXIOM"). */
830
+ code: string;
831
+ }
832
+ interface UpdateLeverageParams {
833
+ /** Hyperliquid asset name without the suffix (e.g. "BTC", "ETH"). */
834
+ asset: string;
835
+ /** Whole-number leverage multiplier (e.g. 5 for 5x). */
836
+ leverage: number;
837
+ /**
838
+ * Whether to use cross-margin (true) or isolated margin (false).
839
+ * Defaults to cross to mirror Axiom's default UX.
840
+ */
841
+ isCross?: boolean;
842
+ }
843
+ /**
844
+ * Result returned by every adapter method. `txHash` is optional because
845
+ * Hyperliquid actions don't always surface a hash; the success of the
846
+ * action is what the orchestrator cares about.
847
+ */
848
+ interface HyperliquidSetupActionResult {
849
+ /** Optional action receipt — surfaced to the UI when present. */
850
+ txHash?: string;
851
+ /**
852
+ * The new state captured immediately after the action — lets the hook
853
+ * skip re-fetching `getAccountState`. Optional; the hook will fall
854
+ * back to a refresh call when omitted.
855
+ */
856
+ state?: Partial<HyperliquidAccountState>;
857
+ }
858
+ /**
859
+ * Adapter contract. Implementations may live in a consumer app (Privy +
860
+ * @nktkas/hyperliquid, for example) or be supplied by a future
861
+ * `@liberfi.io/wallet-connector-*` package.
862
+ */
863
+ interface IHyperliquidSetupAdapter {
864
+ /**
865
+ * Hyperliquid environment this adapter targets — the orchestrator
866
+ * uses it for diagnostic logging only.
867
+ */
868
+ readonly environment: HyperliquidEnvironment;
869
+ /**
870
+ * Read the user's current setup state. Used to decide which steps
871
+ * still need to run, so MUST reflect the latest on-chain truth (not a
872
+ * cache that may be stale after a setup attempt).
873
+ */
874
+ getAccountState(userAddress: string): Promise<HyperliquidAccountState>;
875
+ /** Sign + submit `approveBuilderFee` action; idempotent at the API. */
876
+ approveBuilderFee(params: ApproveBuilderFeeParams): Promise<HyperliquidSetupActionResult>;
877
+ /**
878
+ * Sign + submit `setReferrer` action.
879
+ *
880
+ * Hyperliquid rejects re-binding once a code is set, so the
881
+ * orchestrator gates this with `getAccountState().referrer == null`
882
+ * before calling. Adapters should still surface a clear error if the
883
+ * user retries after the gate.
884
+ */
885
+ setReferrer(params: SetReferrerParams): Promise<HyperliquidSetupActionResult>;
886
+ /** Sign + submit `updateLeverage` action; idempotent at the API. */
887
+ updateLeverage(params: UpdateLeverageParams): Promise<HyperliquidSetupActionResult>;
888
+ }
889
+
890
+ /**
891
+ * Shared REST transport for every LiberFi perpetuals-server client.
892
+ *
893
+ * Pulled out of `LiberFiPerpetualsClient` so the deposit client (and any
894
+ * future feature client) can reuse the same fetch-with-timeout, error
895
+ * mapping, and header merging logic without copy-paste.
896
+ *
897
+ * Design choices:
898
+ *
899
+ * - The class is intentionally minimal: build URL → fire fetch →
900
+ * decode JSON → throw a typed error on non-2xx. No retries, no
901
+ * circuit breaker, no caching. That layering belongs to the caller
902
+ * (e.g. TanStack Query handles retries/cache).
903
+ *
904
+ * - Custom query parameters are passed per-request, not per-instance,
905
+ * except for `defaultQuery` which the perpetuals client uses for the
906
+ * `?provider=` selector.
907
+ *
908
+ * - Headers merge in three layers (call > instance > built-in). This
909
+ * lets a caller add a one-off `Authorization` for a single request
910
+ * without leaking it into the rest of the session.
911
+ */
912
+ /**
913
+ * Thrown when perpetuals-server returns a non-2xx HTTP status, when the
914
+ * request times out, or when the network call fails outright.
915
+ *
916
+ * `statusCode` is the HTTP status (or `0` for network errors / `408`
917
+ * for client-side timeouts). `responseBody` is the verbatim response
918
+ * text — useful for surfacing backend error codes to the user.
919
+ */
920
+ declare class LiberFiApiError extends Error {
921
+ readonly statusCode: number;
922
+ readonly responseBody: string;
923
+ constructor(message: string, statusCode: number, responseBody: string);
924
+ }
925
+ /** Configuration for {@link LiberFiHttpTransport}. */
926
+ interface LiberFiHttpTransportConfig {
927
+ /**
928
+ * REST base URL, with NO trailing slash. The transport strips trailing
929
+ * slashes on construction so callers can pass either form.
930
+ */
931
+ baseUrl: string;
932
+ /** Per-request timeout in milliseconds. Defaults to 30 000 ms. */
933
+ timeout?: number;
934
+ /**
935
+ * Headers merged into every request. Per-request headers (passed to
936
+ * `request()`) win on key collision, then instance headers, then the
937
+ * built-in `Accept` / `Content-Type`.
938
+ */
939
+ headers?: Record<string, string>;
940
+ /**
941
+ * Default query parameters appended to every request URL. Useful for
942
+ * cross-cutting selectors like `?provider=hyperliquid`. Per-request
943
+ * params override on key collision.
944
+ */
945
+ defaultQuery?: Record<string, string | undefined>;
946
+ /**
947
+ * Custom `fetch` implementation. Defaults to the global `fetch`.
948
+ * Useful in tests (drop in a jest mock) or in environments where a
949
+ * pre-configured fetch (e.g. with circuit breaker / proxy) is supplied
950
+ * by the host application.
951
+ */
952
+ fetchImpl?: typeof fetch;
953
+ }
954
+ /** HTTP method shape — keep narrow; deposit and trading both use these. */
955
+ type LiberFiHttpMethod = "GET" | "POST";
956
+ /** Per-request options accepted by {@link LiberFiHttpTransport.request}. */
957
+ interface RequestOptions {
958
+ /** Path relative to `baseUrl` (must start with `/`). */
959
+ path: string;
960
+ /** Optional query string parameters. Undefined / empty values are skipped. */
961
+ query?: Record<string, string | undefined>;
962
+ /** JSON body for POST/PUT/etc. */
963
+ body?: unknown;
964
+ /** One-off headers — overrides the instance defaults. */
965
+ headers?: Record<string, string>;
966
+ /**
967
+ * Override the per-instance timeout for this single request.
968
+ * Use for fast-path reads or long-running submits.
969
+ */
970
+ timeoutMs?: number;
971
+ }
972
+ /**
973
+ * Stateless HTTP transport shared by every LiberFi perpetuals-server
974
+ * client. Construct one per client (or one shared instance — the class
975
+ * is safe for concurrent use).
976
+ */
977
+ declare class LiberFiHttpTransport {
978
+ private readonly baseUrl;
979
+ private readonly timeout;
980
+ private readonly headers?;
981
+ private readonly defaultQuery?;
982
+ private readonly fetchImpl;
983
+ constructor(config: LiberFiHttpTransportConfig);
984
+ /** Read-only accessor used by the perpetuals client for WebSocket fallback. */
985
+ getBaseUrl(): string;
986
+ /** Build a fully-qualified URL with merged query string. */
987
+ buildUrl(path: string, query?: Record<string, string | undefined>): string;
988
+ /**
989
+ * Issue an HTTP request and decode the JSON response. Returns
990
+ * `undefined` (cast to T) for `204 No Content`. Throws
991
+ * {@link LiberFiApiError} on every non-2xx, timeout, or network error.
992
+ */
993
+ request<T>(method: LiberFiHttpMethod, opts: RequestOptions): Promise<T>;
994
+ }
995
+
758
996
  /**
759
997
  * `signTypedData` is invoked once per place / cancel during the
760
998
  * `prepare → submit` flow. The hosting app injects this so the user's wallet
@@ -773,9 +1011,11 @@ interface LiberFiPerpetualsClientConfig {
773
1011
  * - Staging: `https://api.liberfi.io/staging/perpetuals`
774
1012
  * - Production: `https://api.liberfi.io/perpetuals`
775
1013
  *
776
- * The client appends `/v1/...` paths to this value.
1014
+ * The client appends `/v1/...` paths to this value. Required UNLESS a
1015
+ * pre-built {@link LiberFiHttpTransport} is supplied via `transport`,
1016
+ * in which case the transport's baseUrl is used.
777
1017
  */
778
- baseUrl: string;
1018
+ baseUrl?: string;
779
1019
  /**
780
1020
  * Optional WebSocket endpoint. Real-time data is NOT proxied by
781
1021
  * perpetuals-server today — the WS subscription methods connect directly to
@@ -789,6 +1029,7 @@ interface LiberFiPerpetualsClientConfig {
789
1029
  signTypedData?: SignTypedDataFn;
790
1030
  /**
791
1031
  * Per-request timeout in milliseconds. Defaults to 30 000 ms.
1032
+ * Ignored when `transport` is provided (the transport carries its own).
792
1033
  */
793
1034
  timeout?: number;
794
1035
  /**
@@ -799,15 +1040,16 @@ interface LiberFiPerpetualsClientConfig {
799
1040
  provider?: string;
800
1041
  /**
801
1042
  * Optional extra request headers (auth tokens, tracing, etc.) merged into
802
- * every fetch.
1043
+ * every fetch. Ignored when `transport` is provided.
803
1044
  */
804
1045
  headers?: Record<string, string>;
805
- }
806
- /** Thrown when perpetuals-server returns a non-2xx HTTP status. */
807
- declare class LiberFiApiError extends Error {
808
- readonly statusCode: number;
809
- readonly responseBody: string;
810
- constructor(message: string, statusCode: number, responseBody: string);
1046
+ /**
1047
+ * Inject a pre-built transport instead of letting the client construct
1048
+ * one from `baseUrl` / `timeout` / `headers`. Required when sharing a
1049
+ * single transport with the deposit client to halve the per-call
1050
+ * configuration footprint in `PerpetualsProvider`.
1051
+ */
1052
+ transport?: LiberFiHttpTransport;
811
1053
  }
812
1054
  /**
813
1055
  * REST + injected-signer implementation of {@link IPerpetualsClient} that talks
@@ -825,18 +1067,11 @@ declare class LiberFiApiError extends Error {
825
1067
  * exchange (`wsEndpoint`, default Hyperliquid mainnet).
826
1068
  */
827
1069
  declare class LiberFiPerpetualsClient implements IPerpetualsClient {
828
- private readonly baseUrl;
1070
+ private readonly transport;
829
1071
  private readonly wsEndpoint;
830
- private readonly timeout;
831
- private readonly provider?;
832
- private readonly headers?;
833
1072
  private readonly signTypedData?;
834
1073
  private wsManager;
835
1074
  constructor(config: LiberFiPerpetualsClientConfig);
836
- /** Build a fully-qualified URL with optional query string. */
837
- private url;
838
- /** Common fetch wrapper with timeout + structured error mapping. */
839
- private request;
840
1075
  getSupportedCoins(): Promise<string[]>;
841
1076
  getMarket(symbol: string): Promise<MarketData | null>;
842
1077
  getMarkets(symbols?: string[]): Promise<MarketData[]>;
@@ -857,37 +1092,346 @@ declare class LiberFiPerpetualsClient implements IPerpetualsClient {
857
1092
  private requireWS;
858
1093
  }
859
1094
 
1095
+ /**
1096
+ * Wire / domain types for the Solana → Hyperliquid USDC deposit flow.
1097
+ *
1098
+ * These deliberately mirror the perpetuals-server DTOs (see
1099
+ * `internal/handler/deposit_handler.go`) so the SDK <-> backend contract
1100
+ * stays in sync. When the backend adds a new field, add it here too —
1101
+ * the compiler will then point at every place that needs to handle it.
1102
+ *
1103
+ * All amounts denominated in *smallest unit* (lamports for SOL, USDC's
1104
+ * 6-decimal microUSDC for the destination side) are typed as `string` so
1105
+ * we never accidentally lose precision on large values.
1106
+ */
1107
+ /** Where the deposit was initiated from. Drives fee attribution server-side. */
1108
+ type DepositSource = "dex" | "prediction" | "launchpad" | "channel";
1109
+ /** Lifecycle states a deposit can be in. */
1110
+ type DepositStatus = "broadcasted" | "relay_waiting" | "relay_pending" | "settled" | "refunded" | "failed" | "stuck";
1111
+ /** True for status values that never transition further. */
1112
+ declare const TERMINAL_DEPOSIT_STATUSES: ReadonlySet<DepositStatus>;
1113
+ /** A single state transition in the status history. */
1114
+ interface DepositStatusTransition {
1115
+ from: DepositStatus | "";
1116
+ to: DepositStatus;
1117
+ at: string;
1118
+ source: "handler" | "status_pull" | "reconciliation" | string;
1119
+ reason?: string;
1120
+ }
1121
+ /** Surfaced when the upstream produced an unrecoverable error. */
1122
+ interface DepositErrorInfo {
1123
+ code: string;
1124
+ message: string;
1125
+ recoverable: boolean;
1126
+ }
1127
+ /** Exact-decimal breakdown returned by the quote endpoint. */
1128
+ interface DepositBreakdown {
1129
+ /** Total lamports the user is paying in (gross). */
1130
+ grossLamports: string;
1131
+ /** Platform fee transferred to the LiberFi treasury (lamports). */
1132
+ platformFeeLamports: string;
1133
+ /** Net amount Relay bridges (= gross − platformFee), in lamports. */
1134
+ relayDepositLamports: string;
1135
+ /** SOL pubkey the platform fee is sent to. May be empty when fee = 0. */
1136
+ treasuryAddress: string;
1137
+ /** Expected destination output, in microUSDC (6-decimal). May be empty. */
1138
+ expectedOutputUSDC?: string;
1139
+ /** Origin chain id (Solana mainnet on Relay = 792703809). */
1140
+ originChainId: number;
1141
+ /** Destination chain id (Hyperliquid). */
1142
+ destinationChainId: number;
1143
+ /** Origin currency. SOL is encoded as the SystemProgram pseudo-pubkey. */
1144
+ originCurrency: string;
1145
+ /** Destination currency contract. */
1146
+ destinationCurrency: string;
1147
+ /** Relay-issued depository address — the program/wallet receiving SOL. */
1148
+ depository?: string;
1149
+ /** Relay request id; populated once Relay returns a quote. */
1150
+ relayRequestId?: string;
1151
+ }
1152
+ /** Body of POST /v1/deposits/quote. */
1153
+ interface DepositQuoteRequest {
1154
+ userSolanaAddress: string;
1155
+ hyperliquidRecipient: string;
1156
+ /** Smallest-unit amount the user is paying in. */
1157
+ grossLamports: string;
1158
+ /** Fee attribution source. Defaults to `dex` server-side when empty. */
1159
+ source: DepositSource;
1160
+ }
1161
+ /** Response of POST /v1/deposits/quote. */
1162
+ interface DepositQuoteResponse {
1163
+ /** Base64 SOL transaction the user signs in their wallet. */
1164
+ serializedTxBase64: string;
1165
+ /** Transaction size on the wire (used by client-side guards). */
1166
+ sizeBytes: number;
1167
+ /** True for v0 transactions (legacy = false). */
1168
+ isVersioned: boolean;
1169
+ breakdown: DepositBreakdown;
1170
+ /** ISO 8601 timestamp the quote was issued at. */
1171
+ issuedAt: string;
1172
+ /** ISO 8601 timestamp the quote expires at. */
1173
+ expiresAt: string;
1174
+ }
1175
+ /** Body of POST /v1/deposits/submit. */
1176
+ interface DepositSubmitRequest {
1177
+ userSolanaAddress: string;
1178
+ hyperliquidRecipient: string;
1179
+ /** The signed transaction's hash, returned by the wallet on broadcast. */
1180
+ solanaTxHash: string;
1181
+ breakdown: DepositBreakdown;
1182
+ /** Stable user identifier (LiberFi user id, NOT the wallet address). */
1183
+ userId: string;
1184
+ source: DepositSource;
1185
+ /** Optional marketing campaign / referral code passed through to attribution. */
1186
+ campaign?: string;
1187
+ /** Mirror back the issuedAt from /quote so the server can guard freshness. */
1188
+ quoteIssuedAt: string;
1189
+ }
1190
+ /** Response of POST /v1/deposits/submit. */
1191
+ interface DepositSubmitResponse {
1192
+ intentId: string;
1193
+ /** True the first time a unique solanaTxHash is seen; idempotent retries return false. */
1194
+ created: boolean;
1195
+ }
1196
+ /** Response of GET /v1/deposits/{id}. */
1197
+ interface DepositStatusResponse {
1198
+ intentId: string;
1199
+ status: DepositStatus;
1200
+ userSolanaAddress: string;
1201
+ hyperliquidRecipient: string;
1202
+ solanaTxHash: string;
1203
+ relayRequestId?: string;
1204
+ hyperliquidTxHash?: string;
1205
+ breakdown: DepositBreakdown;
1206
+ statusHistory: DepositStatusTransition[];
1207
+ lastError?: DepositErrorInfo;
1208
+ userId: string;
1209
+ source: DepositSource;
1210
+ campaign?: string;
1211
+ createdAt: string;
1212
+ updatedAt: string;
1213
+ }
1214
+
1215
+ /**
1216
+ * REST client for the Solana → Hyperliquid deposit endpoints exposed by
1217
+ * the perpetuals-server (`/v1/deposits/*`).
1218
+ *
1219
+ * Engineering principles:
1220
+ * - Single responsibility: this file knows about /v1/deposits and
1221
+ * nothing else. Quote orchestration, fee adapters, status
1222
+ * reconciliation, etc. live server-side.
1223
+ * - Modularity: the HTTP transport is injected (or built from a
1224
+ * baseUrl) so integration tests can drop in a fetch mock; production
1225
+ * code shares the same transport instance with `LiberFiPerpetualsClient`.
1226
+ * - First principles: three methods (quote / submit / status), no
1227
+ * hidden state, no caching. Polling is the caller's concern (the
1228
+ * hooks do it via TanStack Query).
1229
+ */
1230
+
1231
+ /**
1232
+ * Options for constructing a `LiberFiPerpDepositClient`.
1233
+ *
1234
+ * Either provide a pre-built `transport` (preferred — share one with
1235
+ * `LiberFiPerpetualsClient` so connection limits, headers and timeouts
1236
+ * stay consistent) or pass the raw config and let the client build one.
1237
+ */
1238
+ type LiberFiPerpDepositClientConfig = {
1239
+ transport: LiberFiHttpTransport;
1240
+ } | LiberFiHttpTransportConfig;
1241
+ /** Public surface of the deposit client; matches the three handler endpoints. */
1242
+ interface IPerpDepositClient {
1243
+ /** POST /v1/deposits/quote */
1244
+ quote(req: DepositQuoteRequest): Promise<DepositQuoteResponse>;
1245
+ /** POST /v1/deposits/submit */
1246
+ submit(req: DepositSubmitRequest): Promise<DepositSubmitResponse>;
1247
+ /** GET /v1/deposits/{id} */
1248
+ status(intentId: string): Promise<DepositStatusResponse>;
1249
+ /** POST /v1/deposits/{id}/refresh — bypasses any future cache TTL. */
1250
+ refresh(intentId: string): Promise<DepositStatusResponse>;
1251
+ }
1252
+ /** Concrete implementation backed by `LiberFiHttpTransport`. */
1253
+ declare class LiberFiPerpDepositClient implements IPerpDepositClient {
1254
+ private readonly transport;
1255
+ constructor(config: LiberFiPerpDepositClientConfig);
1256
+ /** Returns the base URL of the underlying transport (mostly for logs/diagnostics). */
1257
+ getBaseUrl(): string;
1258
+ quote(req: DepositQuoteRequest): Promise<DepositQuoteResponse>;
1259
+ submit(req: DepositSubmitRequest): Promise<DepositSubmitResponse>;
1260
+ status(intentId: string): Promise<DepositStatusResponse>;
1261
+ refresh(intentId: string): Promise<DepositStatusResponse>;
1262
+ }
1263
+
1264
+ /**
1265
+ * Pure state machine for the deposit UI.
1266
+ *
1267
+ * The backend owns the *authoritative* lifecycle (broadcasted → relay_*
1268
+ * → settled / refunded / failed / stuck). The frontend has a few extra
1269
+ * states *before* we can call /submit (idle, quoting, ready_to_sign,
1270
+ * signing, broadcasting). We model both halves here as a single FSM so
1271
+ * presentational components can switch on a single tag.
1272
+ *
1273
+ * Engineering principles applied:
1274
+ * - First principles: a state is a *type*, transitions are pure
1275
+ * functions over (state, event) → state. No timers, no fetch, no
1276
+ * setState — those live in hooks.
1277
+ * - Single responsibility: this file knows nothing about HTTP, React,
1278
+ * or wallets. It is unit-testable in isolation.
1279
+ * - Extensibility: add a new event by extending DepositEvent + a case
1280
+ * in `reduceDepositState`. The compiler enforces exhaustiveness.
1281
+ */
1282
+
1283
+ /** UI-only state tags. Server-driven tags are a subset of DepositStatus. */
1284
+ type DepositPhase = "idle" | "quoting" | "ready_to_sign" | "signing" | "broadcasting" | "submitted" | "tracking" | "succeeded" | "refunded" | "failed" | "expired";
1285
+ /** Discriminated union representing the entire deposit flow at any moment. */
1286
+ type DepositState = {
1287
+ phase: "idle";
1288
+ } | {
1289
+ phase: "quoting";
1290
+ } | {
1291
+ phase: "ready_to_sign";
1292
+ quote: DepositQuoteResponse;
1293
+ /** Epoch ms — caller pre-computes for stable comparisons. */
1294
+ expiresAtMs: number;
1295
+ } | {
1296
+ phase: "signing";
1297
+ quote: DepositQuoteResponse;
1298
+ } | {
1299
+ phase: "broadcasting";
1300
+ quote: DepositQuoteResponse;
1301
+ } | {
1302
+ phase: "submitted";
1303
+ quote: DepositQuoteResponse;
1304
+ intentId: string;
1305
+ solanaTxHash: string;
1306
+ } | {
1307
+ phase: "tracking";
1308
+ intentId: string;
1309
+ status: DepositStatusResponse;
1310
+ } | {
1311
+ phase: "succeeded";
1312
+ intentId: string;
1313
+ status: DepositStatusResponse;
1314
+ } | {
1315
+ phase: "refunded";
1316
+ intentId: string;
1317
+ status: DepositStatusResponse;
1318
+ } | {
1319
+ phase: "failed";
1320
+ error: DepositErrorInfo;
1321
+ /** Populated when the failure happened post-submit. */
1322
+ intentId?: string;
1323
+ status?: DepositStatusResponse;
1324
+ } | {
1325
+ phase: "expired";
1326
+ quote: DepositQuoteResponse;
1327
+ };
1328
+ /** Events the FSM can react to. Driven by hooks/components. */
1329
+ type DepositEvent = {
1330
+ type: "RESET";
1331
+ } | {
1332
+ type: "QUOTE_REQUEST";
1333
+ } | {
1334
+ type: "QUOTE_RECEIVED";
1335
+ quote: DepositQuoteResponse;
1336
+ } | {
1337
+ type: "QUOTE_FAILED";
1338
+ error: DepositErrorInfo;
1339
+ } | {
1340
+ type: "QUOTE_EXPIRED";
1341
+ } | {
1342
+ type: "SIGN_START";
1343
+ } | {
1344
+ type: "SIGN_FAILED";
1345
+ error: DepositErrorInfo;
1346
+ } | {
1347
+ type: "BROADCAST_START";
1348
+ } | {
1349
+ type: "BROADCAST_FAILED";
1350
+ error: DepositErrorInfo;
1351
+ } | {
1352
+ type: "SUBMIT_OK";
1353
+ intentId: string;
1354
+ solanaTxHash: string;
1355
+ } | {
1356
+ type: "SUBMIT_FAILED";
1357
+ error: DepositErrorInfo;
1358
+ } | {
1359
+ type: "STATUS_UPDATE";
1360
+ status: DepositStatusResponse;
1361
+ };
1362
+ declare const initialDepositState: DepositState;
1363
+ /**
1364
+ * Transition function. Pure, total — every (state, event) pair is
1365
+ * handled. Unknown transitions are no-ops (return current state); we
1366
+ * don't throw because hooks may fan out events optimistically (e.g. a
1367
+ * stale STATUS_UPDATE arriving after RESET).
1368
+ */
1369
+ declare function reduceDepositState(state: DepositState, event: DepositEvent): DepositState;
1370
+ /** True when the FSM has reached a terminal phase. */
1371
+ declare function isTerminal(state: DepositState): boolean;
1372
+ /** True when the UI should keep polling /status. */
1373
+ declare function isPolling(state: DepositState): boolean;
1374
+ /** Returns the current backend lifecycle status, if any. */
1375
+ declare function currentStatus(state: DepositState): DepositStatus | undefined;
1376
+ /** Returns the breakdown the UI should display, if any. */
1377
+ declare function currentBreakdown(state: DepositState): DepositBreakdown | undefined;
1378
+ /**
1379
+ * Returns true when the phase is terminal *and* corresponds to one of
1380
+ * the known DepositStatus terminal values. Useful for analytics fan-out
1381
+ * (only emit the funnel-end event once per intent).
1382
+ */
1383
+ declare function isTerminalLifecycle(status: DepositStatus | undefined): boolean;
1384
+
860
1385
  /**
861
1386
  * Perpetuals context value type
862
1387
  *
863
- * Provides access to the perpetuals trading client instance
1388
+ * Provides access to the perpetuals trading client and (optionally) the
1389
+ * deposit client. The deposit client is optional because not every
1390
+ * surface that consumes this provider also needs the deposit flow — a
1391
+ * portfolio view that only renders positions can omit it without
1392
+ * pulling the deposit dependency along.
864
1393
  */
865
1394
  interface PerpetualsContextValue {
866
1395
  /**
867
- * Perpetuals client instance for trading operations
1396
+ * Perpetuals client instance for trading operations.
868
1397
  */
869
1398
  client: IPerpetualsClient;
1399
+ /**
1400
+ * Deposit client instance for the Solana → Hyperliquid funding flow.
1401
+ *
1402
+ * Optional: surfaces that don't render the deposit UI can omit it.
1403
+ * Hooks that need it (e.g. `usePerpDepositQuote`) will throw a clear
1404
+ * error pointing at the missing prop.
1405
+ */
1406
+ depositClient?: IPerpDepositClient;
870
1407
  }
871
1408
  /**
872
1409
  * Perpetuals Context
873
1410
  *
874
- * React context for accessing perpetuals trading functionality throughout the app
1411
+ * React context for accessing perpetuals trading + deposit functionality
1412
+ * throughout the app.
875
1413
  */
876
1414
  declare const PerpetualsContext: react.Context<PerpetualsContextValue>;
877
1415
 
878
1416
  /**
879
- * Perpetuals provider props type
1417
+ * Perpetuals provider props type.
1418
+ *
1419
+ * `client` is required; `depositClient` is optional and only needed by
1420
+ * surfaces that render the cross-chain deposit flow.
880
1421
  */
881
1422
  type PerpetualsProviderProps = PropsWithChildren<PerpetualsContextValue>;
882
1423
  /**
883
- * Perpetuals Provider Component
1424
+ * Perpetuals Provider Component.
884
1425
  *
885
- * Provides perpetuals trading client to all child components via React Context
1426
+ * Wraps the perpetuals trading client and (optionally) the deposit
1427
+ * client into a single context value. The value is memoised on the
1428
+ * client identities so re-renders of the consumer app do not break
1429
+ * referential equality for downstream `useContext` consumers.
886
1430
  *
887
- * @param props Provider props containing client and children
1431
+ * @param props Provider props containing client(s) and children
888
1432
  * @returns Provider component wrapping children
889
1433
  */
890
- declare function PerpetualsProvider({ client, children, }: PerpetualsProviderProps): react_jsx_runtime.JSX.Element;
1434
+ declare function PerpetualsProvider({ client, depositClient, children, }: PerpetualsProviderProps): react_jsx_runtime.JSX.Element;
891
1435
 
892
1436
  /**
893
1437
  * Hook to access perpetuals client from context
@@ -1009,6 +1553,292 @@ interface UseUserDataSubscriptionResult<T> {
1009
1553
  }
1010
1554
  declare function useUserDataSubscription<T = UserDataType extends "orders" ? Order : UserDataType extends "positions" ? Position : TradeHistory>(params: UseUserDataSubscriptionParams): UseUserDataSubscriptionResult<T>;
1011
1555
 
1556
+ /**
1557
+ * Hook to access the deposit client from `PerpetualsProvider`.
1558
+ *
1559
+ * Throws if the provider is missing OR if the host app forgot to pass
1560
+ * `depositClient`. The thrown message tells the consumer exactly what
1561
+ * to fix — preferring an explicit error to a silent runtime crash deep
1562
+ * inside a useQuery hook.
1563
+ *
1564
+ * @returns The deposit client instance.
1565
+ */
1566
+ declare function usePerpDepositClient(): IPerpDepositClient;
1567
+
1568
+ /**
1569
+ * Stable query key shape for the deposit quote.
1570
+ *
1571
+ * The amount is part of the key so re-quoting on amount change does not
1572
+ * leak across users; the user/recipient pair is included so two users
1573
+ * sharing the same browser session don't see each other's quotes in the
1574
+ * cache.
1575
+ */
1576
+ declare function perpDepositQuoteQueryKey(req?: DepositQuoteRequest | null): readonly unknown[];
1577
+ /** Pure fetcher — useful for SSR or for invoking outside React. */
1578
+ declare function fetchPerpDepositQuote(client: IPerpDepositClient, req: DepositQuoteRequest): Promise<DepositQuoteResponse>;
1579
+ interface UsePerpDepositQuoteOptions extends Omit<UseQueryOptions<DepositQuoteResponse, Error, DepositQuoteResponse, ReturnType<typeof perpDepositQuoteQueryKey>>, "queryKey" | "queryFn" | "enabled"> {
1580
+ /**
1581
+ * Override automatic gating. By default the query runs when `req` is
1582
+ * fully populated. Pass `enabled: false` to defer firing while the
1583
+ * user is still typing the amount.
1584
+ */
1585
+ enabled?: boolean;
1586
+ }
1587
+ /**
1588
+ * Re-quotes on every parameter change, with TanStack Query handling
1589
+ * dedupe / refetch / cancellation. Caller is responsible for surfacing
1590
+ * `data.expiresAt` to the UI; the FSM will move to `expired` if the
1591
+ * user lingers past the deadline.
1592
+ *
1593
+ * Engineering note: the hook deliberately does NOT auto-refresh on a
1594
+ * timer. Re-quoting silently behind the user would erase the “Confirm”
1595
+ * button mid-action; the form should re-call `refetch()` on its own
1596
+ * cadence (e.g. when `expiresAt` is < 5 s from now).
1597
+ */
1598
+ declare function usePerpDepositQuote(req: DepositQuoteRequest | null | undefined, options?: UsePerpDepositQuoteOptions): _tanstack_react_query.UseQueryResult<DepositQuoteResponse, Error>;
1599
+
1600
+ /**
1601
+ * Adapter the host app must provide. Lives on the consumer side so the
1602
+ * SDK never has to know how a particular wallet (Phantom / Backpack /
1603
+ * Privy / Solflare / …) signs and broadcasts a Solana transaction.
1604
+ *
1605
+ * Contract:
1606
+ * - Decode the `serializedTxBase64` produced by /quote.
1607
+ * - Have the user sign it (this is when the wallet UI shows up).
1608
+ * - Broadcast it. Return the resulting tx hash.
1609
+ * - Throw on user rejection or RPC failure.
1610
+ *
1611
+ * The SDK keeps things narrow: signature, broadcast, and "did the wallet
1612
+ * succeed" are the only outputs we care about. Everything else (RPC
1613
+ * endpoint, commitment, simulation pre-checks) is an implementation
1614
+ * detail the host already owns.
1615
+ */
1616
+ type SignAndBroadcastSolanaTx = (serializedTxBase64: string, ctx: {
1617
+ isVersioned: boolean;
1618
+ sizeBytes: number;
1619
+ }) => Promise<string>;
1620
+ /** Inputs every deposit attempt needs. */
1621
+ interface ExecuteDepositInput {
1622
+ /** The quote previously returned by `/v1/deposits/quote`. */
1623
+ quote: DepositQuoteResponse;
1624
+ /** User-facing identifiers; must match what was sent to /quote. */
1625
+ userSolanaAddress: string;
1626
+ hyperliquidRecipient: string;
1627
+ /** LiberFi user id (NOT the wallet). Stable for fee attribution. */
1628
+ userId: string;
1629
+ source: DepositSource;
1630
+ /** Optional marketing / referral code. */
1631
+ campaign?: string;
1632
+ }
1633
+ /** Hook return shape — exposes the full FSM and a single trigger. */
1634
+ interface UsePerpDepositExecuteResult {
1635
+ state: DepositState;
1636
+ /**
1637
+ * Kick off the sign → broadcast → submit chain. Returns the eventual
1638
+ * `intentId` on success, throws on failure (the FSM will already be
1639
+ * in the `failed` phase with a descriptive `error`).
1640
+ */
1641
+ execute: (input: ExecuteDepositInput) => Promise<string>;
1642
+ /** Force back to `idle`. Use when the user dismisses the modal. */
1643
+ reset: () => void;
1644
+ /** Manually push an event into the FSM (advanced). */
1645
+ dispatch: (event: DepositEvent) => void;
1646
+ }
1647
+ /**
1648
+ * Orchestrates the full deposit flow:
1649
+ *
1650
+ * 1. SIGN_START → wallet signs (host adapter)
1651
+ * 2. BROADCAST_START → wallet broadcasts (host adapter)
1652
+ * 3. SUBMIT_OK → POST /v1/deposits/submit (this hook)
1653
+ * 4. STATUS_UPDATE ← `usePerpDepositStatus` polls and forwards
1654
+ *
1655
+ * Each stage emits a typed event into the same reducer used by the
1656
+ * presentational components. The hook itself never renders anything —
1657
+ * components consume `state.phase` and react accordingly.
1658
+ */
1659
+ declare function usePerpDepositExecute(signAndBroadcast: SignAndBroadcastSolanaTx): UsePerpDepositExecuteResult;
1660
+
1661
+ declare function perpDepositStatusQueryKey(intentId?: string): readonly unknown[];
1662
+ declare function fetchPerpDepositStatus(client: IPerpDepositClient, intentId: string): Promise<DepositStatusResponse>;
1663
+ interface UsePerpDepositStatusOptions extends Omit<UseQueryOptions<DepositStatusResponse, Error, DepositStatusResponse, ReturnType<typeof perpDepositStatusQueryKey>>, "queryKey" | "queryFn" | "refetchInterval" | "enabled"> {
1664
+ enabled?: boolean;
1665
+ /**
1666
+ * Polling interval in milliseconds while the deposit is non-terminal.
1667
+ * Defaults to 3 000 ms — matches the backend's reconciliation cadence
1668
+ * with a small safety margin.
1669
+ */
1670
+ pollIntervalMs?: number;
1671
+ }
1672
+ /**
1673
+ * Polls /v1/deposits/{id} until the deposit reaches a terminal status,
1674
+ * then stops the timer automatically. The component is responsible for
1675
+ * forwarding `data` into the deposit FSM via STATUS_UPDATE events.
1676
+ *
1677
+ * Engineering principle (single responsibility): this hook owns the
1678
+ * "when to ask the server" question; the FSM owns the "what does the
1679
+ * answer mean" question. They communicate through plain typed values.
1680
+ */
1681
+ declare function usePerpDepositStatus(intentId: string | undefined | null, options?: UsePerpDepositStatusOptions): _tanstack_react_query.UseQueryResult<DepositStatusResponse, Error>;
1682
+
1683
+ /**
1684
+ * Pure state machine for the Hyperliquid initialisation flow.
1685
+ *
1686
+ * Driven by `useReducer` — kept as a separate module so the transition
1687
+ * logic is unit-testable without React. The states cover the full
1688
+ * lifecycle:
1689
+ *
1690
+ * idle
1691
+ * → loading (caller pressed "init", reading current state)
1692
+ * → ready (we know which steps remain)
1693
+ * → executing (one step is in flight)
1694
+ * → done | error
1695
+ *
1696
+ * `error` is recoverable — `RETRY_STEP` returns the FSM to `executing`.
1697
+ * `RESET` always rewinds to `idle` so the caller can re-check status.
1698
+ */
1699
+
1700
+ /** Identifier for each setup step — drives the UI checklist. */
1701
+ type SetupStepId = "approveBuilderFee" | "setReferrer" | "updateLeverage";
1702
+ /**
1703
+ * A single step in the setup checklist. `params` carry exactly the
1704
+ * information the adapter needs to perform the action — the FSM never
1705
+ * inspects them; it only routes them to the adapter.
1706
+ */
1707
+ type SetupStep = {
1708
+ id: "approveBuilderFee";
1709
+ params: ApproveBuilderFeeParams;
1710
+ } | {
1711
+ id: "setReferrer";
1712
+ params: SetReferrerParams;
1713
+ } | {
1714
+ id: "updateLeverage";
1715
+ params: UpdateLeverageParams;
1716
+ };
1717
+ /** Per-step status tracked across the checklist. */
1718
+ type StepStatus = "pending" | "skipped" | "running" | "done" | "error";
1719
+ interface StepRecord {
1720
+ step: SetupStep;
1721
+ status: StepStatus;
1722
+ /** Last error message captured for the step. */
1723
+ error?: string;
1724
+ /** Optional tx hash returned by the adapter. */
1725
+ txHash?: string;
1726
+ }
1727
+ type SetupPhase = "idle" | "loading" | "ready" | "executing" | "done" | "error";
1728
+ interface SetupState {
1729
+ phase: SetupPhase;
1730
+ /** Snapshot of the on-chain state captured during `loading`. */
1731
+ accountState?: HyperliquidAccountState;
1732
+ /** All steps requested by the caller, in order. */
1733
+ steps: StepRecord[];
1734
+ /** Index of the step currently executing (only valid in `executing`). */
1735
+ currentIndex?: number;
1736
+ /** Top-level error — typically from `getAccountState`. */
1737
+ error?: string;
1738
+ }
1739
+ type SetupAction = {
1740
+ type: "START_LOADING";
1741
+ } | {
1742
+ type: "LOAD_SUCCESS";
1743
+ accountState: HyperliquidAccountState;
1744
+ steps: StepRecord[];
1745
+ } | {
1746
+ type: "LOAD_ERROR";
1747
+ error: string;
1748
+ } | {
1749
+ type: "RUN_STEP";
1750
+ index: number;
1751
+ } | {
1752
+ type: "STEP_SUCCESS";
1753
+ index: number;
1754
+ txHash?: string;
1755
+ accountState?: HyperliquidAccountState;
1756
+ } | {
1757
+ type: "STEP_ERROR";
1758
+ index: number;
1759
+ error: string;
1760
+ } | {
1761
+ type: "RESET";
1762
+ };
1763
+ declare const initialSetupState: SetupState;
1764
+ /**
1765
+ * Determine the initial status of a step given the current on-chain
1766
+ * state. `done` (sometimes called `skipped` to the user) means the
1767
+ * action has already happened and we can elide it.
1768
+ *
1769
+ * Encapsulated as a pure function so the same logic is exercised by
1770
+ * both the loader (when `LOAD_SUCCESS` constructs the checklist) and
1771
+ * the adapter result handler (when an action reports a partial state
1772
+ * update).
1773
+ */
1774
+ declare function classifyStep(step: SetupStep, state: HyperliquidAccountState): StepStatus;
1775
+ declare function reduceSetupState(state: SetupState, action: SetupAction): SetupState;
1776
+ /**
1777
+ * Find the next step that still needs to run. Returns `null` when the
1778
+ * checklist is complete — the caller should treat the FSM as `done`.
1779
+ */
1780
+ declare function nextRunnableStep(state: SetupState): number | null;
1781
+
1782
+ /**
1783
+ * Configuration for the Hyperliquid setup orchestrator.
1784
+ *
1785
+ * The hook is intentionally adapter-agnostic — it does not import any
1786
+ * Hyperliquid signing code. The consumer wires in an adapter (typically
1787
+ * built around their wallet integration) plus the list of steps they
1788
+ * want to run.
1789
+ */
1790
+ interface UseHyperliquidSetupOptions {
1791
+ /** Adapter that knows how to read state and submit signed actions. */
1792
+ adapter: IHyperliquidSetupAdapter;
1793
+ /** EVM address of the user (required to read account state). */
1794
+ userAddress: string | undefined;
1795
+ /**
1796
+ * The steps the consumer wants the user to complete. Order is
1797
+ * preserved in the UI, and the orchestrator advances strictly in
1798
+ * sequence so failures don't strand the user mid-checklist.
1799
+ */
1800
+ steps: SetupStep[];
1801
+ /**
1802
+ * If true, the hook performs an initial state read on mount /
1803
+ * adapter change. Defaults to `true`.
1804
+ */
1805
+ autoLoad?: boolean;
1806
+ /** Optional callback invoked once every step is `done` or `skipped`. */
1807
+ onComplete?: (state: SetupState) => void;
1808
+ /** Optional callback for diagnostic logging. */
1809
+ onError?: (err: Error, context: {
1810
+ stepId?: SetupStep["id"];
1811
+ }) => void;
1812
+ }
1813
+ interface UseHyperliquidSetupResult {
1814
+ state: SetupState;
1815
+ /** Re-fetch the on-chain state. Idempotent — safe to call repeatedly. */
1816
+ reload: () => Promise<void>;
1817
+ /** Run the next pending / error step. No-op when the checklist is done. */
1818
+ runNext: () => Promise<void>;
1819
+ /** Run a specific step by index — used by per-row "Retry" buttons. */
1820
+ runStep: (index: number) => Promise<void>;
1821
+ /** Reset the FSM to `idle` (e.g. when the user closes the wizard). */
1822
+ reset: () => void;
1823
+ }
1824
+ /**
1825
+ * Orchestrates the Hyperliquid first-run setup checklist.
1826
+ *
1827
+ * Responsibilities:
1828
+ * - Read the user's account state via the adapter.
1829
+ * - Classify each requested step against that state, marking ones
1830
+ * already done as `skipped`.
1831
+ * - Advance through the remaining steps, calling the appropriate
1832
+ * adapter method and merging the returned partial state back.
1833
+ * - Surface errors per-step so the UI can show a precise retry CTA.
1834
+ *
1835
+ * Out of scope:
1836
+ * - Signing — adapter does it.
1837
+ * - Persistence — Hyperliquid is the source of truth; we re-read on
1838
+ * reload instead of caching across sessions.
1839
+ */
1840
+ declare function useHyperliquidSetup(opts: UseHyperliquidSetupOptions): UseHyperliquidSetupResult;
1841
+
1012
1842
  type CoinInfoWidgetProps = {
1013
1843
  symbol: string;
1014
1844
  };
@@ -1297,4 +2127,211 @@ declare function TradeHistoryUI({ trades, timeRange, onTimeRangeChange, currentP
1297
2127
  declare function TradeHistorySkeleton(): react_jsx_runtime.JSX.Element;
1298
2128
  declare function TradeHistoryEmpty(): react_jsx_runtime.JSX.Element;
1299
2129
 
1300
- export { type Account, type CancelOrderParams, type CancelOrderResult, type Coin, CoinInfoNotFoundUI, CoinInfoSkeletonsUI, CoinInfoUI, type CoinInfoUIProps, CoinInfoWidget, type CoinInfoWidgetProps, type GetOpenOrdersParams, type GetOpenOrdersResult, type GetPositionsParams, type GetPositionsResult, type GetTradesParams, type GetTradesResult, HyperliquidApiError, type HyperliquidClientConfig, type HyperliquidEnvironment, HyperliquidPerpetualsClient, type IPerpetualsClient, type Kline, type KlineInterval, LiberFiApiError, LiberFiPerpetualsClient, type LiberFiPerpetualsClientConfig, type MarketData, type MarketDataType, OpenOrdersEmpty, OpenOrdersSkeleton, OpenOrdersUI, type OpenOrdersUIProps, OpenOrdersWidget, type OpenOrdersWidgetProps, type Order, type OrderBook, type OrderBookLevel, OrderBookUI, type OrderBookUIProps, OrderBookWidget, type OrderBookWidgetProps, type OrderSide, type OrderStatus, type OrderType, PerpetualsContext, type PerpetualsContextValue, PerpetualsProvider, type PerpetualsProviderProps, type PlaceOrderFormData, PlaceOrderFormUI, type PlaceOrderFormUIProps, PlaceOrderFormWidget, type PlaceOrderFormWidgetProps, type PlaceOrderParams, type PlaceOrderResult, type Position, PositionsEmpty, PositionsSkeleton, PositionsUI, type PositionsUIProps, PositionsWidget, type PositionsWidgetProps, type PriceLevel, SearchCoinsUI, type SearchCoinsUIProps, SearchCoinsWidget, type SearchCoinsWidgetProps, type SignTypedDataFn, type Symbol, type TimeRange, type Trade, type TradeHistory, TradeHistoryEmpty, TradeHistorySkeleton, TradeHistoryUI, type TradeHistoryUIProps, TradeHistoryWidget, type TradeHistoryWidgetProps, type TradeSide, TradesUI, type TradesUIProps, TradesWidget, type TradesWidgetProps, type TradingProvider, type UseCancelOrderMutationParams, type UseCandlesSubscriptionParams, type UseCandlesSubscriptionResult, type UseCoinInfoReturnType, type UseCreateOrderMutationParams, type UseKlinesQueryParams, type UseMarketDataSubscriptionParams, type UseMarketDataSubscriptionResult, type UseMarketQueryParams, type UseMarketsQueryParams, type UseOpenOrdersScriptParams, type UseOpenOrdersScriptResult, type UseOrderBookQueryParams, type UseOrderBookScriptParams, type UseOrderBookScriptResult, type UseOrdersQueryParams, type UsePlaceOrderFormScriptParams, type UsePlaceOrderFormScriptResult, type UsePositionsQueryParams, type UsePositionsScriptParams, type UsePositionsScriptResult, type UseRecentTradesQueryParams, type UseSearchCoinsScriptParams, type UseSearchCoinsScriptResult, type UseTradeHistoryScriptParams, type UseTradeHistoryScriptResult, type UseTradesQueryParams, type UseTradesScriptParams, type UseTradesScriptResult, type UseUserDataSubscriptionParams, type UseUserDataSubscriptionResult, type UserDataType, cancelOrder, coinsQueryKey, createOrder, fetchCoins, fetchKlines, fetchMarket, fetchMarkets, fetchOrderBook, fetchOrders, fetchPositions, fetchRecentTrades, fetchTrades, klinesQueryKey, marketQueryKey, marketsQueryKey, orderBookQueryKey, ordersQueryKey, positionsQueryKey, recentTradesQueryKey, tradesQueryKey, useCancelOrderMutation, useCandlesSubscription, useCoinInfo, useCoinsQuery, useCreateOrderMutation, useKlinesQuery, useMarketDataSubscription, useMarketQuery, useMarketsQuery, useOpenOrdersScript, useOrderBookQuery, useOrderBookScript, useOrdersQuery, usePerpetualsClient, usePlaceOrderFormScript, usePositionsQuery, usePositionsScript, useRecentTradesQuery, useSearchCoinsScript, useTradeHistoryScript, useTradesQuery, useTradesScript, useUserDataSubscription, _default as version };
2130
+ /**
2131
+ * Highest-level deposit widget. Wires the three presentational
2132
+ * components (form / confirm / status) to the deposit hooks +
2133
+ * state machine.
2134
+ *
2135
+ * Engineering principles:
2136
+ * - Single responsibility: this file is the *only* place that knows
2137
+ * how the three components compose. Anything richer (e.g. embedded
2138
+ * FAQ panel, support links) belongs to the host application.
2139
+ * - Inversion of control: every side effect the host might want to
2140
+ * own (sign + broadcast, success / failure callbacks, explorer
2141
+ * URLs, balance fetch, address validation) is a prop. The widget
2142
+ * never imports a wallet adapter directly.
2143
+ */
2144
+ interface DepositFlowWidgetProps {
2145
+ /** Connected Solana wallet — used as `userSolanaAddress` in /quote. */
2146
+ userSolanaAddress: string;
2147
+ /** Stable LiberFi user id (for fee attribution). */
2148
+ userId: string;
2149
+ /** Where the deposit was initiated from. */
2150
+ source: DepositSource;
2151
+ /** Optional referral / campaign code propagated to the backend. */
2152
+ campaign?: string;
2153
+ /** Initial Hyperliquid recipient (e.g. derived from the user's EVM wallet). */
2154
+ defaultRecipient?: string;
2155
+ /**
2156
+ * Wallet adapter — sign and broadcast a Solana transaction. The host
2157
+ * app supplies its own wallet integration (Phantom, Privy, Backpack,
2158
+ * …) and returns the resulting tx hash. See `SignAndBroadcastSolanaTx`.
2159
+ */
2160
+ signAndBroadcast: SignAndBroadcastSolanaTx;
2161
+ /** Optional balance display (in SOL units, e.g. "12.345"). */
2162
+ balanceSol?: string;
2163
+ /** Click handler for "Max" — only rendered when `balanceSol` is set. */
2164
+ onMaxClick?: () => void;
2165
+ /** Validates the recipient string. Return undefined when valid. */
2166
+ validateRecipient?: (value: string) => string | undefined;
2167
+ /** Build a Solana explorer URL from a tx hash. */
2168
+ buildSolanaExplorerUrl?: (txHash: string) => string;
2169
+ /** Build a Hyperliquid explorer URL from a tx hash. */
2170
+ buildHyperliquidExplorerUrl?: (txHash: string) => string;
2171
+ /** Fired when a deposit reaches `settled`. */
2172
+ onSettled?: (intentId: string) => void;
2173
+ /** Fired when a deposit fails (after the wallet signed). */
2174
+ onError?: (intentId: string | undefined, message: string) => void;
2175
+ className?: string;
2176
+ }
2177
+ declare function DepositFlowWidget({ userSolanaAddress, userId, source, campaign, defaultRecipient, signAndBroadcast, balanceSol, onMaxClick, validateRecipient, buildSolanaExplorerUrl, buildHyperliquidExplorerUrl, onSettled, onError, className, }: DepositFlowWidgetProps): react_jsx_runtime.JSX.Element;
2178
+
2179
+ /**
2180
+ * Pure presentational form for collecting the deposit amount + the
2181
+ * Hyperliquid recipient address.
2182
+ *
2183
+ * No data fetching, no state — every input is controlled from above.
2184
+ * Lets the host app decide when to show the wallet's connected SOL
2185
+ * balance (or omit it entirely).
2186
+ */
2187
+ interface DepositFormUIProps {
2188
+ amount: string;
2189
+ onAmountChange: (value: string) => void;
2190
+ recipient: string;
2191
+ onRecipientChange: (value: string) => void;
2192
+ /** Optional: shown as the "Balance: …" hint above the amount input. */
2193
+ balanceSol?: string;
2194
+ /** Disables every interactive control (e.g. while quoting). */
2195
+ disabled?: boolean;
2196
+ /** Inline error to render under the amount input. */
2197
+ amountError?: string;
2198
+ /** Inline error to render under the recipient input. */
2199
+ recipientError?: string;
2200
+ /** Click handler for "Max" — only rendered when `balanceSol` is set. */
2201
+ onMax?: () => void;
2202
+ className?: string;
2203
+ }
2204
+ declare function DepositFormUI({ amount, onAmountChange, recipient, onRecipientChange, balanceSol, disabled, amountError, recipientError, onMax, className, }: DepositFormUIProps): react_jsx_runtime.JSX.Element;
2205
+
2206
+ /**
2207
+ * Pure presentational confirm modal for the deposit flow.
2208
+ *
2209
+ * Owns no fetching or signing — it just renders the breakdown and
2210
+ * fires `onConfirm` / `onCancel`. The expiry countdown ticks locally
2211
+ * via setInterval and re-renders once a second; when it hits 0 the
2212
+ * `onExpire` callback fires (the parent should refetch the quote).
2213
+ */
2214
+ interface DepositConfirmUIProps {
2215
+ isOpen: boolean;
2216
+ /** Quote currently being shown to the user. Required when `isOpen`. */
2217
+ quote: DepositQuoteResponse | undefined;
2218
+ /** True while `/submit` (or wallet sign) is in flight. Disables the CTA. */
2219
+ isExecuting?: boolean;
2220
+ /** True when the displayed quote has already expired. */
2221
+ isExpired?: boolean;
2222
+ onConfirm: () => void;
2223
+ onCancel: () => void;
2224
+ /** Fires when the local countdown reaches zero. */
2225
+ onExpire?: () => void;
2226
+ /** Optional inline error to surface inside the modal. */
2227
+ error?: string;
2228
+ }
2229
+ declare function DepositConfirmUI({ isOpen, quote, isExecuting, isExpired, onConfirm, onCancel, onExpire, error, }: DepositConfirmUIProps): react_jsx_runtime.JSX.Element;
2230
+
2231
+ /**
2232
+ * Pure presentational status panel.
2233
+ *
2234
+ * Renders one of four visual states:
2235
+ * - in-progress (broadcasting / submitted / tracking)
2236
+ * - succeeded
2237
+ * - refunded
2238
+ * - failed
2239
+ *
2240
+ * Explorer URLs are caller-provided so the SDK never has to know which
2241
+ * RPC / explorer the host wants (Solscan vs Solana Beach, etc.).
2242
+ */
2243
+ interface DepositStatusUIProps {
2244
+ isOpen: boolean;
2245
+ /** The current FSM phase — drives the visual treatment. */
2246
+ phase: DepositPhase;
2247
+ /** Backend status record (may be unavailable on first frame). */
2248
+ status?: DepositStatusResponse;
2249
+ /** Optional Solana explorer URL (caller decides the network). */
2250
+ solanaExplorerUrl?: string;
2251
+ /** Optional Hyperliquid explorer URL. */
2252
+ hyperliquidExplorerUrl?: string;
2253
+ /** "Try again" handler — only rendered when `phase === "failed"`. */
2254
+ onRetry?: () => void;
2255
+ onClose: () => void;
2256
+ /** Optional override for the human-readable message. */
2257
+ errorMessage?: string;
2258
+ }
2259
+ declare function DepositStatusUI({ isOpen, phase, status, solanaExplorerUrl, hyperliquidExplorerUrl, onRetry, onClose, errorMessage, }: DepositStatusUIProps): react_jsx_runtime.JSX.Element;
2260
+
2261
+ /**
2262
+ * Tiny number-formatting helpers shared by the deposit UI.
2263
+ *
2264
+ * We use plain `bigint` arithmetic here — never `Number(...)` on a
2265
+ * lamport / microUSDC value — so we never silently lose precision on
2266
+ * deposits that exceed `Number.MAX_SAFE_INTEGER` lamports.
2267
+ */
2268
+ /**
2269
+ * Convert a lamport amount (string bigint) to a SOL-denominated string
2270
+ * with `precision` decimals and trailing zeros stripped.
2271
+ */
2272
+ declare function lamportsToSol(value: string, precision?: number): string;
2273
+ /** Convert microUSDC (6 decimals) to a USDC display string. */
2274
+ declare function microUsdcToUsdc(value: string | undefined, precision?: number): string;
2275
+ /** Convert a SOL-denominated decimal string to a lamport `string` (bigint). */
2276
+ declare function solToLamports(value: string): string;
2277
+ /** Returns whole-second countdown until `expiresAtMs`. Negative -> 0. */
2278
+ declare function secondsUntil(expiresAtMs: number, nowMs?: number): number;
2279
+ /** Truncate an address to `head…tail` for display. */
2280
+ declare function shortAddress(addr: string, head?: number, tail?: number): string;
2281
+
2282
+ /**
2283
+ * Pure presentational card for the Hyperliquid first-run setup flow.
2284
+ *
2285
+ * The component is fully driven by the FSM state from
2286
+ * `useHyperliquidSetup` plus a couple of action callbacks, so consumers
2287
+ * can wire it into either a modal, a sidebar panel, or an inline card
2288
+ * without forking the markup.
2289
+ */
2290
+ interface HyperliquidInitUIProps {
2291
+ /** FSM snapshot rendered as the checklist. */
2292
+ state: SetupState;
2293
+ /** Trigger the next runnable step (sequential default). */
2294
+ onContinue: () => void;
2295
+ /** Retry a specific step (used by per-row error recovery). */
2296
+ onRetryStep?: (index: number) => void;
2297
+ /** Refresh the on-chain state — typically rendered when the load failed. */
2298
+ onReload?: () => void;
2299
+ /** Optional dismiss handler — show a "Skip for now" CTA when set. */
2300
+ onDismiss?: () => void;
2301
+ /** Optional className override for embedding inside other cards. */
2302
+ className?: string;
2303
+ }
2304
+ declare function HyperliquidInitUI({ state, onContinue, onRetryStep, onReload, onDismiss, className, }: HyperliquidInitUIProps): react_jsx_runtime.JSX.Element;
2305
+
2306
+ /**
2307
+ * Highest-level Hyperliquid setup widget.
2308
+ *
2309
+ * Wraps `useHyperliquidSetup` with the presentational card so consumers
2310
+ * can drop in a single component:
2311
+ *
2312
+ * <HyperliquidInitWidget
2313
+ * adapter={mySetupAdapter}
2314
+ * userAddress={evmAddress}
2315
+ * steps={[ ... ]}
2316
+ * onComplete={() => navigate("/perp")}
2317
+ * onDismiss={() => closeModal()}
2318
+ * />
2319
+ *
2320
+ * The widget is a thin coordinator — all logic lives in the hook and
2321
+ * all presentation lives in `HyperliquidInitUI`. This split keeps the
2322
+ * UI testable in isolation (Storybook just hands it a `state` prop).
2323
+ */
2324
+ interface HyperliquidInitWidgetProps extends Pick<UseHyperliquidSetupOptions, "adapter" | "userAddress" | "steps" | "autoLoad" | "onError"> {
2325
+ /** Invoked once every step is `done` or `skipped`. */
2326
+ onComplete?: (state: SetupState) => void;
2327
+ /**
2328
+ * Optional dismiss callback — when supplied the card renders a
2329
+ * "Skip for now" / "Close" CTA so the user can leave the wizard.
2330
+ */
2331
+ onDismiss?: () => void;
2332
+ /** Optional className passthrough to the rendered card. */
2333
+ className?: string;
2334
+ }
2335
+ declare function HyperliquidInitWidget({ adapter, userAddress, steps, autoLoad, onComplete, onError, onDismiss, className, }: HyperliquidInitWidgetProps): react_jsx_runtime.JSX.Element;
2336
+
2337
+ export { type Account, type ApproveBuilderFeeParams, type CancelOrderParams, type CancelOrderResult, type Coin, CoinInfoNotFoundUI, CoinInfoSkeletonsUI, CoinInfoUI, type CoinInfoUIProps, CoinInfoWidget, type CoinInfoWidgetProps, type DepositBreakdown, DepositConfirmUI, type DepositConfirmUIProps, type DepositErrorInfo, type DepositEvent, DepositFlowWidget, type DepositFlowWidgetProps, DepositFormUI, type DepositFormUIProps, type DepositPhase, type DepositQuoteRequest, type DepositQuoteResponse, type DepositSource, type DepositState, type DepositStatus, type DepositStatusResponse, type DepositStatusTransition, DepositStatusUI, type DepositStatusUIProps, type DepositSubmitRequest, type DepositSubmitResponse, type ExecuteDepositInput, type GetOpenOrdersParams, type GetOpenOrdersResult, type GetPositionsParams, type GetPositionsResult, type GetTradesParams, type GetTradesResult, type HyperliquidAccountState, HyperliquidApiError, type HyperliquidClientConfig, type HyperliquidEnvironment, HyperliquidInitUI, type HyperliquidInitUIProps, HyperliquidInitWidget, type HyperliquidInitWidgetProps, HyperliquidPerpetualsClient, type HyperliquidSetupActionResult, type IHyperliquidSetupAdapter, type IPerpDepositClient, type IPerpetualsClient, type Kline, type KlineInterval, LiberFiApiError, type LiberFiHttpMethod, type RequestOptions as LiberFiHttpRequestOptions, LiberFiHttpTransport, type LiberFiHttpTransportConfig, LiberFiPerpDepositClient, type LiberFiPerpDepositClientConfig, LiberFiPerpetualsClient, type LiberFiPerpetualsClientConfig, type MarketData, type MarketDataType, OpenOrdersEmpty, OpenOrdersSkeleton, OpenOrdersUI, type OpenOrdersUIProps, OpenOrdersWidget, type OpenOrdersWidgetProps, type Order, type OrderBook, type OrderBookLevel, OrderBookUI, type OrderBookUIProps, OrderBookWidget, type OrderBookWidgetProps, type OrderSide, type OrderStatus, type OrderType, PerpetualsContext, type PerpetualsContextValue, PerpetualsProvider, type PerpetualsProviderProps, type PlaceOrderFormData, PlaceOrderFormUI, type PlaceOrderFormUIProps, PlaceOrderFormWidget, type PlaceOrderFormWidgetProps, type PlaceOrderParams, type PlaceOrderResult, type Position, PositionsEmpty, PositionsSkeleton, PositionsUI, type PositionsUIProps, PositionsWidget, type PositionsWidgetProps, type PriceLevel, SearchCoinsUI, type SearchCoinsUIProps, SearchCoinsWidget, type SearchCoinsWidgetProps, type SetReferrerParams, type SetupAction, type SetupPhase, type SetupState, type SetupStep, type SetupStepId, type SignAndBroadcastSolanaTx, type SignTypedDataFn, type StepRecord, type StepStatus, type Symbol, TERMINAL_DEPOSIT_STATUSES, type TimeRange, type Trade, type TradeHistory, TradeHistoryEmpty, TradeHistorySkeleton, TradeHistoryUI, type TradeHistoryUIProps, TradeHistoryWidget, type TradeHistoryWidgetProps, type TradeSide, TradesUI, type TradesUIProps, TradesWidget, type TradesWidgetProps, type TradingProvider, type UpdateLeverageParams, type UseCancelOrderMutationParams, type UseCandlesSubscriptionParams, type UseCandlesSubscriptionResult, type UseCoinInfoReturnType, type UseCreateOrderMutationParams, type UseHyperliquidSetupOptions, type UseHyperliquidSetupResult, type UseKlinesQueryParams, type UseMarketDataSubscriptionParams, type UseMarketDataSubscriptionResult, type UseMarketQueryParams, type UseMarketsQueryParams, type UseOpenOrdersScriptParams, type UseOpenOrdersScriptResult, type UseOrderBookQueryParams, type UseOrderBookScriptParams, type UseOrderBookScriptResult, type UseOrdersQueryParams, type UsePerpDepositExecuteResult, type UsePerpDepositQuoteOptions, type UsePerpDepositStatusOptions, type UsePlaceOrderFormScriptParams, type UsePlaceOrderFormScriptResult, type UsePositionsQueryParams, type UsePositionsScriptParams, type UsePositionsScriptResult, type UseRecentTradesQueryParams, type UseSearchCoinsScriptParams, type UseSearchCoinsScriptResult, type UseTradeHistoryScriptParams, type UseTradeHistoryScriptResult, type UseTradesQueryParams, type UseTradesScriptParams, type UseTradesScriptResult, type UseUserDataSubscriptionParams, type UseUserDataSubscriptionResult, type UserDataType, cancelOrder, classifyStep, coinsQueryKey, createOrder, currentBreakdown as currentDepositBreakdown, currentStatus as currentDepositStatus, fetchCoins, fetchKlines, fetchMarket, fetchMarkets, fetchOrderBook, fetchOrders, fetchPerpDepositQuote, fetchPerpDepositStatus, fetchPositions, fetchRecentTrades, fetchTrades, initialDepositState, initialSetupState, isPolling as isDepositPolling, isTerminal as isDepositTerminal, isTerminalLifecycle as isTerminalDepositLifecycle, klinesQueryKey, lamportsToSol, marketQueryKey, marketsQueryKey, microUsdcToUsdc, nextRunnableStep, orderBookQueryKey, ordersQueryKey, perpDepositQuoteQueryKey, perpDepositStatusQueryKey, positionsQueryKey, recentTradesQueryKey, reduceDepositState, reduceSetupState, secondsUntil, shortAddress, solToLamports, tradesQueryKey, useCancelOrderMutation, useCandlesSubscription, useCoinInfo, useCoinsQuery, useCreateOrderMutation, useHyperliquidSetup, useKlinesQuery, useMarketDataSubscription, useMarketQuery, useMarketsQuery, useOpenOrdersScript, useOrderBookQuery, useOrderBookScript, useOrdersQuery, usePerpDepositClient, usePerpDepositExecute, usePerpDepositQuote, usePerpDepositStatus, usePerpetualsClient, usePlaceOrderFormScript, usePositionsQuery, usePositionsScript, useRecentTradesQuery, useSearchCoinsScript, useTradeHistoryScript, useTradesQuery, useTradesScript, useUserDataSubscription, _default as version };