From 135ab421076638056560e416e04ab9dc9db7c6a1 Mon Sep 17 00:00:00 2001 From: SGiaccobasso Date: Tue, 10 Dec 2024 15:28:46 -0300 Subject: [PATCH] chore: wip token details --- apps/maestro/src/config/evm-chains.ts | 24 ++++++++++++++++++ .../lib/providers/WagmiConfigPropvider.tsx | 4 +-- .../routers/erc20/getERC20TokenDetails.ts | 4 +-- .../getInterchainTokenDetails.ts | 25 ++++++++----------- .../interchainToken/searchInterchainToken.ts | 8 +++--- apps/maestro/src/services/erc20/hooks.ts | 2 +- apps/maestro/src/services/gmp/hooks.ts | 4 +-- .../src/services/interchainToken/hooks.ts | 16 ++++++++++-- .../ConnectWalletButton.tsx | 22 ++++++++++------ .../ConnectWalletModal/ConnectWalletModal.tsx | 19 ++++++++------ .../InterchainTokenDetailsPage/index.tsx | 12 +++------ 11 files changed, 87 insertions(+), 53 deletions(-) diff --git a/apps/maestro/src/config/evm-chains.ts b/apps/maestro/src/config/evm-chains.ts index 32f5c0c32..f80583045 100644 --- a/apps/maestro/src/config/evm-chains.ts +++ b/apps/maestro/src/config/evm-chains.ts @@ -116,8 +116,32 @@ export const ALL_CHAINS: ExtendedWagmiChainConfig[] = [ default: { name: "Sui Explorer", url: "https://suiscan.xyz/testnet" }, }, }, + //TODO: check if this is ok + { + id: 103, + axelarChainId: "sui", + axelarChainName: "sui", + environment: ENVIRONMENTS.testnet, + name: "Sui Testnet", + nativeCurrency: { + name: "SUI", + symbol: "SUI", + decimals: 9, + }, + rpcUrls: { + default: { http: ["https://fullnode.testnet.sui.io:443"] }, + public: { http: ["https://fullnode.testnet.sui.io:443"] }, + }, + blockExplorers: { + default: { name: "Sui Explorer", url: "https://suiscan.xyz/testnet" }, + }, + }, { ...sepolia, + rpcUrls: { + default: { http: ["https://rpc-sepolia.rockx.com"] }, + public: { http: ["https://rpc-sepolia.rockx.com"] }, + }, axelarChainId: "ethereum-sepolia", axelarChainName: "ethereum-sepolia", environment: ENVIRONMENTS.testnet, diff --git a/apps/maestro/src/lib/providers/WagmiConfigPropvider.tsx b/apps/maestro/src/lib/providers/WagmiConfigPropvider.tsx index 794bc697b..e3ecd0592 100644 --- a/apps/maestro/src/lib/providers/WagmiConfigPropvider.tsx +++ b/apps/maestro/src/lib/providers/WagmiConfigPropvider.tsx @@ -1,6 +1,6 @@ import type { FC, PropsWithChildren } from "react"; -import { WagmiConfig } from "wagmi"; +import { WagmiProvider } from "wagmi"; import { wagmiConfig } from "~/config/wagmi"; @@ -8,5 +8,5 @@ export const WagmiConfigPropvider: FC = ({ children }) => { if (!wagmiConfig) { return <>{children}; } - return {children}; + return {children}; }; diff --git a/apps/maestro/src/server/routers/erc20/getERC20TokenDetails.ts b/apps/maestro/src/server/routers/erc20/getERC20TokenDetails.ts index 4779300ad..78363548e 100644 --- a/apps/maestro/src/server/routers/erc20/getERC20TokenDetails.ts +++ b/apps/maestro/src/server/routers/erc20/getERC20TokenDetails.ts @@ -6,7 +6,6 @@ import { always } from "rambda"; import { z } from "zod"; import { ExtendedWagmiChainConfig } from "~/config/evm-chains"; -import { hex40Literal } from "~/lib/utils/validation"; import { publicProcedure } from "~/server/trpc"; //TODO: migrate to kv store? @@ -20,13 +19,12 @@ export const getERC20TokenDetails = publicProcedure .input( z.object({ chainId: z.number().optional(), - tokenAddress: hex40Literal(), + tokenAddress: z.string(), }) ) .query(async ({ input, ctx }) => { try { const { wagmiChainConfigs: chainConfigs } = ctx.configs; - const chainConfig = chainConfigs.find( (chain) => chain.id === input.chainId ); diff --git a/apps/maestro/src/server/routers/interchainToken/getInterchainTokenDetails.ts b/apps/maestro/src/server/routers/interchainToken/getInterchainTokenDetails.ts index 877239147..12bbe5e53 100644 --- a/apps/maestro/src/server/routers/interchainToken/getInterchainTokenDetails.ts +++ b/apps/maestro/src/server/routers/interchainToken/getInterchainTokenDetails.ts @@ -2,19 +2,15 @@ import { TRPCError } from "@trpc/server"; import { z } from "zod"; import { TOKEN_MANAGER_TYPES } from "~/lib/drizzle/schema/common"; -import { - hex0xLiteral, - hex40Literal, - hex64Literal, -} from "~/lib/utils/validation"; +import { hex0xLiteral, hex64Literal } from "~/lib/utils/validation"; import { publicProcedure } from "~/server/trpc"; const remoteTokenSchema = z.object({ id: z.string(), tokenId: z.string(), axelarChainId: z.string(), - tokenAddress: hex40Literal(), - tokenManagerAddress: hex40Literal().nullable(), + tokenAddress: z.string(), + tokenManagerAddress: z.string().nullable(), tokenManagerType: z.enum(TOKEN_MANAGER_TYPES).nullable(), deploymentMessageId: z.string(), deploymentStatus: z.string().nullable(), @@ -24,21 +20,21 @@ const remoteTokenSchema = z.object({ export const inputSchema = z.object({ chainId: z.number(), - tokenAddress: hex40Literal(), + tokenAddress: z.string(), }); const outputSchema = z.object({ tokenId: z.string(), - tokenAddress: hex40Literal(), + tokenAddress: z.string(), axelarChainId: z.string(), tokenName: z.string(), tokenSymbol: z.string(), tokenDecimals: z.number(), deploymentMessageId: z.string(), - deployerAddress: hex40Literal(), - tokenManagerAddress: hex40Literal().nullable(), + deployerAddress: z.string(), + tokenManagerAddress: z.string().nullable(), tokenManagerType: z.enum(TOKEN_MANAGER_TYPES).nullable(), - originalMinterAddress: hex40Literal().nullable(), + originalMinterAddress: z.string().nullable(), kind: z.string(), createdAt: z.date().nullable(), updatedAt: z.date().nullable(), @@ -62,10 +58,11 @@ export const getInterchainTokenDetails = publicProcedure .query(async ({ input, ctx }) => { const chains = await ctx.configs.evmChains(); const configs = chains[input.chainId]; - + // TODO: remove this once we have sui in the chains object + const axelarChainId = input.chainId === 103 ? "sui" : configs.info.id; const tokenRecord = await ctx.persistence.postgres.getInterchainTokenByChainIdAndTokenAddress( - configs.info.id, + axelarChainId, input.tokenAddress ); diff --git a/apps/maestro/src/server/routers/interchainToken/searchInterchainToken.ts b/apps/maestro/src/server/routers/interchainToken/searchInterchainToken.ts index aed607e05..76e1a25a1 100644 --- a/apps/maestro/src/server/routers/interchainToken/searchInterchainToken.ts +++ b/apps/maestro/src/server/routers/interchainToken/searchInterchainToken.ts @@ -7,7 +7,7 @@ import { z } from "zod"; import type { ExtendedWagmiChainConfig } from "~/config/wagmi"; import { InterchainToken, RemoteInterchainToken } from "~/lib/drizzle/schema"; import { TOKEN_MANAGER_TYPES } from "~/lib/drizzle/schema/common"; -import { hex40Literal, hexLiteral } from "~/lib/utils/validation"; +import { hexLiteral } from "~/lib/utils/validation"; import type { Context } from "~/server/context"; import { publicProcedure } from "~/server/trpc"; @@ -17,8 +17,8 @@ const tokenDetailsSchema = z.object({ axelarChainId: z.string(), // nullable fields tokenId: hexLiteral().nullable(), - tokenAddress: hex40Literal().nullable(), - tokenManagerAddress: hex40Literal().optional().nullable(), + tokenAddress: z.string().nullable(), + tokenManagerAddress: z.string().optional().nullable(), tokenManagerType: z.enum(TOKEN_MANAGER_TYPES).nullable(), isOriginToken: z.boolean().nullable(), isRegistered: z.boolean(), @@ -27,7 +27,7 @@ const tokenDetailsSchema = z.object({ export const inputSchema = z.object({ chainId: z.number().optional(), - tokenAddress: hex40Literal(), + tokenAddress: z.string(), strict: z.boolean().optional(), }); diff --git a/apps/maestro/src/services/erc20/hooks.ts b/apps/maestro/src/services/erc20/hooks.ts index 1bab1ca95..a19ebed67 100644 --- a/apps/maestro/src/services/erc20/hooks.ts +++ b/apps/maestro/src/services/erc20/hooks.ts @@ -14,7 +14,7 @@ export function useERC20TokenDetailsQuery(input: { tokenAddress: String(input.tokenAddress), }, { - enabled: isAddress(input.tokenAddress ?? ""), + enabled: !!input.tokenAddress, retry: false, staleTime: 1000 * 60 * 60 * 24, // 24 hours refetchOnWindowFocus: false, diff --git a/apps/maestro/src/services/gmp/hooks.ts b/apps/maestro/src/services/gmp/hooks.ts index 82bf78598..f00a57049 100644 --- a/apps/maestro/src/services/gmp/hooks.ts +++ b/apps/maestro/src/services/gmp/hooks.ts @@ -1,8 +1,6 @@ import { Maybe } from "@axelarjs/utils"; import { useMemo } from "react"; -import { isAddress } from "viem"; - import { trpc } from "~/lib/trpc"; import { hex64 } from "~/lib/utils/validation"; import { useEVMChainConfigsQuery } from "../axelarscan/hooks"; @@ -22,7 +20,7 @@ export function useInterchainTokensQuery(input: { strict: input.strict, }, { - enabled: Maybe.of(input.tokenAddress).mapOr(false, isAddress), + enabled: Maybe.of(input.tokenAddress).mapOr(false, Boolean), retry: false, refetchOnWindowFocus: false, } diff --git a/apps/maestro/src/services/interchainToken/hooks.ts b/apps/maestro/src/services/interchainToken/hooks.ts index 0bae65226..8ff4afbe4 100644 --- a/apps/maestro/src/services/interchainToken/hooks.ts +++ b/apps/maestro/src/services/interchainToken/hooks.ts @@ -1,5 +1,7 @@ import { Maybe } from "@axelarjs/utils"; +import { getFullnodeUrl } from "@mysten/sui.js/client"; +import { SuiClient } from "@mysten/sui/client"; import { isAddress } from "viem"; import { trpc } from "~/lib/trpc"; @@ -14,18 +16,28 @@ export function useInterchainTokenDetailsQuery(input: { tokenAddress: String(input.tokenAddress), }, { - enabled: isAddress(input.tokenAddress ?? ""), + enabled: !!input.tokenAddress, staleTime: 1000 * 60 * 60 * 24, // 24 hours refetchOnWindowFocus: false, } ); } -export function useInterchainTokenBalanceForOwnerQuery(input: { +export async function useInterchainTokenBalanceForOwnerQuery(input: { chainId?: number; tokenAddress?: `0x${string}`; owner?: `0x${string}`; }) { + // TODO: WIP + if (input.chainId === 103) { + const coinType = `${input.tokenAddress}::sui::SUI`; + const client = new SuiClient({ url: getFullnodeUrl("testnet") }); + const coins = await client.getCoins({ + owner: input.owner as string, + coinType, + }); + return coins; + } return trpc.erc20.getERC20TokenBalanceForOwner.useQuery( { chainId: Number(input.chainId), diff --git a/apps/maestro/src/ui/compounds/ConnectWalletButton/ConnectWalletButton.tsx b/apps/maestro/src/ui/compounds/ConnectWalletButton/ConnectWalletButton.tsx index 437f16d49..660c905af 100644 --- a/apps/maestro/src/ui/compounds/ConnectWalletButton/ConnectWalletButton.tsx +++ b/apps/maestro/src/ui/compounds/ConnectWalletButton/ConnectWalletButton.tsx @@ -6,7 +6,15 @@ import { useWeb3Modal } from "@web3modal/wagmi/react"; type Props = ButtonProps; const ConnectWalletButton = forwardRef( - (props, ref) => { + ( + { + $size = "sm", + $variant = "primary", + children = "Connect Wallet", + ...props + }, + ref + ) => { const { open } = useWeb3Modal(); return ( @@ -15,17 +23,15 @@ const ConnectWalletButton = forwardRef( {...props} onClick={open.bind(null, { view: "Connect" })} ref={ref} - /> + $size={$size} + $variant={$variant} + > + {children} + ); } ); ConnectWalletButton.displayName = "ConnectWalletButton"; -ConnectWalletButton.defaultProps = { - $size: "sm", - $variant: "primary", - children: "Connect Wallet", -}; - export default ConnectWalletButton; diff --git a/apps/maestro/src/ui/compounds/ConnectWalletModal/ConnectWalletModal.tsx b/apps/maestro/src/ui/compounds/ConnectWalletModal/ConnectWalletModal.tsx index fe2e8b2bc..dc5c659b1 100644 --- a/apps/maestro/src/ui/compounds/ConnectWalletModal/ConnectWalletModal.tsx +++ b/apps/maestro/src/ui/compounds/ConnectWalletModal/ConnectWalletModal.tsx @@ -6,7 +6,15 @@ import { ConnectModal } from "@mysten/dapp-kit"; import ConnectWalletButton from "../ConnectWalletButton/ConnectWalletButton"; const ConnectWalletModal = forwardRef( - ({ children, ...props }, ref) => { + ( + { + $size = "md", + $variant = "primary", + children = "Connect Wallet", + ...props + }, + ref + ) => { const [isModalOpen, setIsModalOpen] = React.useState(false); return ( ( }} trigger={