@andrewkimjoseph/celina-sdk 0.9.7 → 0.9.9
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/build/analytics/mcp-tool-events.js +2 -0
- package/build/analytics/mcp-tool-events.js.map +1 -1
- package/build/index.d.ts +1 -1
- package/build/services/gooddollar.service.d.ts +16 -2
- package/build/services/gooddollar.service.js +54 -31
- package/build/services/gooddollar.service.js.map +1 -1
- package/build/src/a2a/agent-card.d.ts +37 -0
- package/build/src/a2a/agent-card.js +46 -0
- package/build/src/a2a/agent-card.js.map +1 -0
- package/build/src/a2a/index.d.ts +2 -0
- package/build/src/a2a/index.js +3 -0
- package/build/src/a2a/index.js.map +1 -0
- package/build/src/a2a/skills.d.ts +18 -0
- package/build/src/a2a/skills.js +101 -0
- package/build/src/a2a/skills.js.map +1 -0
- package/build/src/abis/aave-pool.d.ts +37 -0
- package/build/src/abis/aave-pool.js +26 -0
- package/build/src/abis/aave-pool.js.map +1 -0
- package/build/src/abis/accounts.d.ts +13 -0
- package/build/src/abis/accounts.js +10 -0
- package/build/src/abis/accounts.js.map +1 -0
- package/build/src/abis/election.d.ts +124 -0
- package/build/src/abis/election.js +88 -0
- package/build/src/abis/election.js.map +1 -0
- package/build/src/abis/gooddollar-broker.d.ts +77 -0
- package/build/src/abis/gooddollar-broker.js +44 -0
- package/build/src/abis/gooddollar-broker.js.map +1 -0
- package/build/src/abis/gooddollar-identity.d.ts +85 -0
- package/build/src/abis/gooddollar-identity.js +52 -0
- package/build/src/abis/gooddollar-identity.js.map +1 -0
- package/build/src/abis/governance.d.ts +86 -0
- package/build/src/abis/governance.js +68 -0
- package/build/src/abis/governance.js.map +1 -0
- package/build/src/abis/locked-gold.d.ts +10 -0
- package/build/src/abis/locked-gold.js +10 -0
- package/build/src/abis/locked-gold.js.map +1 -0
- package/build/src/abis/nft.d.ts +107 -0
- package/build/src/abis/nft.js +75 -0
- package/build/src/abis/nft.js.map +1 -0
- package/build/src/abis/permit2.d.ts +43 -0
- package/build/src/abis/permit2.js +30 -0
- package/build/src/abis/permit2.js.map +1 -0
- package/build/src/abis/self-registry.d.ts +194 -0
- package/build/src/abis/self-registry.js +120 -0
- package/build/src/abis/self-registry.js.map +1 -0
- package/build/src/abis/ubi-scheme.d.ts +91 -0
- package/build/src/abis/ubi-scheme.js +66 -0
- package/build/src/abis/ubi-scheme.js.map +1 -0
- package/build/src/abis/uniswap-state-view.d.ts +34 -0
- package/build/src/abis/uniswap-state-view.js +22 -0
- package/build/src/abis/uniswap-state-view.js.map +1 -0
- package/build/src/abis/uniswap-v4-quoter.d.ts +86 -0
- package/build/src/abis/uniswap-v4-quoter.js +64 -0
- package/build/src/abis/uniswap-v4-quoter.js.map +1 -0
- package/build/src/abis/universal-router.d.ts +16 -0
- package/build/src/abis/universal-router.js +14 -0
- package/build/src/abis/universal-router.js.map +1 -0
- package/build/src/abis/validators-minimal.d.ts +65 -0
- package/build/src/abis/validators-minimal.js +39 -0
- package/build/src/abis/validators-minimal.js.map +1 -0
- package/build/src/analytics/amplitude.d.ts +11 -0
- package/build/src/analytics/amplitude.js +76 -0
- package/build/src/analytics/amplitude.js.map +1 -0
- package/build/src/analytics/config.d.ts +7 -0
- package/build/src/analytics/config.js +28 -0
- package/build/src/analytics/config.js.map +1 -0
- package/build/src/analytics/consumer-package.d.ts +9 -0
- package/build/src/analytics/consumer-package.js +143 -0
- package/build/src/analytics/consumer-package.js.map +1 -0
- package/build/src/analytics/mcp-tool-events.d.ts +5 -0
- package/build/src/analytics/mcp-tool-events.js +53 -0
- package/build/src/analytics/mcp-tool-events.js.map +1 -0
- package/build/src/analytics/wallet-context.d.ts +11 -0
- package/build/src/analytics/wallet-context.js +81 -0
- package/build/src/analytics/wallet-context.js.map +1 -0
- package/build/src/analytics/wallet-extract.d.ts +9 -0
- package/build/src/analytics/wallet-extract.js +21 -0
- package/build/src/analytics/wallet-extract.js.map +1 -0
- package/build/src/analytics/wrap-service.d.ts +5 -0
- package/build/src/analytics/wrap-service.js +38 -0
- package/build/src/analytics/wrap-service.js.map +1 -0
- package/build/src/clients/celo-client.d.ts +17 -0
- package/build/src/clients/celo-client.js +28 -0
- package/build/src/clients/celo-client.js.map +1 -0
- package/build/src/clients/ens-client.d.ts +17 -0
- package/build/src/clients/ens-client.js +30 -0
- package/build/src/clients/ens-client.js.map +1 -0
- package/build/src/clients/mento-sdk.d.ts +2 -0
- package/build/src/clients/mento-sdk.js +9 -0
- package/build/src/clients/mento-sdk.js.map +1 -0
- package/build/src/clients/self-api.d.ts +82 -0
- package/build/src/clients/self-api.js +242 -0
- package/build/src/clients/self-api.js.map +1 -0
- package/build/src/clients/uniswap-sdk.d.ts +4 -0
- package/build/src/clients/uniswap-sdk.js +13 -0
- package/build/src/clients/uniswap-sdk.js.map +1 -0
- package/build/src/config/aave.d.ts +17 -0
- package/build/src/config/aave.js +77 -0
- package/build/src/config/aave.js.map +1 -0
- package/build/src/config/celina-tag.d.ts +4 -0
- package/build/src/config/celina-tag.js +13 -0
- package/build/src/config/celina-tag.js.map +1 -0
- package/build/src/config/celo-core-contracts.d.ts +8 -0
- package/build/src/config/celo-core-contracts.js +9 -0
- package/build/src/config/celo-core-contracts.js.map +1 -0
- package/build/src/config/chains.d.ts +937 -0
- package/build/src/config/chains.js +319 -0
- package/build/src/config/chains.js.map +1 -0
- package/build/src/config/gooddollar.d.ts +16 -0
- package/build/src/config/gooddollar.js +24 -0
- package/build/src/config/gooddollar.js.map +1 -0
- package/build/src/config/sdk-config.d.ts +33 -0
- package/build/src/config/sdk-config.js +31 -0
- package/build/src/config/sdk-config.js.map +1 -0
- package/build/src/config/self.d.ts +22 -0
- package/build/src/config/self.js +27 -0
- package/build/src/config/self.js.map +1 -0
- package/build/src/config/uniswap.d.ts +42 -0
- package/build/src/config/uniswap.js +76 -0
- package/build/src/config/uniswap.js.map +1 -0
- package/build/src/index.d.ts +90 -0
- package/build/src/index.js +65 -0
- package/build/src/index.js.map +1 -0
- package/build/src/oasf/index.d.ts +2 -0
- package/build/src/oasf/index.js +3 -0
- package/build/src/oasf/index.js.map +1 -0
- package/build/src/oasf/record.d.ts +39 -0
- package/build/src/oasf/record.js +35 -0
- package/build/src/oasf/record.js.map +1 -0
- package/build/src/oasf/taxonomy.d.ts +19 -0
- package/build/src/oasf/taxonomy.js +46 -0
- package/build/src/oasf/taxonomy.js.map +1 -0
- package/build/src/services/aave.service.d.ts +58 -0
- package/build/src/services/aave.service.js +210 -0
- package/build/src/services/aave.service.js.map +1 -0
- package/build/src/services/account.service.d.ts +22 -0
- package/build/src/services/account.service.js +29 -0
- package/build/src/services/account.service.js.map +1 -0
- package/build/src/services/blockchain.service.d.ts +107 -0
- package/build/src/services/blockchain.service.js +151 -0
- package/build/src/services/blockchain.service.js.map +1 -0
- package/build/src/services/contract.service.d.ts +78 -0
- package/build/src/services/contract.service.js +117 -0
- package/build/src/services/contract.service.js.map +1 -0
- package/build/src/services/ens.service.d.ts +44 -0
- package/build/src/services/ens.service.js +92 -0
- package/build/src/services/ens.service.js.map +1 -0
- package/build/src/services/gooddollar.service.d.ts +183 -0
- package/build/src/services/gooddollar.service.js +675 -0
- package/build/src/services/gooddollar.service.js.map +1 -0
- package/build/src/services/governance.service.d.ts +96 -0
- package/build/src/services/governance.service.js +255 -0
- package/build/src/services/governance.service.js.map +1 -0
- package/build/src/services/mento-fx.service.d.ts +80 -0
- package/build/src/services/mento-fx.service.js +319 -0
- package/build/src/services/mento-fx.service.js.map +1 -0
- package/build/src/services/nft.service.d.ts +58 -0
- package/build/src/services/nft.service.js +222 -0
- package/build/src/services/nft.service.js.map +1 -0
- package/build/src/services/self-session-store.d.ts +19 -0
- package/build/src/services/self-session-store.js +28 -0
- package/build/src/services/self-session-store.js.map +1 -0
- package/build/src/services/self.service.d.ts +241 -0
- package/build/src/services/self.service.js +699 -0
- package/build/src/services/self.service.js.map +1 -0
- package/build/src/services/staking.service.d.ts +140 -0
- package/build/src/services/staking.service.js +444 -0
- package/build/src/services/staking.service.js.map +1 -0
- package/build/src/services/token.service.d.ts +110 -0
- package/build/src/services/token.service.js +189 -0
- package/build/src/services/token.service.js.map +1 -0
- package/build/src/services/transaction.service.d.ts +68 -0
- package/build/src/services/transaction.service.js +198 -0
- package/build/src/services/transaction.service.js.map +1 -0
- package/build/src/services/uniswap-path-router.d.ts +40 -0
- package/build/src/services/uniswap-path-router.js +168 -0
- package/build/src/services/uniswap-path-router.js.map +1 -0
- package/build/src/services/uniswap-pool-discovery.d.ts +55 -0
- package/build/src/services/uniswap-pool-discovery.js +198 -0
- package/build/src/services/uniswap-pool-discovery.js.map +1 -0
- package/build/src/services/uniswap.service.d.ts +82 -0
- package/build/src/services/uniswap.service.js +352 -0
- package/build/src/services/uniswap.service.js.map +1 -0
- package/build/src/simulation/index.d.ts +5 -0
- package/build/src/simulation/index.js +2 -0
- package/build/src/simulation/index.js.map +1 -0
- package/build/src/simulation/simulate-prepared-step.d.ts +17 -0
- package/build/src/simulation/simulate-prepared-step.js +42 -0
- package/build/src/simulation/simulate-prepared-step.js.map +1 -0
- package/build/src/tools/catalog.d.ts +11 -0
- package/build/src/tools/catalog.js +43 -0
- package/build/src/tools/catalog.js.map +1 -0
- package/build/src/tools/domains/aave.d.ts +2 -0
- package/build/src/tools/domains/aave.js +115 -0
- package/build/src/tools/domains/aave.js.map +1 -0
- package/build/src/tools/domains/blockchain.d.ts +2 -0
- package/build/src/tools/domains/blockchain.js +86 -0
- package/build/src/tools/domains/blockchain.js.map +1 -0
- package/build/src/tools/domains/browser.d.ts +2 -0
- package/build/src/tools/domains/browser.js +45 -0
- package/build/src/tools/domains/browser.js.map +1 -0
- package/build/src/tools/domains/contract.d.ts +2 -0
- package/build/src/tools/domains/contract.js +67 -0
- package/build/src/tools/domains/contract.js.map +1 -0
- package/build/src/tools/domains/ens.d.ts +2 -0
- package/build/src/tools/domains/ens.js +16 -0
- package/build/src/tools/domains/ens.js.map +1 -0
- package/build/src/tools/domains/gooddollar.d.ts +2 -0
- package/build/src/tools/domains/gooddollar.js +171 -0
- package/build/src/tools/domains/gooddollar.js.map +1 -0
- package/build/src/tools/domains/governance.d.ts +2 -0
- package/build/src/tools/domains/governance.js +41 -0
- package/build/src/tools/domains/governance.js.map +1 -0
- package/build/src/tools/domains/index.d.ts +1 -0
- package/build/src/tools/domains/index.js +31 -0
- package/build/src/tools/domains/index.js.map +1 -0
- package/build/src/tools/domains/mento-fx.d.ts +2 -0
- package/build/src/tools/domains/mento-fx.js +67 -0
- package/build/src/tools/domains/mento-fx.js.map +1 -0
- package/build/src/tools/domains/nft.d.ts +2 -0
- package/build/src/tools/domains/nft.js +38 -0
- package/build/src/tools/domains/nft.js.map +1 -0
- package/build/src/tools/domains/self.d.ts +2 -0
- package/build/src/tools/domains/self.js +187 -0
- package/build/src/tools/domains/self.js.map +1 -0
- package/build/src/tools/domains/staking.d.ts +2 -0
- package/build/src/tools/domains/staking.js +74 -0
- package/build/src/tools/domains/staking.js.map +1 -0
- package/build/src/tools/domains/token.d.ts +2 -0
- package/build/src/tools/domains/token.js +74 -0
- package/build/src/tools/domains/token.js.map +1 -0
- package/build/src/tools/domains/transaction.d.ts +2 -0
- package/build/src/tools/domains/transaction.js +120 -0
- package/build/src/tools/domains/transaction.js.map +1 -0
- package/build/src/tools/domains/uniswap.d.ts +2 -0
- package/build/src/tools/domains/uniswap.js +67 -0
- package/build/src/tools/domains/uniswap.js.map +1 -0
- package/build/src/tools/filter.d.ts +2 -0
- package/build/src/tools/filter.js +50 -0
- package/build/src/tools/filter.js.map +1 -0
- package/build/src/tools/index.d.ts +7 -0
- package/build/src/tools/index.js +7 -0
- package/build/src/tools/index.js.map +1 -0
- package/build/src/tools/schemas/common.d.ts +165 -0
- package/build/src/tools/schemas/common.js +207 -0
- package/build/src/tools/schemas/common.js.map +1 -0
- package/build/src/tools/schemas/wallet-params.d.ts +9 -0
- package/build/src/tools/schemas/wallet-params.js +52 -0
- package/build/src/tools/schemas/wallet-params.js.map +1 -0
- package/build/src/tools/swap-routing.d.ts +25 -0
- package/build/src/tools/swap-routing.js +174 -0
- package/build/src/tools/swap-routing.js.map +1 -0
- package/build/src/tools/types.d.ts +124 -0
- package/build/src/tools/types.js +2 -0
- package/build/src/tools/types.js.map +1 -0
- package/build/src/tools/utils/normalize-token.d.ts +2 -0
- package/build/src/tools/utils/normalize-token.js +12 -0
- package/build/src/tools/utils/normalize-token.js.map +1 -0
- package/build/src/tools/utils/wallet.d.ts +4 -0
- package/build/src/tools/utils/wallet.js +8 -0
- package/build/src/tools/utils/wallet.js.map +1 -0
- package/build/src/tools/website-sync.d.ts +28 -0
- package/build/src/tools/website-sync.js +165 -0
- package/build/src/tools/website-sync.js.map +1 -0
- package/build/src/types/prepared.d.ts +28 -0
- package/build/src/types/prepared.js +12 -0
- package/build/src/types/prepared.js.map +1 -0
- package/build/src/utils/celo-format.d.ts +6 -0
- package/build/src/utils/celo-format.js +17 -0
- package/build/src/utils/celo-format.js.map +1 -0
- package/build/src/utils/erc20-allowance-storage.d.ts +20 -0
- package/build/src/utils/erc20-allowance-storage.js +64 -0
- package/build/src/utils/erc20-allowance-storage.js.map +1 -0
- package/build/src/utils/format-date.d.ts +2 -0
- package/build/src/utils/format-date.js +13 -0
- package/build/src/utils/format-date.js.map +1 -0
- package/build/src/utils/format-duration.d.ts +2 -0
- package/build/src/utils/format-duration.js +17 -0
- package/build/src/utils/format-duration.js.map +1 -0
- package/build/src/utils/format-unix-datetime.d.ts +4 -0
- package/build/src/utils/format-unix-datetime.js +18 -0
- package/build/src/utils/format-unix-datetime.js.map +1 -0
- package/build/src/utils/gooddollar-ubi-period.d.ts +23 -0
- package/build/src/utils/gooddollar-ubi-period.js +23 -0
- package/build/src/utils/gooddollar-ubi-period.js.map +1 -0
- package/build/src/utils/normalize-address.d.ts +7 -0
- package/build/src/utils/normalize-address.js +16 -0
- package/build/src/utils/normalize-address.js.map +1 -0
- package/build/src/utils/self-format.d.ts +28 -0
- package/build/src/utils/self-format.js +79 -0
- package/build/src/utils/self-format.js.map +1 -0
- package/build/src/utils/self-signing.d.ts +4 -0
- package/build/src/utils/self-signing.js +38 -0
- package/build/src/utils/self-signing.js.map +1 -0
- package/build/src/utils/transaction-errors.d.ts +3 -0
- package/build/src/utils/transaction-errors.js +17 -0
- package/build/src/utils/transaction-errors.js.map +1 -0
- package/build/tests/catalog/domains/blockchain.d.ts +2 -0
- package/build/tests/catalog/domains/blockchain.js +127 -0
- package/build/tests/catalog/domains/blockchain.js.map +1 -0
- package/build/tests/catalog/domains/chain-ext.d.ts +5 -0
- package/build/tests/catalog/domains/chain-ext.js +207 -0
- package/build/tests/catalog/domains/chain-ext.js.map +1 -0
- package/build/tests/catalog/domains/defi.d.ts +6 -0
- package/build/tests/catalog/domains/defi.js +581 -0
- package/build/tests/catalog/domains/defi.js.map +1 -0
- package/build/tests/catalog/domains/self.d.ts +2 -0
- package/build/tests/catalog/domains/self.js +208 -0
- package/build/tests/catalog/domains/self.js.map +1 -0
- package/build/tests/catalog/domains/token.d.ts +2 -0
- package/build/tests/catalog/domains/token.js +70 -0
- package/build/tests/catalog/domains/token.js.map +1 -0
- package/build/tests/catalog/domains/transaction.d.ts +2 -0
- package/build/tests/catalog/domains/transaction.js +96 -0
- package/build/tests/catalog/domains/transaction.js.map +1 -0
- package/build/tests/catalog/index.d.ts +2 -0
- package/build/tests/catalog/index.js +2 -0
- package/build/tests/catalog/index.js.map +1 -0
- package/build/tests/catalog/operations.d.ts +12 -0
- package/build/tests/catalog/operations.js +29 -0
- package/build/tests/catalog/operations.js.map +1 -0
- package/build/tests/catalog/types.d.ts +24 -0
- package/build/tests/catalog/types.js +2 -0
- package/build/tests/catalog/types.js.map +1 -0
- package/build/tests/fixtures/mainnet.d.ts +54 -0
- package/build/tests/fixtures/mainnet.js +53 -0
- package/build/tests/fixtures/mainnet.js.map +1 -0
- package/build/tests/helpers/assert.d.ts +4 -0
- package/build/tests/helpers/assert.js +24 -0
- package/build/tests/helpers/assert.js.map +1 -0
- package/build/tests/helpers/env.d.ts +11 -0
- package/build/tests/helpers/env.js +28 -0
- package/build/tests/helpers/env.js.map +1 -0
- package/build/tests/helpers/gating.d.ts +3 -0
- package/build/tests/helpers/gating.js +23 -0
- package/build/tests/helpers/gating.js.map +1 -0
- package/build/tests/testing-entry.d.ts +6 -0
- package/build/tests/testing-entry.js +6 -0
- package/build/tests/testing-entry.js.map +1 -0
- package/build/tools/domains/browser.js +4 -1
- package/build/tools/domains/browser.js.map +1 -1
- package/build/tools/domains/gooddollar.js +11 -7
- package/build/tools/domains/gooddollar.js.map +1 -1
- package/build/tools/schemas/common.d.ts +7 -0
- package/build/tools/schemas/common.js +9 -1
- package/build/tools/schemas/common.js.map +1 -1
- package/build/tools/swap-routing.d.ts +1 -0
- package/build/tools/swap-routing.js +2 -1
- package/build/tools/swap-routing.js.map +1 -1
- package/package.json +5 -9
- package/tests/README.md +0 -78
- package/tests/catalog/domains/blockchain.ts +0 -133
- package/tests/catalog/domains/chain-ext.ts +0 -219
- package/tests/catalog/domains/defi.ts +0 -532
- package/tests/catalog/domains/self.ts +0 -220
- package/tests/catalog/domains/token.ts +0 -74
- package/tests/catalog/domains/transaction.ts +0 -111
- package/tests/catalog/index.ts +0 -7
- package/tests/catalog/operations.ts +0 -53
- package/tests/catalog/types.ts +0 -27
- package/tests/fixtures/mainnet.ts +0 -93
- package/tests/helpers/assert.ts +0 -30
- package/tests/helpers/env.ts +0 -38
- package/tests/helpers/gating.ts +0 -36
- package/tests/testing-entry.ts +0 -27
|
@@ -0,0 +1,110 @@
|
|
|
1
|
+
import type { CeloClientFactory } from "../clients/celo-client.js";
|
|
2
|
+
/** Resolved Celo mainnet registry token (symbol, address, decimals). */
|
|
3
|
+
export interface ResolvedToken {
|
|
4
|
+
/** Registry address, or `"native"` for CELO. */
|
|
5
|
+
address: `0x${string}` | "native";
|
|
6
|
+
/** Canonical registry symbol (e.g. `USDm`, `GoodDollar`). */
|
|
7
|
+
symbol: string;
|
|
8
|
+
/** Token decimals for amount parsing. */
|
|
9
|
+
decimals: number;
|
|
10
|
+
}
|
|
11
|
+
/** Celo mainnet token registry lookups and balance reads. */
|
|
12
|
+
export declare class TokenService {
|
|
13
|
+
private readonly clientFactory;
|
|
14
|
+
constructor(clientFactory: CeloClientFactory);
|
|
15
|
+
/**
|
|
16
|
+
* Resolve a Celo mainnet registry token by symbol, alias, or registry address.
|
|
17
|
+
* @throws If the token is not in the Celo registry
|
|
18
|
+
*/
|
|
19
|
+
resolveToken(token: string): ResolvedToken;
|
|
20
|
+
/** Fetch registry token metadata on Celo mainnet. */
|
|
21
|
+
getTokenInfo(token: string): Promise<{
|
|
22
|
+
network: "mainnet";
|
|
23
|
+
address: `0x${string}` | "native";
|
|
24
|
+
name: string;
|
|
25
|
+
symbol: string;
|
|
26
|
+
decimals: number;
|
|
27
|
+
}>;
|
|
28
|
+
/** CELO and ERC-20 balances for registry tokens (defaults: CELO, USDm). */
|
|
29
|
+
getBalances(address: `0x${string}`, tokens?: string[]): Promise<{
|
|
30
|
+
network: "mainnet";
|
|
31
|
+
address: `0x${string}`;
|
|
32
|
+
balances: ({
|
|
33
|
+
token: string;
|
|
34
|
+
address: "native";
|
|
35
|
+
raw: string;
|
|
36
|
+
formatted: string;
|
|
37
|
+
} | {
|
|
38
|
+
token: string;
|
|
39
|
+
address: `0x${string}`;
|
|
40
|
+
raw: string;
|
|
41
|
+
formatted: string;
|
|
42
|
+
})[];
|
|
43
|
+
}>;
|
|
44
|
+
/**
|
|
45
|
+
* Scan fiat-pegged registry stablecoins for an address; omits zero balances by default.
|
|
46
|
+
* GoodDollar and WETH are excluded — use `getTokenBalance` or GoodDollar tools.
|
|
47
|
+
* @param address - Wallet to scan
|
|
48
|
+
* @param options.stablecoins - Subset of registry symbols to check
|
|
49
|
+
* @param options.includeZero - Include tokens with zero balance
|
|
50
|
+
*/
|
|
51
|
+
getStablecoinBalances(address: `0x${string}`, options?: {
|
|
52
|
+
stablecoins?: string[];
|
|
53
|
+
includeZero?: boolean;
|
|
54
|
+
}): Promise<{
|
|
55
|
+
network: string;
|
|
56
|
+
address: `0x${string}`;
|
|
57
|
+
totalChecked: number;
|
|
58
|
+
stablecoins: ({
|
|
59
|
+
symbol: string;
|
|
60
|
+
address: `0x${string}`;
|
|
61
|
+
issuer: string;
|
|
62
|
+
useCase: string;
|
|
63
|
+
raw: string;
|
|
64
|
+
formatted: string;
|
|
65
|
+
readError: boolean;
|
|
66
|
+
} | {
|
|
67
|
+
symbol: string;
|
|
68
|
+
address: `0x${string}`;
|
|
69
|
+
issuer: string;
|
|
70
|
+
useCase: string;
|
|
71
|
+
raw: string;
|
|
72
|
+
formatted: string;
|
|
73
|
+
readError?: undefined;
|
|
74
|
+
})[];
|
|
75
|
+
}>;
|
|
76
|
+
/** Balance for a Celo mainnet registry token (symbol or registry address). */
|
|
77
|
+
getTokenBalance(token: string, accountAddress: `0x${string}`): Promise<{
|
|
78
|
+
network: "mainnet";
|
|
79
|
+
tokenAddress: "native";
|
|
80
|
+
accountAddress: `0x${string}`;
|
|
81
|
+
name: string;
|
|
82
|
+
symbol: string;
|
|
83
|
+
decimals: number;
|
|
84
|
+
raw: string;
|
|
85
|
+
formatted: string;
|
|
86
|
+
} | {
|
|
87
|
+
network: "mainnet";
|
|
88
|
+
tokenAddress: `0x${string}`;
|
|
89
|
+
accountAddress: `0x${string}`;
|
|
90
|
+
name: string;
|
|
91
|
+
symbol: string;
|
|
92
|
+
decimals: number;
|
|
93
|
+
raw: string;
|
|
94
|
+
formatted: string;
|
|
95
|
+
}>;
|
|
96
|
+
/**
|
|
97
|
+
* Parse a human-readable amount string to base units for the given decimals.
|
|
98
|
+
* @param amount - Decimal string (e.g. `"10"` or `"0.05"`)
|
|
99
|
+
* @param decimals - Token decimals from `resolveToken`
|
|
100
|
+
*/
|
|
101
|
+
parseAmount(amount: string, decimals: number): bigint;
|
|
102
|
+
/**
|
|
103
|
+
* Ensure `owner` holds at least `amount` of the input token before swap/route work.
|
|
104
|
+
* @param spendToken - ERC-20 to check (defaults to registry address; use WCELO when swapping native CELO)
|
|
105
|
+
*/
|
|
106
|
+
assertSpendableBalance(owner: `0x${string}`, resolved: ResolvedToken, amount: string, options?: {
|
|
107
|
+
spendToken?: `0x${string}` | "native";
|
|
108
|
+
hint?: string;
|
|
109
|
+
}): Promise<void>;
|
|
110
|
+
}
|
|
@@ -0,0 +1,189 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Token registry lookups and balance reads on Celo mainnet.
|
|
3
|
+
*/
|
|
4
|
+
import { erc20Abi, formatUnits, parseUnits } from "viem";
|
|
5
|
+
import { findKnownToken, KNOWN_TOKEN_SYMBOLS, resolveStablecoins, suggestKnownTokens, } from "../config/chains.js";
|
|
6
|
+
import { normalizeAddress } from "../utils/normalize-address.js";
|
|
7
|
+
/** Celo mainnet token registry lookups and balance reads. */
|
|
8
|
+
export class TokenService {
|
|
9
|
+
clientFactory;
|
|
10
|
+
constructor(clientFactory) {
|
|
11
|
+
this.clientFactory = clientFactory;
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Resolve a Celo mainnet registry token by symbol, alias, or registry address.
|
|
15
|
+
* @throws If the token is not in the Celo registry
|
|
16
|
+
*/
|
|
17
|
+
resolveToken(token) {
|
|
18
|
+
const known = findKnownToken(token.trim());
|
|
19
|
+
if (!known) {
|
|
20
|
+
const suggestions = suggestKnownTokens(token);
|
|
21
|
+
if (suggestions.length > 0) {
|
|
22
|
+
throw new Error(`Unknown token "${token}" on Celo mainnet. Did you mean ${suggestions.map((entry) => entry.symbol).join(", ")}?`);
|
|
23
|
+
}
|
|
24
|
+
throw new Error(`Unknown token "${token}" on Celo mainnet. Use ${KNOWN_TOKEN_SYMBOLS.join(", ")}.`);
|
|
25
|
+
}
|
|
26
|
+
return {
|
|
27
|
+
address: known.address,
|
|
28
|
+
symbol: known.symbol,
|
|
29
|
+
decimals: known.decimals,
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
/** Fetch registry token metadata on Celo mainnet. */
|
|
33
|
+
async getTokenInfo(token) {
|
|
34
|
+
const resolved = this.resolveToken(token);
|
|
35
|
+
return {
|
|
36
|
+
network: "mainnet",
|
|
37
|
+
address: resolved.address,
|
|
38
|
+
name: resolved.address === "native" ? "Celo" : resolved.symbol,
|
|
39
|
+
symbol: resolved.symbol,
|
|
40
|
+
decimals: resolved.decimals,
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
/** CELO and ERC-20 balances for registry tokens (defaults: CELO, USDm). */
|
|
44
|
+
async getBalances(address, tokens = ["CELO", "USDm"]) {
|
|
45
|
+
const { public: client } = this.clientFactory.getClients();
|
|
46
|
+
const balances = await Promise.all(tokens.map(async (tokenInput) => {
|
|
47
|
+
const token = this.resolveToken(tokenInput);
|
|
48
|
+
if (token.address === "native") {
|
|
49
|
+
const balance = await client.getBalance({ address });
|
|
50
|
+
return {
|
|
51
|
+
token: token.symbol,
|
|
52
|
+
address: "native",
|
|
53
|
+
raw: balance.toString(),
|
|
54
|
+
formatted: formatUnits(balance, token.decimals),
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
const balance = await client.readContract({
|
|
58
|
+
address: token.address,
|
|
59
|
+
abi: erc20Abi,
|
|
60
|
+
functionName: "balanceOf",
|
|
61
|
+
args: [address],
|
|
62
|
+
});
|
|
63
|
+
return {
|
|
64
|
+
token: token.symbol,
|
|
65
|
+
address: token.address,
|
|
66
|
+
raw: balance.toString(),
|
|
67
|
+
formatted: formatUnits(balance, token.decimals),
|
|
68
|
+
};
|
|
69
|
+
}));
|
|
70
|
+
return { network: "mainnet", address, balances };
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* Scan fiat-pegged registry stablecoins for an address; omits zero balances by default.
|
|
74
|
+
* GoodDollar and WETH are excluded — use `getTokenBalance` or GoodDollar tools.
|
|
75
|
+
* @param address - Wallet to scan
|
|
76
|
+
* @param options.stablecoins - Subset of registry symbols to check
|
|
77
|
+
* @param options.includeZero - Include tokens with zero balance
|
|
78
|
+
*/
|
|
79
|
+
async getStablecoinBalances(address, options) {
|
|
80
|
+
const coins = resolveStablecoins(options?.stablecoins);
|
|
81
|
+
const { public: client } = this.clientFactory.getClients();
|
|
82
|
+
const results = await client.multicall({
|
|
83
|
+
contracts: coins.map((coin) => ({
|
|
84
|
+
address: coin.address,
|
|
85
|
+
abi: erc20Abi,
|
|
86
|
+
functionName: "balanceOf",
|
|
87
|
+
args: [address],
|
|
88
|
+
})),
|
|
89
|
+
allowFailure: true,
|
|
90
|
+
});
|
|
91
|
+
const balances = coins.map((coin, index) => {
|
|
92
|
+
const result = results[index];
|
|
93
|
+
if (result.status === "failure") {
|
|
94
|
+
return {
|
|
95
|
+
symbol: coin.symbol,
|
|
96
|
+
address: coin.address,
|
|
97
|
+
issuer: coin.issuer,
|
|
98
|
+
useCase: coin.useCase,
|
|
99
|
+
raw: "0",
|
|
100
|
+
formatted: "0",
|
|
101
|
+
readError: true,
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
const raw = result.result;
|
|
105
|
+
return {
|
|
106
|
+
symbol: coin.symbol,
|
|
107
|
+
address: coin.address,
|
|
108
|
+
issuer: coin.issuer,
|
|
109
|
+
useCase: coin.useCase,
|
|
110
|
+
raw: raw.toString(),
|
|
111
|
+
formatted: formatUnits(raw, coin.decimals),
|
|
112
|
+
};
|
|
113
|
+
});
|
|
114
|
+
const stablecoins = options?.includeZero
|
|
115
|
+
? balances
|
|
116
|
+
: balances.filter((balance) => balance.raw !== "0");
|
|
117
|
+
return {
|
|
118
|
+
network: "mainnet",
|
|
119
|
+
address,
|
|
120
|
+
totalChecked: coins.length,
|
|
121
|
+
stablecoins,
|
|
122
|
+
};
|
|
123
|
+
}
|
|
124
|
+
/** Balance for a Celo mainnet registry token (symbol or registry address). */
|
|
125
|
+
async getTokenBalance(token, accountAddress) {
|
|
126
|
+
const resolved = this.resolveToken(token);
|
|
127
|
+
const account = normalizeAddress(accountAddress, "account address");
|
|
128
|
+
const { public: client } = this.clientFactory.getClients();
|
|
129
|
+
if (resolved.address === "native") {
|
|
130
|
+
const balance = await client.getBalance({ address: account });
|
|
131
|
+
return {
|
|
132
|
+
network: "mainnet",
|
|
133
|
+
tokenAddress: "native",
|
|
134
|
+
accountAddress: account,
|
|
135
|
+
name: "Celo",
|
|
136
|
+
symbol: "CELO",
|
|
137
|
+
decimals: resolved.decimals,
|
|
138
|
+
raw: balance.toString(),
|
|
139
|
+
formatted: formatUnits(balance, resolved.decimals),
|
|
140
|
+
};
|
|
141
|
+
}
|
|
142
|
+
const balance = await client.readContract({
|
|
143
|
+
address: resolved.address,
|
|
144
|
+
abi: erc20Abi,
|
|
145
|
+
functionName: "balanceOf",
|
|
146
|
+
args: [account],
|
|
147
|
+
});
|
|
148
|
+
return {
|
|
149
|
+
network: "mainnet",
|
|
150
|
+
tokenAddress: resolved.address,
|
|
151
|
+
accountAddress: account,
|
|
152
|
+
name: resolved.symbol,
|
|
153
|
+
symbol: resolved.symbol,
|
|
154
|
+
decimals: resolved.decimals,
|
|
155
|
+
raw: balance.toString(),
|
|
156
|
+
formatted: formatUnits(balance, resolved.decimals),
|
|
157
|
+
};
|
|
158
|
+
}
|
|
159
|
+
/**
|
|
160
|
+
* Parse a human-readable amount string to base units for the given decimals.
|
|
161
|
+
* @param amount - Decimal string (e.g. `"10"` or `"0.05"`)
|
|
162
|
+
* @param decimals - Token decimals from `resolveToken`
|
|
163
|
+
*/
|
|
164
|
+
parseAmount(amount, decimals) {
|
|
165
|
+
return parseUnits(amount, decimals);
|
|
166
|
+
}
|
|
167
|
+
/**
|
|
168
|
+
* Ensure `owner` holds at least `amount` of the input token before swap/route work.
|
|
169
|
+
* @param spendToken - ERC-20 to check (defaults to registry address; use WCELO when swapping native CELO)
|
|
170
|
+
*/
|
|
171
|
+
async assertSpendableBalance(owner, resolved, amount, options) {
|
|
172
|
+
const { public: client } = this.clientFactory.getClients();
|
|
173
|
+
const required = this.parseAmount(amount, resolved.decimals);
|
|
174
|
+
const spend = options?.spendToken ?? resolved.address;
|
|
175
|
+
const balance = spend === "native"
|
|
176
|
+
? await client.getBalance({ address: owner })
|
|
177
|
+
: await client.readContract({
|
|
178
|
+
address: spend,
|
|
179
|
+
abi: erc20Abi,
|
|
180
|
+
functionName: "balanceOf",
|
|
181
|
+
args: [owner],
|
|
182
|
+
});
|
|
183
|
+
if (balance < required) {
|
|
184
|
+
const available = formatUnits(balance, resolved.decimals);
|
|
185
|
+
throw new Error(`Insufficient ${resolved.symbol} balance. Required ${amount} ${resolved.symbol}, available ${available}.${options?.hint ?? ""}`);
|
|
186
|
+
}
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
//# sourceMappingURL=token.service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"token.service.js","sourceRoot":"","sources":["../../../src/services/token.service.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Token sends: estimateSend simulates gas; prepareSend builds unsigned tx steps.
|
|
3
|
+
* Calldata is tagged with CELINA_DATA_SUFFIX for on-chain attribution.
|
|
4
|
+
*/
|
|
5
|
+
import { type Hex } from "viem";
|
|
6
|
+
import type { CeloClientFactory } from "../clients/celo-client.js";
|
|
7
|
+
import { type SerializedPreparedFlow } from "../types/prepared.js";
|
|
8
|
+
export type SendEstimateResult = {
|
|
9
|
+
network: "mainnet";
|
|
10
|
+
from: `0x${string}`;
|
|
11
|
+
to: `0x${string}`;
|
|
12
|
+
token: string;
|
|
13
|
+
amount: string;
|
|
14
|
+
gas: string | null;
|
|
15
|
+
insufficientBalance?: boolean;
|
|
16
|
+
message?: string;
|
|
17
|
+
};
|
|
18
|
+
/** Token sends, gas fee reads, and `prepareSend` flows with CELINA calldata tags. */
|
|
19
|
+
export declare class TransactionService {
|
|
20
|
+
private readonly clientFactory;
|
|
21
|
+
private readonly tokenService;
|
|
22
|
+
constructor(clientFactory: CeloClientFactory);
|
|
23
|
+
/**
|
|
24
|
+
* Simulate gas for a CELO or ERC-20 transfer from `from`.
|
|
25
|
+
* @param from - Sender wallet address
|
|
26
|
+
* @param to - Recipient address
|
|
27
|
+
* @param token - Symbol (e.g. `CELO`, `USDm`) or contract address
|
|
28
|
+
* @param amount - Human-readable amount (e.g. `"10"`)
|
|
29
|
+
* @returns Gas estimate in units as a decimal string, or a structured insufficient-balance result when simulation reverts.
|
|
30
|
+
*/
|
|
31
|
+
estimateSend(from: `0x${string}`, to: `0x${string}`, token: string, amount: string): Promise<SendEstimateResult>;
|
|
32
|
+
/**
|
|
33
|
+
* Build an unsigned send flow (native CELO or ERC-20 transfer).
|
|
34
|
+
* @param from - Sender wallet address (must match connected wallet when signing)
|
|
35
|
+
* @param to - Recipient address
|
|
36
|
+
* @param token - Symbol or contract address
|
|
37
|
+
* @param amount - Human-readable amount
|
|
38
|
+
* @returns Single-step `SerializedPreparedFlow` for wagmi `sendTransactionAsync`
|
|
39
|
+
*/
|
|
40
|
+
prepareSend(from: `0x${string}`, to: `0x${string}`, token: string, amount: string): Promise<SerializedPreparedFlow>;
|
|
41
|
+
/** Current gas fee data including EIP-1559 fees when supported. */
|
|
42
|
+
getGasFeeData(): Promise<{
|
|
43
|
+
network: "mainnet";
|
|
44
|
+
baseFeePerGas: string;
|
|
45
|
+
maxFeePerGas: string;
|
|
46
|
+
maxPriorityFeePerGas: string;
|
|
47
|
+
gasPrice: string;
|
|
48
|
+
eip1559: boolean;
|
|
49
|
+
}>;
|
|
50
|
+
/** Generic transaction gas estimate (not token-transfer specific). */
|
|
51
|
+
estimateTransaction(params: {
|
|
52
|
+
from: `0x${string}`;
|
|
53
|
+
to: `0x${string}`;
|
|
54
|
+
value?: string;
|
|
55
|
+
data?: Hex;
|
|
56
|
+
}): Promise<{
|
|
57
|
+
network: "mainnet";
|
|
58
|
+
from: `0x${string}`;
|
|
59
|
+
to: `0x${string}`;
|
|
60
|
+
gasLimit: string;
|
|
61
|
+
gasPrice: string;
|
|
62
|
+
maxFeePerGas: string;
|
|
63
|
+
maxPriorityFeePerGas: string;
|
|
64
|
+
estimatedCost: string;
|
|
65
|
+
estimatedCostFormatted: string;
|
|
66
|
+
isEip1559: boolean;
|
|
67
|
+
}>;
|
|
68
|
+
}
|
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Token sends: estimateSend simulates gas; prepareSend builds unsigned tx steps.
|
|
3
|
+
* Calldata is tagged with CELINA_DATA_SUFFIX for on-chain attribution.
|
|
4
|
+
*/
|
|
5
|
+
import { concat, encodeFunctionData, erc20Abi, parseEther, parseGwei, } from "viem";
|
|
6
|
+
import { MENTO_CELO_ADDRESS } from "../config/chains.js";
|
|
7
|
+
import { CELINA_DATA_SUFFIX } from "../config/celina-tag.js";
|
|
8
|
+
import { normalizeAddress } from "../utils/normalize-address.js";
|
|
9
|
+
import { serializePreparedFlow, } from "../types/prepared.js";
|
|
10
|
+
import { TokenService } from "./token.service.js";
|
|
11
|
+
import { insufficientBalanceEstimateMessage, isInsufficientBalanceSimulationError, } from "../utils/transaction-errors.js";
|
|
12
|
+
function taggedCalldata(data) {
|
|
13
|
+
return concat([data, CELINA_DATA_SUFFIX]);
|
|
14
|
+
}
|
|
15
|
+
/** Token sends, gas fee reads, and `prepareSend` flows with CELINA calldata tags. */
|
|
16
|
+
export class TransactionService {
|
|
17
|
+
clientFactory;
|
|
18
|
+
tokenService;
|
|
19
|
+
constructor(clientFactory) {
|
|
20
|
+
this.clientFactory = clientFactory;
|
|
21
|
+
this.tokenService = new TokenService(clientFactory);
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* Simulate gas for a CELO or ERC-20 transfer from `from`.
|
|
25
|
+
* @param from - Sender wallet address
|
|
26
|
+
* @param to - Recipient address
|
|
27
|
+
* @param token - Symbol (e.g. `CELO`, `USDm`) or contract address
|
|
28
|
+
* @param amount - Human-readable amount (e.g. `"10"`)
|
|
29
|
+
* @returns Gas estimate in units as a decimal string, or a structured insufficient-balance result when simulation reverts.
|
|
30
|
+
*/
|
|
31
|
+
async estimateSend(from, to, token, amount) {
|
|
32
|
+
const { public: client } = this.clientFactory.getClients();
|
|
33
|
+
const resolved = this.tokenService.resolveToken(token);
|
|
34
|
+
const base = {
|
|
35
|
+
network: "mainnet",
|
|
36
|
+
from,
|
|
37
|
+
to,
|
|
38
|
+
token: resolved.symbol,
|
|
39
|
+
amount,
|
|
40
|
+
};
|
|
41
|
+
try {
|
|
42
|
+
if (resolved.address === "native") {
|
|
43
|
+
const tokenAmount = parseEther(amount);
|
|
44
|
+
const gas = await client.estimateContractGas({
|
|
45
|
+
account: from,
|
|
46
|
+
address: MENTO_CELO_ADDRESS,
|
|
47
|
+
abi: erc20Abi,
|
|
48
|
+
functionName: "transfer",
|
|
49
|
+
args: [to, tokenAmount],
|
|
50
|
+
});
|
|
51
|
+
return { ...base, gas: gas.toString() };
|
|
52
|
+
}
|
|
53
|
+
const tokenAmount = this.tokenService.parseAmount(amount, resolved.decimals);
|
|
54
|
+
const gas = await client.estimateContractGas({
|
|
55
|
+
account: from,
|
|
56
|
+
address: resolved.address,
|
|
57
|
+
abi: erc20Abi,
|
|
58
|
+
functionName: "transfer",
|
|
59
|
+
args: [to, tokenAmount],
|
|
60
|
+
});
|
|
61
|
+
return { ...base, gas: gas.toString() };
|
|
62
|
+
}
|
|
63
|
+
catch (error) {
|
|
64
|
+
if (isInsufficientBalanceSimulationError(error)) {
|
|
65
|
+
return {
|
|
66
|
+
...base,
|
|
67
|
+
gas: null,
|
|
68
|
+
insufficientBalance: true,
|
|
69
|
+
message: insufficientBalanceEstimateMessage(resolved.symbol),
|
|
70
|
+
};
|
|
71
|
+
}
|
|
72
|
+
throw error;
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
/**
|
|
76
|
+
* Build an unsigned send flow (native CELO or ERC-20 transfer).
|
|
77
|
+
* @param from - Sender wallet address (must match connected wallet when signing)
|
|
78
|
+
* @param to - Recipient address
|
|
79
|
+
* @param token - Symbol or contract address
|
|
80
|
+
* @param amount - Human-readable amount
|
|
81
|
+
* @returns Single-step `SerializedPreparedFlow` for wagmi `sendTransactionAsync`
|
|
82
|
+
*/
|
|
83
|
+
async prepareSend(from, to, token, amount) {
|
|
84
|
+
const resolved = this.tokenService.resolveToken(token);
|
|
85
|
+
if (resolved.address === "native") {
|
|
86
|
+
const tokenAmount = parseEther(amount);
|
|
87
|
+
const data = taggedCalldata(encodeFunctionData({
|
|
88
|
+
abi: erc20Abi,
|
|
89
|
+
functionName: "transfer",
|
|
90
|
+
args: [to, tokenAmount],
|
|
91
|
+
}));
|
|
92
|
+
const flow = {
|
|
93
|
+
network: "mainnet",
|
|
94
|
+
from,
|
|
95
|
+
summary: `Send ${amount} CELO to ${to}`,
|
|
96
|
+
steps: [
|
|
97
|
+
{
|
|
98
|
+
kind: "erc20",
|
|
99
|
+
to: MENTO_CELO_ADDRESS,
|
|
100
|
+
data,
|
|
101
|
+
value: "0",
|
|
102
|
+
description: `Send ${amount} CELO`,
|
|
103
|
+
},
|
|
104
|
+
],
|
|
105
|
+
};
|
|
106
|
+
return serializePreparedFlow(flow);
|
|
107
|
+
}
|
|
108
|
+
const tokenAmount = this.tokenService.parseAmount(amount, resolved.decimals);
|
|
109
|
+
const data = taggedCalldata(encodeFunctionData({
|
|
110
|
+
abi: erc20Abi,
|
|
111
|
+
functionName: "transfer",
|
|
112
|
+
args: [to, tokenAmount],
|
|
113
|
+
}));
|
|
114
|
+
const flow = {
|
|
115
|
+
network: "mainnet",
|
|
116
|
+
from,
|
|
117
|
+
summary: `Send ${amount} ${resolved.symbol} to ${to}`,
|
|
118
|
+
steps: [
|
|
119
|
+
{
|
|
120
|
+
kind: "erc20",
|
|
121
|
+
to: resolved.address,
|
|
122
|
+
data,
|
|
123
|
+
value: "0",
|
|
124
|
+
description: `Transfer ${amount} ${resolved.symbol}`,
|
|
125
|
+
},
|
|
126
|
+
],
|
|
127
|
+
};
|
|
128
|
+
return serializePreparedFlow(flow);
|
|
129
|
+
}
|
|
130
|
+
/** Current gas fee data including EIP-1559 fees when supported. */
|
|
131
|
+
async getGasFeeData() {
|
|
132
|
+
const { public: client } = this.clientFactory.getClients();
|
|
133
|
+
const [block, gasPrice] = await Promise.all([
|
|
134
|
+
client.getBlock({ blockTag: "latest" }),
|
|
135
|
+
client.getGasPrice(),
|
|
136
|
+
]);
|
|
137
|
+
const baseFeePerGas = block.baseFeePerGas;
|
|
138
|
+
if (baseFeePerGas) {
|
|
139
|
+
const maxPriorityFeePerGas = parseGwei("2");
|
|
140
|
+
const maxFeePerGas = baseFeePerGas * 2n + maxPriorityFeePerGas;
|
|
141
|
+
return {
|
|
142
|
+
network: "mainnet",
|
|
143
|
+
baseFeePerGas: baseFeePerGas.toString(),
|
|
144
|
+
maxFeePerGas: maxFeePerGas.toString(),
|
|
145
|
+
maxPriorityFeePerGas: maxPriorityFeePerGas.toString(),
|
|
146
|
+
gasPrice: gasPrice.toString(),
|
|
147
|
+
eip1559: true,
|
|
148
|
+
};
|
|
149
|
+
}
|
|
150
|
+
return {
|
|
151
|
+
network: "mainnet",
|
|
152
|
+
baseFeePerGas: "0",
|
|
153
|
+
maxFeePerGas: gasPrice.toString(),
|
|
154
|
+
maxPriorityFeePerGas: "0",
|
|
155
|
+
gasPrice: gasPrice.toString(),
|
|
156
|
+
eip1559: false,
|
|
157
|
+
};
|
|
158
|
+
}
|
|
159
|
+
/** Generic transaction gas estimate (not token-transfer specific). */
|
|
160
|
+
async estimateTransaction(params) {
|
|
161
|
+
const from = normalizeAddress(params.from, "from address");
|
|
162
|
+
const to = normalizeAddress(params.to, "to address");
|
|
163
|
+
const { public: client } = this.clientFactory.getClients();
|
|
164
|
+
const value = params.value ? BigInt(params.value) : 0n;
|
|
165
|
+
const data = params.data ?? "0x";
|
|
166
|
+
let gasLimit;
|
|
167
|
+
try {
|
|
168
|
+
gasLimit = await client.estimateGas({
|
|
169
|
+
account: from,
|
|
170
|
+
to,
|
|
171
|
+
value,
|
|
172
|
+
data,
|
|
173
|
+
});
|
|
174
|
+
}
|
|
175
|
+
catch (error) {
|
|
176
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
177
|
+
throw new Error(`Transaction gas estimation failed: ${message}. ` +
|
|
178
|
+
"Ensure from/to addresses differ for empty transfers, or provide valid calldata.");
|
|
179
|
+
}
|
|
180
|
+
const feeData = await this.getGasFeeData();
|
|
181
|
+
const maxFee = BigInt(feeData.maxFeePerGas);
|
|
182
|
+
const estimatedCost = gasLimit * maxFee;
|
|
183
|
+
const estimatedCostCelo = Number(estimatedCost) / 1e18;
|
|
184
|
+
return {
|
|
185
|
+
network: "mainnet",
|
|
186
|
+
from,
|
|
187
|
+
to,
|
|
188
|
+
gasLimit: gasLimit.toString(),
|
|
189
|
+
gasPrice: feeData.gasPrice,
|
|
190
|
+
maxFeePerGas: feeData.maxFeePerGas,
|
|
191
|
+
maxPriorityFeePerGas: feeData.maxPriorityFeePerGas,
|
|
192
|
+
estimatedCost: estimatedCost.toString(),
|
|
193
|
+
estimatedCostFormatted: `${estimatedCostCelo} CELO`,
|
|
194
|
+
isEip1559: feeData.eip1559,
|
|
195
|
+
};
|
|
196
|
+
}
|
|
197
|
+
}
|
|
198
|
+
//# sourceMappingURL=transaction.service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"transaction.service.js","sourceRoot":"","sources":["../../../src/services/transaction.service.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Uniswap v4 path routing: BFS over pool index and V4Quoter best-path selection.
|
|
3
|
+
*/
|
|
4
|
+
import type { PublicClient } from "viem";
|
|
5
|
+
import { type UniswapPoolKey } from "../config/uniswap.js";
|
|
6
|
+
/** Single hop descriptor in a Uniswap v4 multi-hop path. */
|
|
7
|
+
export type UniswapPathKey = {
|
|
8
|
+
intermediateCurrency: `0x${string}`;
|
|
9
|
+
fee: number;
|
|
10
|
+
tickSpacing: number;
|
|
11
|
+
hooks: `0x${string}`;
|
|
12
|
+
hookData: `0x${string}`;
|
|
13
|
+
};
|
|
14
|
+
/** Best quoted route between two v4 currencies. */
|
|
15
|
+
export type UniswapSwapRoute = {
|
|
16
|
+
currencyIn: `0x${string}`;
|
|
17
|
+
currencyOut: `0x${string}`;
|
|
18
|
+
pools: UniswapPoolKey[];
|
|
19
|
+
pathKeys: UniswapPathKey[];
|
|
20
|
+
hops: number;
|
|
21
|
+
};
|
|
22
|
+
/**
|
|
23
|
+
* Quote all candidate paths and return the highest-output Uniswap v4 route.
|
|
24
|
+
* @param client - Celo public client for quoter simulation
|
|
25
|
+
* @param currencyIn - Input currency address (native CELO maps to WCELO upstream)
|
|
26
|
+
* @param currencyOut - Output currency address
|
|
27
|
+
* @param amountIn - Input amount in base units
|
|
28
|
+
* @returns Best route and quoter output, or `null` when no path quotes successfully
|
|
29
|
+
*/
|
|
30
|
+
export declare function findBestUniswapRoute(client: PublicClient, currencyIn: `0x${string}`, currencyOut: `0x${string}`, amountIn: bigint): Promise<{
|
|
31
|
+
route: UniswapSwapRoute;
|
|
32
|
+
amountOut: bigint;
|
|
33
|
+
indexSource: string;
|
|
34
|
+
} | null>;
|
|
35
|
+
/**
|
|
36
|
+
* Apply slippage tolerance to a quoted output amount.
|
|
37
|
+
* @param amountOut - Quoted output in base units
|
|
38
|
+
* @param slippagePercent - Max slippage in percent (e.g. `0.5` for 0.5%)
|
|
39
|
+
*/
|
|
40
|
+
export declare function applySlippage(amountOut: bigint, slippagePercent: number): bigint;
|