@abstraxn/signer-react 1.0.2 → 1.0.4

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/CHANGELOG.md CHANGED
@@ -5,6 +5,24 @@ All notable changes to this project will be documented in this file.
5
5
  The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
6
6
  and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
7
 
8
+ ## [1.0.3] - 2026-01-29
9
+
10
+ ### Added
11
+ - `useGetGasPrice` hook to fetch gas price (maxFeePerGas, maxPriorityFeePerGas, gasPrice) from the chain
12
+
13
+ ### Changed
14
+ - `useEstimateGas` now returns only `{ gasLimit }`; use `useGetGasPrice` for fees
15
+ - `useSignTxn` and `useSignAndSendTxn`: parameter renamed from `override` to `gas` with direct fields `gasLimit`, `gasPrice?`, `maxFeePerGas?`, `maxPriorityFeePerGas?`
16
+
17
+ ## [1.0.2] - 2026-01-29
18
+
19
+ ### Added
20
+ - `useGetGasPrice` hook to fetch gas price (maxFeePerGas, maxPriorityFeePerGas, gasPrice) from the chain
21
+
22
+ ### Changed
23
+ - `useEstimateGas` now returns only `{ gasLimit }`; use `useGetGasPrice` for fees
24
+ - `useSignTxn` and `useSignAndSendTxn`: parameter renamed from `override` to `gas` with direct fields `gasLimit`, `gasPrice?`, `maxFeePerGas?`, `maxPriorityFeePerGas?`
25
+
8
26
  ## [1.0.1] - 2026-01-28
9
27
 
10
28
  ### Added
@@ -8392,33 +8392,32 @@ export declare function usePrepareRawTxn(provider: PublicClient): {
8392
8392
  * // Prepare transaction
8393
8393
  * const rawTx = await prepareRawTxn({ from: address!, to: '0x...', value: '0.001' });
8394
8394
  * const { estimateGas } = useEstimateGas(publicClient);
8395
- * const gasEstimate = await estimateGas({ account: address!, to: rawTx.to, data: rawTx.data, value: rawTx.value });
8396
- * // Sign (override required; no estimation in hook)
8395
+ * const { getGasPrice } = useGetGasPrice(publicClient);
8396
+ * const { gasLimit } = await estimateGas({ account: address!, to: rawTx.to, data: rawTx.data, value: rawTx.value });
8397
+ * const fees = await getGasPrice();
8397
8398
  * const signedTx = await signTxn({
8398
8399
  * from: address!,
8399
8400
  * ...rawTx,
8400
- * override: { gasLimit: gasEstimate.gasLimit, maxFeePerGas: gasEstimate.maxFeePerGas!, maxPriorityFeePerGas: gasEstimate.maxPriorityFeePerGas! },
8401
+ * gas: { gasLimit, maxFeePerGas: fees.maxFeePerGas!, maxPriorityFeePerGas: fees.maxPriorityFeePerGas! },
8401
8402
  * });
8402
8403
  * ```
8403
8404
  */
8404
8405
  export declare function useSignTxn(provider: PublicClient): {
8405
- signTxn: ({ from, to, value, data, chainId, override, }: {
8406
+ signTxn: ({ from, to, value, data, chainId, gas, }: {
8406
8407
  from: Address;
8407
8408
  to: Address;
8408
8409
  value: string | bigint;
8409
8410
  data: `0x${string}`;
8410
8411
  chainId?: number;
8411
- /** Gas and fees (user must pass; no estimation in hook). EIP-1559 or legacy. Use useEstimateGas to get values. */
8412
- override: {
8413
- gasLimit: bigint;
8414
- maxFeePerGas: bigint;
8415
- maxPriorityFeePerGas: bigint;
8416
- } | {
8417
- gasLimit: bigint;
8418
- gasPrice: bigint;
8412
+ /** Gas: optionally pass gasLimit + (maxFeePerGas & maxPriorityFeePerGas for EIP-1559) or (gasPrice for legacy). */
8413
+ gas?: {
8414
+ gasLimit?: bigint;
8415
+ gasPrice?: bigint;
8416
+ maxFeePerGas?: bigint;
8417
+ maxPriorityFeePerGas?: bigint;
8419
8418
  };
8420
8419
  }) => Promise<{
8421
- unsignedTransaction: `0x02${string}` | import("viem").TransactionSerializedLegacy;
8420
+ unsignedTransaction: `0x02${string}` | `0x01${string}` | `0x03${string}` | `0x04${string}` | import("viem").TransactionSerializedLegacy;
8422
8421
  signedTransaction: string;
8423
8422
  }>;
8424
8423
  isConnected: boolean;
@@ -8439,35 +8438,34 @@ export declare function useSignTxn(provider: PublicClient): {
8439
8438
  * // Prepare transaction
8440
8439
  * const rawTx = await prepareRawTxn({ from: address!, to: '0x...', value: '0.001' });
8441
8440
  * const { estimateGas } = useEstimateGas(publicClient);
8442
- * const gasEstimate = await estimateGas({ account: address!, to: rawTx.to, data: rawTx.data, value: rawTx.value });
8443
- * // Sign and send (override required; no estimation in hook)
8441
+ * const { getGasPrice } = useGetGasPrice(publicClient);
8442
+ * const { gasLimit } = await estimateGas({ account: address!, to: rawTx.to, data: rawTx.data, value: rawTx.value });
8443
+ * const fees = await getGasPrice();
8444
8444
  * const result = await signAndSendTxn({
8445
8445
  * from: address!,
8446
8446
  * ...rawTx,
8447
- * override: { gasLimit: gasEstimate.gasLimit, maxFeePerGas: gasEstimate.maxFeePerGas!, maxPriorityFeePerGas: gasEstimate.maxPriorityFeePerGas! },
8447
+ * gas: { gasLimit, maxFeePerGas: fees.maxFeePerGas!, maxPriorityFeePerGas: fees.maxPriorityFeePerGas! },
8448
8448
  * });
8449
8449
  * console.log('Transaction hash:', result.hash);
8450
8450
  * ```
8451
8451
  */
8452
8452
  export declare function useSignAndSendTxn(provider: PublicClient): {
8453
- signAndSendTxn: ({ from, to, value, data, chainId, override, }: {
8453
+ signAndSendTxn: ({ from, to, value, data, chainId, gas, }: {
8454
8454
  from: Address;
8455
8455
  to: Address;
8456
8456
  value: string | bigint;
8457
8457
  data: `0x${string}`;
8458
8458
  chainId?: number;
8459
- /** Gas and fees (user must pass; no estimation in hook). EIP-1559 or legacy. Use useEstimateGas to get values. */
8460
- override: {
8461
- gasLimit: bigint;
8462
- maxFeePerGas: bigint;
8463
- maxPriorityFeePerGas: bigint;
8464
- } | {
8465
- gasLimit: bigint;
8466
- gasPrice: bigint;
8459
+ /** Gas: optionally pass gasLimit + (maxFeePerGas & maxPriorityFeePerGas for EIP-1559) or (gasPrice for legacy). */
8460
+ gas?: {
8461
+ gasLimit?: bigint;
8462
+ gasPrice?: bigint;
8463
+ maxFeePerGas?: bigint;
8464
+ maxPriorityFeePerGas?: bigint;
8467
8465
  };
8468
8466
  }) => Promise<{
8469
8467
  hash: `0x${string}`;
8470
- unsignedTransaction: `0x02${string}` | import("viem").TransactionSerializedLegacy;
8468
+ unsignedTransaction: `0x02${string}` | `0x01${string}` | `0x03${string}` | `0x04${string}` | import("viem").TransactionSerializedLegacy;
8471
8469
  signedTransaction: string;
8472
8470
  }>;
8473
8471
  isConnected: boolean;
@@ -8509,7 +8507,7 @@ export declare function useWaitForTxnReceipt(provider: PublicClient): {
8509
8507
  };
8510
8508
  /**
8511
8509
  * Hook to estimate gas for a transaction
8512
- * Returns gasLimit and fees to pass as override to useSignTxn / useSignAndSendTxn (no estimation inside those hooks).
8510
+ * Returns gasLimit to pass as gas.gasLimit to useSignTxn / useSignAndSendTxn (use useGetGasPrice for fees; no estimation inside those hooks).
8513
8511
  *
8514
8512
  * @param provider - PublicClient instance (can be created using usePublicClient hook)
8515
8513
  * @returns Object with estimateGas function
@@ -8523,8 +8521,7 @@ export declare function useWaitForTxnReceipt(provider: PublicClient): {
8523
8521
  * data: rawTx.data,
8524
8522
  * value: rawTx.value,
8525
8523
  * });
8526
- * // EIP-1559: override: { gasLimit: result.gasLimit, maxFeePerGas: result.maxFeePerGas!, maxPriorityFeePerGas: result.maxPriorityFeePerGas! }
8527
- * // Legacy: override: { gasLimit: result.gasLimit, gasPrice: result.gasPrice! }
8524
+ * // gas: { gasLimit: result.gasLimit }
8528
8525
  * ```
8529
8526
  */
8530
8527
  export declare function useEstimateGas(provider: PublicClient): {
@@ -8535,6 +8532,26 @@ export declare function useEstimateGas(provider: PublicClient): {
8535
8532
  value?: string | bigint;
8536
8533
  }) => Promise<{
8537
8534
  gasLimit: bigint;
8535
+ }>;
8536
+ };
8537
+ /**
8538
+ * Hook to get current gas price / EIP-1559 fees from the chain.
8539
+ * Use with useEstimateGas when you need gas limit and gas price for the gas param in useSignTxn / useSignAndSendTxn.
8540
+ *
8541
+ * @param provider - PublicClient instance (can be created using usePublicClient hook)
8542
+ * @returns Object with getGasPrice function returning maxFeePerGas, maxPriorityFeePerGas, and/or gasPrice
8543
+ *
8544
+ * @example
8545
+ * ```tsx
8546
+ * const { publicClient } = usePublicClient(...);
8547
+ * const { getGasPrice } = useGetGasPrice(publicClient);
8548
+ * const fees = await getGasPrice();
8549
+ * // EIP-1559: gas: { gasLimit, maxFeePerGas: fees.maxFeePerGas!, maxPriorityFeePerGas: fees.maxPriorityFeePerGas! }
8550
+ * // Legacy: gas: { gasLimit, gasPrice: fees.gasPrice! }
8551
+ * ```
8552
+ */
8553
+ export declare function useGetGasPrice(provider: PublicClient): {
8554
+ getGasPrice: () => Promise<{
8538
8555
  gasPrice?: bigint;
8539
8556
  maxFeePerGas?: bigint;
8540
8557
  maxPriorityFeePerGas?: bigint;
package/dist/src/hooks.js CHANGED
@@ -581,18 +581,106 @@ export function usePrepareRawTxn(provider) {
581
581
  * // Prepare transaction
582
582
  * const rawTx = await prepareRawTxn({ from: address!, to: '0x...', value: '0.001' });
583
583
  * const { estimateGas } = useEstimateGas(publicClient);
584
- * const gasEstimate = await estimateGas({ account: address!, to: rawTx.to, data: rawTx.data, value: rawTx.value });
585
- * // Sign (override required; no estimation in hook)
584
+ * const { getGasPrice } = useGetGasPrice(publicClient);
585
+ * const { gasLimit } = await estimateGas({ account: address!, to: rawTx.to, data: rawTx.data, value: rawTx.value });
586
+ * const fees = await getGasPrice();
586
587
  * const signedTx = await signTxn({
587
588
  * from: address!,
588
589
  * ...rawTx,
589
- * override: { gasLimit: gasEstimate.gasLimit, maxFeePerGas: gasEstimate.maxFeePerGas!, maxPriorityFeePerGas: gasEstimate.maxPriorityFeePerGas! },
590
+ * gas: { gasLimit, maxFeePerGas: fees.maxFeePerGas!, maxPriorityFeePerGas: fees.maxPriorityFeePerGas! },
590
591
  * });
591
592
  * ```
592
593
  */
594
+ // export function useSignTxn(provider: PublicClient) {
595
+ // const { wallet, isConnected, address, signTransactionViaAPI } = useAbstraxnWallet();
596
+ // const signTxn = useCallback(async ({
597
+ // from,
598
+ // to,
599
+ // value,
600
+ // data,
601
+ // chainId,
602
+ // gas,
603
+ // }: {
604
+ // from: Address;
605
+ // to: Address;
606
+ // value: string | bigint;
607
+ // data: `0x${string}`;
608
+ // chainId?: number;
609
+ // /** Gas: pass gasLimit + (maxFeePerGas & maxPriorityFeePerGas for EIP-1559) or (gasPrice for legacy). Use useEstimateGas and useGetGasPrice. */
610
+ // gas: {
611
+ // gasLimit: bigint;
612
+ // gasPrice?: bigint;
613
+ // maxFeePerGas?: bigint;
614
+ // maxPriorityFeePerGas?: bigint;
615
+ // };
616
+ // }) => {
617
+ // if (!isConnected || !wallet) {
618
+ // throw new Error('Wallet is not connected');
619
+ // }
620
+ // if (!provider) {
621
+ // throw new Error('Provider (publicClient) is required');
622
+ // }
623
+ // if (!from) {
624
+ // throw new Error('From address is required');
625
+ // }
626
+ // if (!to) {
627
+ // throw new Error('To address is required');
628
+ // }
629
+ // if (gas.gasLimit === undefined) {
630
+ // throw new Error('gas.gasLimit is required. Use useEstimateGas to get values.');
631
+ // }
632
+ // const isLegacy = gas.gasPrice !== undefined;
633
+ // if (!isLegacy) {
634
+ // if (gas.maxFeePerGas === undefined || gas.maxPriorityFeePerGas === undefined) {
635
+ // throw new Error('gas.maxFeePerGas and gas.maxPriorityFeePerGas are required for EIP-1559, or pass gas.gasPrice for legacy.');
636
+ // }
637
+ // }
638
+ // // Get chain ID from provider or use provided one
639
+ // const targetChainId = chainId || provider.chain?.id;
640
+ // if (!targetChainId) {
641
+ // throw new Error('Chain ID is required. Either provide it or ensure provider has a chain configured.');
642
+ // }
643
+ // // Get nonce
644
+ // const nonce = await provider.getTransactionCount({ address: from });
645
+ // // Value in wei (pass-through from prepareRawTxn, no hex conversion)
646
+ // const valueInWei = typeof value === 'bigint' ? value : BigInt(value === '0x' || value === '' ? '0' : value);
647
+ // // Build unsigned tx from user gas (no estimation in hook)
648
+ // const unsignedTx = isLegacy
649
+ // ? {
650
+ // chainId: targetChainId,
651
+ // from,
652
+ // to,
653
+ // data,
654
+ // value: valueInWei,
655
+ // nonce,
656
+ // gas: gas.gasLimit,
657
+ // gasPrice: gas.gasPrice,
658
+ // }
659
+ // : {
660
+ // chainId: targetChainId,
661
+ // from,
662
+ // to,
663
+ // data,
664
+ // value: valueInWei,
665
+ // nonce,
666
+ // gas: gas.gasLimit,
667
+ // maxFeePerGas: gas.maxFeePerGas!,
668
+ // maxPriorityFeePerGas: gas.maxPriorityFeePerGas!,
669
+ // };
670
+ // // Serialize transaction
671
+ // const serializedTx = serializeTransaction(unsignedTx);
672
+ // // Sign transaction via Turnkey API
673
+ // const signResult = await signTransactionViaAPI(serializedTx, from);
674
+ // return {
675
+ // unsignedTransaction: serializedTx,
676
+ // signedTransaction: signResult.signedTransaction,
677
+ // };
678
+ // }, [provider, isConnected, wallet, address, signTransactionViaAPI]);
679
+ // return { signTxn, isConnected, address };
680
+ // }
593
681
  export function useSignTxn(provider) {
594
682
  const { wallet, isConnected, address, signTransactionViaAPI } = useAbstraxnWallet();
595
- const signTxn = useCallback(async ({ from, to, value, data, chainId, override, }) => {
683
+ const signTxn = useCallback(async ({ from, to, value, data, chainId, gas, }) => {
596
684
  if (!isConnected || !wallet) {
597
685
  throw new Error('Wallet is not connected');
598
686
  }
@@ -605,16 +693,6 @@ export function useSignTxn(provider) {
605
693
  if (!to) {
606
694
  throw new Error('To address is required');
607
695
  }
608
- if (override.gasLimit === undefined) {
609
- throw new Error('override.gasLimit is required. Use useEstimateGas to get values.');
610
- }
611
- const isLegacy = 'gasPrice' in override && override.gasPrice !== undefined;
612
- if (!isLegacy) {
613
- const o = override;
614
- if (o.maxFeePerGas === undefined || o.maxPriorityFeePerGas === undefined) {
615
- throw new Error('override.maxFeePerGas and maxPriorityFeePerGas are required for EIP-1559, or pass gasPrice for legacy.');
616
- }
617
- }
618
696
  // Get chain ID from provider or use provided one
619
697
  const targetChainId = chainId || provider.chain?.id;
620
698
  if (!targetChainId) {
@@ -624,32 +702,29 @@ export function useSignTxn(provider) {
624
702
  const nonce = await provider.getTransactionCount({ address: from });
625
703
  // Value in wei (pass-through from prepareRawTxn, no hex conversion)
626
704
  const valueInWei = typeof value === 'bigint' ? value : BigInt(value === '0x' || value === '' ? '0' : value);
627
- // Build unsigned tx from user override only (no estimateGas/estimateFeesPerGas)
628
- const unsignedTx = isLegacy
629
- ? {
630
- chainId: targetChainId,
631
- from,
632
- to,
633
- data,
634
- value: valueInWei,
635
- nonce,
636
- gas: override.gasLimit,
637
- gasPrice: override.gasPrice,
638
- }
639
- : (() => {
640
- const o = override;
641
- return {
642
- chainId: targetChainId,
643
- from,
644
- to,
645
- data,
646
- value: valueInWei,
647
- nonce,
648
- gas: o.gasLimit,
649
- maxFeePerGas: o.maxFeePerGas,
650
- maxPriorityFeePerGas: o.maxPriorityFeePerGas,
651
- };
652
- })();
705
+ // Build base transaction object
706
+ const baseTx = {
707
+ chainId: targetChainId,
708
+ from,
709
+ to,
710
+ data,
711
+ value: valueInWei,
712
+ nonce,
713
+ };
714
+ // Add gas properties if they exist
715
+ const unsignedTx = { ...baseTx };
716
+ if (gas?.gasLimit !== undefined) {
717
+ unsignedTx.gas = gas.gasLimit;
718
+ }
719
+ if (gas?.gasPrice !== undefined) {
720
+ unsignedTx.gasPrice = gas.gasPrice;
721
+ }
722
+ if (gas?.maxFeePerGas !== undefined) {
723
+ unsignedTx.maxFeePerGas = gas.maxFeePerGas;
724
+ }
725
+ if (gas?.maxPriorityFeePerGas !== undefined) {
726
+ unsignedTx.maxPriorityFeePerGas = gas.maxPriorityFeePerGas;
727
+ }
653
728
  // Serialize transaction
654
729
  const serializedTx = serializeTransaction(unsignedTx);
655
730
  // Sign transaction via Turnkey API
@@ -676,19 +751,112 @@ export function useSignTxn(provider) {
676
751
  * // Prepare transaction
677
752
  * const rawTx = await prepareRawTxn({ from: address!, to: '0x...', value: '0.001' });
678
753
  * const { estimateGas } = useEstimateGas(publicClient);
679
- * const gasEstimate = await estimateGas({ account: address!, to: rawTx.to, data: rawTx.data, value: rawTx.value });
680
- * // Sign and send (override required; no estimation in hook)
754
+ * const { getGasPrice } = useGetGasPrice(publicClient);
755
+ * const { gasLimit } = await estimateGas({ account: address!, to: rawTx.to, data: rawTx.data, value: rawTx.value });
756
+ * const fees = await getGasPrice();
681
757
  * const result = await signAndSendTxn({
682
758
  * from: address!,
683
759
  * ...rawTx,
684
- * override: { gasLimit: gasEstimate.gasLimit, maxFeePerGas: gasEstimate.maxFeePerGas!, maxPriorityFeePerGas: gasEstimate.maxPriorityFeePerGas! },
760
+ * gas: { gasLimit, maxFeePerGas: fees.maxFeePerGas!, maxPriorityFeePerGas: fees.maxPriorityFeePerGas! },
685
761
  * });
686
762
  * console.log('Transaction hash:', result.hash);
687
763
  * ```
688
764
  */
765
+ // export function useSignAndSendTxn(provider: PublicClient) {
766
+ // const { wallet, isConnected, address, signTransactionViaAPI } = useAbstraxnWallet();
767
+ // const signAndSendTxn = useCallback(async ({
768
+ // from,
769
+ // to,
770
+ // value,
771
+ // data,
772
+ // chainId,
773
+ // gas,
774
+ // }: {
775
+ // from: Address;
776
+ // to: Address;
777
+ // value: string | bigint;
778
+ // data: `0x${string}`;
779
+ // chainId?: number;
780
+ // /** Gas: pass gasLimit + (maxFeePerGas & maxPriorityFeePerGas for EIP-1559) or (gasPrice for legacy). Use useEstimateGas and useGetGasPrice. */
781
+ // gas: {
782
+ // gasLimit: bigint;
783
+ // gasPrice?: bigint;
784
+ // maxFeePerGas?: bigint;
785
+ // maxPriorityFeePerGas?: bigint;
786
+ // };
787
+ // }) => {
788
+ // if (!isConnected || !wallet) {
789
+ // throw new Error('Wallet is not connected');
790
+ // }
791
+ // if (!provider) {
792
+ // throw new Error('Provider (publicClient) is required');
793
+ // }
794
+ // if (!from) {
795
+ // throw new Error('From address is required');
796
+ // }
797
+ // if (!to) {
798
+ // throw new Error('To address is required');
799
+ // }
800
+ // if (gas.gasLimit === undefined) {
801
+ // throw new Error('gas.gasLimit is required. Use useEstimateGas to get values.');
802
+ // }
803
+ // const isLegacy = gas.gasPrice !== undefined;
804
+ // if (!isLegacy) {
805
+ // if (gas.maxFeePerGas === undefined || gas.maxPriorityFeePerGas === undefined) {
806
+ // throw new Error('gas.maxFeePerGas and gas.maxPriorityFeePerGas are required for EIP-1559, or pass gas.gasPrice for legacy.');
807
+ // }
808
+ // }
809
+ // // Get chain ID from provider or use provided one
810
+ // const targetChainId = chainId || provider.chain?.id;
811
+ // if (!targetChainId) {
812
+ // throw new Error('Chain ID is required. Either provide it or ensure provider has a chain configured.');
813
+ // }
814
+ // // Get nonce
815
+ // const nonce = await provider.getTransactionCount({ address: from });
816
+ // // Value in wei (pass-through from prepareRawTxn, no hex conversion)
817
+ // const valueInWei = typeof value === 'bigint' ? value : BigInt(value === '0x' || value === '' ? '0' : value);
818
+ // // Build unsigned tx from user gas (no estimation in hook)
819
+ // const unsignedTx = isLegacy
820
+ // ? {
821
+ // chainId: targetChainId,
822
+ // from,
823
+ // to,
824
+ // data,
825
+ // value: valueInWei,
826
+ // nonce,
827
+ // gas: gas.gasLimit,
828
+ // gasPrice: gas.gasPrice,
829
+ // }
830
+ // : {
831
+ // chainId: targetChainId,
832
+ // from,
833
+ // to,
834
+ // data,
835
+ // value: valueInWei,
836
+ // nonce,
837
+ // gas: gas.gasLimit,
838
+ // maxFeePerGas: gas.maxFeePerGas!,
839
+ // maxPriorityFeePerGas: gas.maxPriorityFeePerGas!,
840
+ // };
841
+ // // Serialize transaction
842
+ // const serializedTx = serializeTransaction(unsignedTx);
843
+ // // Sign transaction via Turnkey API
844
+ // const signResult = await signTransactionViaAPI(serializedTx, from);
845
+ // // Send the signed transaction
846
+ // const hash = await provider.sendRawTransaction({
847
+ // serializedTransaction: signResult.signedTransaction as `0x${string}`,
848
+ // });
849
+ // return {
850
+ // hash,
851
+ // unsignedTransaction: serializedTx,
852
+ // signedTransaction: signResult.signedTransaction,
853
+ // };
854
+ // }, [provider, isConnected, wallet, address, signTransactionViaAPI]);
855
+ // return { signAndSendTxn, isConnected, address };
856
+ // }
689
857
  export function useSignAndSendTxn(provider) {
690
858
  const { wallet, isConnected, address, signTransactionViaAPI } = useAbstraxnWallet();
691
- const signAndSendTxn = useCallback(async ({ from, to, value, data, chainId, override, }) => {
859
+ const signAndSendTxn = useCallback(async ({ from, to, value, data, chainId, gas, }) => {
692
860
  if (!isConnected || !wallet) {
693
861
  throw new Error('Wallet is not connected');
694
862
  }
@@ -701,16 +869,6 @@ export function useSignAndSendTxn(provider) {
701
869
  if (!to) {
702
870
  throw new Error('To address is required');
703
871
  }
704
- if (override.gasLimit === undefined) {
705
- throw new Error('override.gasLimit is required. Use useEstimateGas to get values.');
706
- }
707
- const isLegacy = 'gasPrice' in override && override.gasPrice !== undefined;
708
- if (!isLegacy) {
709
- const o = override;
710
- if (o.maxFeePerGas === undefined || o.maxPriorityFeePerGas === undefined) {
711
- throw new Error('override.maxFeePerGas and maxPriorityFeePerGas are required for EIP-1559, or pass gasPrice for legacy.');
712
- }
713
- }
714
872
  // Get chain ID from provider or use provided one
715
873
  const targetChainId = chainId || provider.chain?.id;
716
874
  if (!targetChainId) {
@@ -720,32 +878,29 @@ export function useSignAndSendTxn(provider) {
720
878
  const nonce = await provider.getTransactionCount({ address: from });
721
879
  // Value in wei (pass-through from prepareRawTxn, no hex conversion)
722
880
  const valueInWei = typeof value === 'bigint' ? value : BigInt(value === '0x' || value === '' ? '0' : value);
723
- // Build unsigned tx from user override only (no estimateGas/estimateFeesPerGas)
724
- const unsignedTx = isLegacy
725
- ? {
726
- chainId: targetChainId,
727
- from,
728
- to,
729
- data,
730
- value: valueInWei,
731
- nonce,
732
- gas: override.gasLimit,
733
- gasPrice: override.gasPrice,
734
- }
735
- : (() => {
736
- const o = override;
737
- return {
738
- chainId: targetChainId,
739
- from,
740
- to,
741
- data,
742
- value: valueInWei,
743
- nonce,
744
- gas: o.gasLimit,
745
- maxFeePerGas: o.maxFeePerGas,
746
- maxPriorityFeePerGas: o.maxPriorityFeePerGas,
747
- };
748
- })();
881
+ // Build base transaction object
882
+ const baseTx = {
883
+ chainId: targetChainId,
884
+ from,
885
+ to,
886
+ data,
887
+ value: valueInWei,
888
+ nonce,
889
+ };
890
+ // Add gas properties if they exist
891
+ const unsignedTx = { ...baseTx };
892
+ if (gas?.gasLimit !== undefined) {
893
+ unsignedTx.gas = gas.gasLimit;
894
+ }
895
+ if (gas?.gasPrice !== undefined) {
896
+ unsignedTx.gasPrice = gas.gasPrice;
897
+ }
898
+ if (gas?.maxFeePerGas !== undefined) {
899
+ unsignedTx.maxFeePerGas = gas.maxFeePerGas;
900
+ }
901
+ if (gas?.maxPriorityFeePerGas !== undefined) {
902
+ unsignedTx.maxPriorityFeePerGas = gas.maxPriorityFeePerGas;
903
+ }
749
904
  // Serialize transaction
750
905
  const serializedTx = serializeTransaction(unsignedTx);
751
906
  // Sign transaction via Turnkey API
@@ -817,7 +972,7 @@ export function useWaitForTxnReceipt(provider) {
817
972
  }
818
973
  /**
819
974
  * Hook to estimate gas for a transaction
820
- * Returns gasLimit and fees to pass as override to useSignTxn / useSignAndSendTxn (no estimation inside those hooks).
975
+ * Returns gasLimit to pass as gas.gasLimit to useSignTxn / useSignAndSendTxn (use useGetGasPrice for fees; no estimation inside those hooks).
821
976
  *
822
977
  * @param provider - PublicClient instance (can be created using usePublicClient hook)
823
978
  * @returns Object with estimateGas function
@@ -831,8 +986,7 @@ export function useWaitForTxnReceipt(provider) {
831
986
  * data: rawTx.data,
832
987
  * value: rawTx.value,
833
988
  * });
834
- * // EIP-1559: override: { gasLimit: result.gasLimit, maxFeePerGas: result.maxFeePerGas!, maxPriorityFeePerGas: result.maxPriorityFeePerGas! }
835
- * // Legacy: override: { gasLimit: result.gasLimit, gasPrice: result.gasPrice! }
989
+ * // gas: { gasLimit: result.gasLimit }
836
990
  * ```
837
991
  */
838
992
  export function useEstimateGas(provider) {
@@ -853,26 +1007,49 @@ export function useEstimateGas(provider) {
853
1007
  data: data ?? '0x',
854
1008
  value: valueInWei,
855
1009
  });
1010
+ return { gasLimit };
1011
+ }, [provider]);
1012
+ return { estimateGas };
1013
+ }
1014
+ /**
1015
+ * Hook to get current gas price / EIP-1559 fees from the chain.
1016
+ * Use with useEstimateGas when you need gas limit and gas price for the gas param in useSignTxn / useSignAndSendTxn.
1017
+ *
1018
+ * @param provider - PublicClient instance (can be created using usePublicClient hook)
1019
+ * @returns Object with getGasPrice function returning maxFeePerGas, maxPriorityFeePerGas, and/or gasPrice
1020
+ *
1021
+ * @example
1022
+ * ```tsx
1023
+ * const { publicClient } = usePublicClient(...);
1024
+ * const { getGasPrice } = useGetGasPrice(publicClient);
1025
+ * const fees = await getGasPrice();
1026
+ * // EIP-1559: gas: { gasLimit, maxFeePerGas: fees.maxFeePerGas!, maxPriorityFeePerGas: fees.maxPriorityFeePerGas! }
1027
+ * // Legacy: gas: { gasLimit, gasPrice: fees.gasPrice! }
1028
+ * ```
1029
+ */
1030
+ export function useGetGasPrice(provider) {
1031
+ const getGasPrice = useCallback(async () => {
1032
+ if (!provider) {
1033
+ throw new Error('Provider (publicClient) is required');
1034
+ }
1035
+ const result = {};
856
1036
  try {
857
1037
  const fees = await provider.estimateFeesPerGas();
858
- return {
859
- gasLimit,
860
- maxFeePerGas: fees.maxFeePerGas,
861
- maxPriorityFeePerGas: fees.maxPriorityFeePerGas,
862
- gasPrice: fees.gasPrice,
863
- };
1038
+ result.maxFeePerGas = fees.maxFeePerGas;
864
1039
  }
865
- catch (error) {
866
- try {
867
- const gasPrice = await provider.getGasPrice();
868
- return { gasLimit, gasPrice };
869
- }
870
- catch (legacyError) {
871
- return { gasLimit };
872
- }
1040
+ catch {
1041
+ // EIP-1559 not supported, will try legacy below
1042
+ }
1043
+ try {
1044
+ result.gasPrice = await provider.getGasPrice();
1045
+ result.maxPriorityFeePerGas = await provider.estimateMaxPriorityFeePerGas();
873
1046
  }
1047
+ catch {
1048
+ // Optional: gasPrice not available
1049
+ }
1050
+ return result;
874
1051
  }, [provider]);
875
- return { estimateGas };
1052
+ return { getGasPrice };
876
1053
  }
877
1054
  /**
878
1055
  * Hook to read from contract