diff --git a/app/src/components/Button.tsx b/app/src/components/Button.tsx index e2a18980..db8552a4 100644 --- a/app/src/components/Button.tsx +++ b/app/src/components/Button.tsx @@ -28,8 +28,8 @@ export namespace Button { default: 'text-gray12 bg-blackA1 dark:bg-whiteA1 border border-blackA1 dark:border-whiteA1', primary: 'text-white bg-blue10', - destructive: 'text-white bg-red10', - success: 'text-white bg-green10', + destructive: 'text-red10 bg-red3', + success: 'text-white bg-green9', warning: 'text-white bg-amber8', }, size: { diff --git a/app/src/components/Layout.tsx b/app/src/components/Layout.tsx index 3cf49e11..a6e4aba4 100644 --- a/app/src/components/Layout.tsx +++ b/app/src/components/Layout.tsx @@ -58,7 +58,7 @@ export namespace Layout {
- +
{title}
@@ -86,6 +86,7 @@ export namespace Layout { default: 'bg-blueA3 text-blue10', primary: 'bg-blueA3 text-blue10', warning: 'bg-amberA2 text-amber8', + destructive: 'bg-red3 text-red10', }, }, defaultVariants: { @@ -140,9 +141,7 @@ export namespace Layout { // Wallet Footer export function Wallet(props: Wallet.Props) { - const address = - props.address ?? - Hooks.usePortoStore(porto, (state) => state.accounts[0]?.address) + const address = props.address ?? Hooks.useAccount(porto)?.address if (!address) return null return (
diff --git a/app/src/lib/Query.ts b/app/src/lib/Query.ts index af1c2b29..a9c09498 100644 --- a/app/src/lib/Query.ts +++ b/app/src/lib/Query.ts @@ -5,6 +5,7 @@ export const client = new QueryClient({ defaultOptions: { queries: { gcTime: 1000 * 60 * 60 * 24, // 24 hours + retry: 0, }, }, }) diff --git a/app/src/routeTree.gen.ts b/app/src/routeTree.gen.ts index e1c139c7..358b1f2e 100644 --- a/app/src/routeTree.gen.ts +++ b/app/src/routeTree.gen.ts @@ -13,10 +13,12 @@ import { Route as rootRoute } from './routes/__root' import { Route as DialogImport } from './routes/_dialog' import { Route as IndexImport } from './routes/index' +import { Route as DialogDialogWalletsendCallsImport } from './routes/_dialog.dialog/wallet_sendCalls' import { Route as DialogDialogWalletconnectImport } from './routes/_dialog.dialog/wallet_connect' import { Route as DialogDialogPersonalsignImport } from './routes/_dialog.dialog/personal_sign' import { Route as DialogDialogExperimentalcreateAccountImport } from './routes/_dialog.dialog/experimental_createAccount' import { Route as DialogDialogExperimentalauthorizeKeyImport } from './routes/_dialog.dialog/experimental_authorizeKey' +import { Route as DialogDialogEthsendTransactionImport } from './routes/_dialog.dialog/eth_sendTransaction' import { Route as DialogDialogEthrequestAccountsImport } from './routes/_dialog.dialog/eth_requestAccounts' import { Route as DialogDialogSplatImport } from './routes/_dialog.dialog/$' @@ -33,6 +35,13 @@ const IndexRoute = IndexImport.update({ getParentRoute: () => rootRoute, } as any) +const DialogDialogWalletsendCallsRoute = + DialogDialogWalletsendCallsImport.update({ + id: '/dialog/wallet_sendCalls', + path: '/dialog/wallet_sendCalls', + getParentRoute: () => DialogRoute, + } as any) + const DialogDialogWalletconnectRoute = DialogDialogWalletconnectImport.update({ id: '/dialog/wallet_connect', path: '/dialog/wallet_connect', @@ -59,6 +68,13 @@ const DialogDialogExperimentalauthorizeKeyRoute = getParentRoute: () => DialogRoute, } as any) +const DialogDialogEthsendTransactionRoute = + DialogDialogEthsendTransactionImport.update({ + id: '/dialog/eth_sendTransaction', + path: '/dialog/eth_sendTransaction', + getParentRoute: () => DialogRoute, + } as any) + const DialogDialogEthrequestAccountsRoute = DialogDialogEthrequestAccountsImport.update({ id: '/dialog/eth_requestAccounts', @@ -104,6 +120,13 @@ declare module '@tanstack/react-router' { preLoaderRoute: typeof DialogDialogEthrequestAccountsImport parentRoute: typeof DialogImport } + '/_dialog/dialog/eth_sendTransaction': { + id: '/_dialog/dialog/eth_sendTransaction' + path: '/dialog/eth_sendTransaction' + fullPath: '/dialog/eth_sendTransaction' + preLoaderRoute: typeof DialogDialogEthsendTransactionImport + parentRoute: typeof DialogImport + } '/_dialog/dialog/experimental_authorizeKey': { id: '/_dialog/dialog/experimental_authorizeKey' path: '/dialog/experimental_authorizeKey' @@ -132,6 +155,13 @@ declare module '@tanstack/react-router' { preLoaderRoute: typeof DialogDialogWalletconnectImport parentRoute: typeof DialogImport } + '/_dialog/dialog/wallet_sendCalls': { + id: '/_dialog/dialog/wallet_sendCalls' + path: '/dialog/wallet_sendCalls' + fullPath: '/dialog/wallet_sendCalls' + preLoaderRoute: typeof DialogDialogWalletsendCallsImport + parentRoute: typeof DialogImport + } } } @@ -140,21 +170,25 @@ declare module '@tanstack/react-router' { interface DialogRouteChildren { DialogDialogSplatRoute: typeof DialogDialogSplatRoute DialogDialogEthrequestAccountsRoute: typeof DialogDialogEthrequestAccountsRoute + DialogDialogEthsendTransactionRoute: typeof DialogDialogEthsendTransactionRoute DialogDialogExperimentalauthorizeKeyRoute: typeof DialogDialogExperimentalauthorizeKeyRoute DialogDialogExperimentalcreateAccountRoute: typeof DialogDialogExperimentalcreateAccountRoute DialogDialogPersonalsignRoute: typeof DialogDialogPersonalsignRoute DialogDialogWalletconnectRoute: typeof DialogDialogWalletconnectRoute + DialogDialogWalletsendCallsRoute: typeof DialogDialogWalletsendCallsRoute } const DialogRouteChildren: DialogRouteChildren = { DialogDialogSplatRoute: DialogDialogSplatRoute, DialogDialogEthrequestAccountsRoute: DialogDialogEthrequestAccountsRoute, + DialogDialogEthsendTransactionRoute: DialogDialogEthsendTransactionRoute, DialogDialogExperimentalauthorizeKeyRoute: DialogDialogExperimentalauthorizeKeyRoute, DialogDialogExperimentalcreateAccountRoute: DialogDialogExperimentalcreateAccountRoute, DialogDialogPersonalsignRoute: DialogDialogPersonalsignRoute, DialogDialogWalletconnectRoute: DialogDialogWalletconnectRoute, + DialogDialogWalletsendCallsRoute: DialogDialogWalletsendCallsRoute, } const DialogRouteWithChildren = @@ -165,10 +199,12 @@ export interface FileRoutesByFullPath { '': typeof DialogRouteWithChildren '/dialog/$': typeof DialogDialogSplatRoute '/dialog/eth_requestAccounts': typeof DialogDialogEthrequestAccountsRoute + '/dialog/eth_sendTransaction': typeof DialogDialogEthsendTransactionRoute '/dialog/experimental_authorizeKey': typeof DialogDialogExperimentalauthorizeKeyRoute '/dialog/experimental_createAccount': typeof DialogDialogExperimentalcreateAccountRoute '/dialog/personal_sign': typeof DialogDialogPersonalsignRoute '/dialog/wallet_connect': typeof DialogDialogWalletconnectRoute + '/dialog/wallet_sendCalls': typeof DialogDialogWalletsendCallsRoute } export interface FileRoutesByTo { @@ -176,10 +212,12 @@ export interface FileRoutesByTo { '': typeof DialogRouteWithChildren '/dialog/$': typeof DialogDialogSplatRoute '/dialog/eth_requestAccounts': typeof DialogDialogEthrequestAccountsRoute + '/dialog/eth_sendTransaction': typeof DialogDialogEthsendTransactionRoute '/dialog/experimental_authorizeKey': typeof DialogDialogExperimentalauthorizeKeyRoute '/dialog/experimental_createAccount': typeof DialogDialogExperimentalcreateAccountRoute '/dialog/personal_sign': typeof DialogDialogPersonalsignRoute '/dialog/wallet_connect': typeof DialogDialogWalletconnectRoute + '/dialog/wallet_sendCalls': typeof DialogDialogWalletsendCallsRoute } export interface FileRoutesById { @@ -188,10 +226,12 @@ export interface FileRoutesById { '/_dialog': typeof DialogRouteWithChildren '/_dialog/dialog/$': typeof DialogDialogSplatRoute '/_dialog/dialog/eth_requestAccounts': typeof DialogDialogEthrequestAccountsRoute + '/_dialog/dialog/eth_sendTransaction': typeof DialogDialogEthsendTransactionRoute '/_dialog/dialog/experimental_authorizeKey': typeof DialogDialogExperimentalauthorizeKeyRoute '/_dialog/dialog/experimental_createAccount': typeof DialogDialogExperimentalcreateAccountRoute '/_dialog/dialog/personal_sign': typeof DialogDialogPersonalsignRoute '/_dialog/dialog/wallet_connect': typeof DialogDialogWalletconnectRoute + '/_dialog/dialog/wallet_sendCalls': typeof DialogDialogWalletsendCallsRoute } export interface FileRouteTypes { @@ -201,30 +241,36 @@ export interface FileRouteTypes { | '' | '/dialog/$' | '/dialog/eth_requestAccounts' + | '/dialog/eth_sendTransaction' | '/dialog/experimental_authorizeKey' | '/dialog/experimental_createAccount' | '/dialog/personal_sign' | '/dialog/wallet_connect' + | '/dialog/wallet_sendCalls' fileRoutesByTo: FileRoutesByTo to: | '/' | '' | '/dialog/$' | '/dialog/eth_requestAccounts' + | '/dialog/eth_sendTransaction' | '/dialog/experimental_authorizeKey' | '/dialog/experimental_createAccount' | '/dialog/personal_sign' | '/dialog/wallet_connect' + | '/dialog/wallet_sendCalls' id: | '__root__' | '/' | '/_dialog' | '/_dialog/dialog/$' | '/_dialog/dialog/eth_requestAccounts' + | '/_dialog/dialog/eth_sendTransaction' | '/_dialog/dialog/experimental_authorizeKey' | '/_dialog/dialog/experimental_createAccount' | '/_dialog/dialog/personal_sign' | '/_dialog/dialog/wallet_connect' + | '/_dialog/dialog/wallet_sendCalls' fileRoutesById: FileRoutesById } @@ -260,10 +306,12 @@ export const routeTree = rootRoute "children": [ "/_dialog/dialog/$", "/_dialog/dialog/eth_requestAccounts", + "/_dialog/dialog/eth_sendTransaction", "/_dialog/dialog/experimental_authorizeKey", "/_dialog/dialog/experimental_createAccount", "/_dialog/dialog/personal_sign", - "/_dialog/dialog/wallet_connect" + "/_dialog/dialog/wallet_connect", + "/_dialog/dialog/wallet_sendCalls" ] }, "/_dialog/dialog/$": { @@ -274,6 +322,10 @@ export const routeTree = rootRoute "filePath": "_dialog.dialog/eth_requestAccounts.tsx", "parent": "/_dialog" }, + "/_dialog/dialog/eth_sendTransaction": { + "filePath": "_dialog.dialog/eth_sendTransaction.tsx", + "parent": "/_dialog" + }, "/_dialog/dialog/experimental_authorizeKey": { "filePath": "_dialog.dialog/experimental_authorizeKey.tsx", "parent": "/_dialog" @@ -289,6 +341,10 @@ export const routeTree = rootRoute "/_dialog/dialog/wallet_connect": { "filePath": "_dialog.dialog/wallet_connect.tsx", "parent": "/_dialog" + }, + "/_dialog/dialog/wallet_sendCalls": { + "filePath": "_dialog.dialog/wallet_sendCalls.tsx", + "parent": "/_dialog" } } } diff --git a/app/src/routes/_dialog.dialog/-components/TransactionRequest.tsx b/app/src/routes/_dialog.dialog/-components/TransactionRequest.tsx new file mode 100644 index 00000000..addfed91 --- /dev/null +++ b/app/src/routes/_dialog.dialog/-components/TransactionRequest.tsx @@ -0,0 +1,191 @@ +import { useMutation, useQuery } from '@tanstack/react-query' +import { cx } from 'cva' +import type { RpcSchema } from 'ox' +import { Delegation } from 'porto' +import { Actions, Hooks } from 'porto/remote' + +import { Button } from '~/components/Button' +import { Layout } from '~/components/Layout' +import { Spinner } from '~/components/Spinner' +import * as Dialog from '~/lib/Dialog' +import { porto } from '~/lib/Porto' +import { ValueFormatter } from '~/utils' +import ArrowDownLeft from '~icons/lucide/arrow-down-left' +import ArrowUpRight from '~icons/lucide/arrow-up-right' +import TriangleAlert from '~icons/lucide/triangle-alert' +import Star from '~icons/ph/star-four-bold' + +export function TransactionRequest(props: TransactionRequest.Props) { + const { calls } = props + + const account = Hooks.useAccount(porto) + const client = Hooks.useClient(porto) + const origin = Dialog.useStore((state) => state.referrer?.origin) + const chainId = + typeof props.chainId === 'number' + ? props.chainId + : Hooks.useChain(porto)?.id + + // TODO + chainId + + const request = Hooks.useRequest(porto) + const respond = useMutation({ + mutationFn() { + return Actions.respond(porto, request!) + }, + }) + + const simulate = useQuery({ + queryKey: ['simulate', client.uid, calls], + queryFn: async () => { + const { balances, results } = await Delegation.simulate(client, { + account: account!.address!, + calls: calls as any, + }) + const failure = results.find((x) => x.status === 'failure') + if (failure) throw failure.error + return { balances, results } + }, + }) + const balances = + simulate.data?.balances.filter((x) => x.value.diff !== 0n) ?? [] + + return ( + + + Review the action to perform below.} + variant={simulate.status === 'error' ? 'destructive' : 'default'} + /> + + + + {simulate.status === 'pending' && ( +
+
+ +
+
+ )} + + {simulate.status === 'success' && ( +
+
+ {balances.map((balance) => { + const { token, value } = balance + if (value.diff === BigInt(0)) return null + + const { decimals, symbol } = token + + const receiving = value.diff > BigInt(0) + const formatted = ValueFormatter.format(value.diff, decimals) + + const Icon = receiving ? ArrowDownLeft : ArrowUpRight + + return ( +
+
+ +
+
+ {receiving ? 'Receive' : 'Send'}{' '} + + {formatted} + {' '} + {symbol} +
+
+ ) + })} +
+ + {/*
+ +
+
+ Fees + TODO +
+
*/} +
+ )} + + {simulate.status === 'error' && ( +
+
Error
+
+ An error occurred while simulating the action. Contact{' '} + {origin?.hostname} for more + information. +
+
+ )} + + + + {simulate.status === 'success' && ( + + + + + + )} + + {simulate.status === 'error' && ( + + + + )} + + + + ) +} + +export namespace TransactionRequest { + export type Props = { + calls: RpcSchema.ExtractParams< + RpcSchema.Wallet, + 'wallet_sendCalls' + >[0]['calls'] + chainId?: number | undefined + } +} diff --git a/app/src/routes/_dialog.dialog/eth_sendTransaction.tsx b/app/src/routes/_dialog.dialog/eth_sendTransaction.tsx new file mode 100644 index 00000000..88ca8718 --- /dev/null +++ b/app/src/routes/_dialog.dialog/eth_sendTransaction.tsx @@ -0,0 +1,26 @@ +import { createFileRoute } from '@tanstack/react-router' +import { Hex, type RpcSchema } from 'ox' +import type { RpcSchema as porto_RpcSchema } from 'porto' + +import { TransactionRequest } from './-components/TransactionRequest' + +export const Route = createFileRoute('/_dialog/dialog/eth_sendTransaction')({ + component: RouteComponent, + validateSearch( + search, + ): RpcSchema.ExtractParams { + return search as never + }, +}) + +function RouteComponent() { + const { 0: parameters } = Route.useSearch() ?? {} + const { chainId, data, to, value } = parameters + + return ( + + ) +} diff --git a/app/src/routes/_dialog.dialog/wallet_sendCalls.tsx b/app/src/routes/_dialog.dialog/wallet_sendCalls.tsx new file mode 100644 index 00000000..36582039 --- /dev/null +++ b/app/src/routes/_dialog.dialog/wallet_sendCalls.tsx @@ -0,0 +1,26 @@ +import { createFileRoute } from '@tanstack/react-router' +import { Hex, type RpcSchema } from 'ox' +import type { RpcSchema as porto_RpcSchema } from 'porto' + +import { TransactionRequest } from './-components/TransactionRequest' + +export const Route = createFileRoute('/_dialog/dialog/wallet_sendCalls')({ + component: RouteComponent, + validateSearch( + search, + ): RpcSchema.ExtractParams { + return search as never + }, +}) + +function RouteComponent() { + const { 0: parameters } = Route.useSearch() ?? {} + const { calls, chainId } = parameters + + return ( + + ) +} diff --git a/playground/src/App.tsx b/playground/src/App.tsx index 34119aa4..9e85fbe5 100644 --- a/playground/src/App.tsx +++ b/playground/src/App.tsx @@ -473,7 +473,7 @@ function SendCalls() { }, ] - if (action === 'approve-transfer') + if (action === 'transfer') return [ { to: ExperimentERC20.address, @@ -495,6 +495,50 @@ function SendCalls() { }, ] as const + if (action === 'mint-transfer') + return [ + { + to: '0x390dd40042a844f92b499069cfe983236d9fe204', + data: AbiFunction.encodeData( + AbiFunction.fromAbi(ExperimentERC20.abi, 'mint'), + [account, Value.fromEther('100')], + ), + }, + { + to: ExperimentERC20.address, + data: AbiFunction.encodeData( + AbiFunction.fromAbi(ExperimentERC20.abi, 'approve'), + [account, Value.fromEther('50')], + ), + }, + { + to: ExperimentERC20.address, + data: AbiFunction.encodeData( + AbiFunction.fromAbi(ExperimentERC20.abi, 'transferFrom'), + [ + account, + '0x0000000000000000000000000000000000000000', + Value.fromEther('50'), + ], + ), + }, + ] as const + + if (action === 'revert') + return [ + { + to: '0x390dd40042a844f92b499069cfe983236d9fe204', + data: AbiFunction.encodeData( + AbiFunction.fromAbi(ExperimentERC20.abi, 'transferFrom'), + [ + '0x0000000000000000000000000000000000000000', + account, + Value.fromEther('100'), + ], + ), + }, + ] as const + return [ { to: '0x0000000000000000000000000000000000000000', @@ -524,7 +568,9 @@ function SendCalls() {
diff --git a/playground/src/contracts.ts b/playground/src/contracts.ts index a194c640..3fc6930f 100644 --- a/playground/src/contracts.ts +++ b/playground/src/contracts.ts @@ -185,5 +185,5 @@ export const ExperimentERC20 = { { type: 'error', name: 'PermitExpired', inputs: [] }, { type: 'error', name: 'TotalSupplyOverflow', inputs: [] }, ], - address: '0x238c8CD93ee9F8c7Edf395548eF60c0d2e46665E', + address: '0x706aa5c8e5cc2c67da21ee220718f6f6b154e75c', } as const diff --git a/src/core/Delegation.test.ts b/src/core/Delegation.test.ts index dc586f15..e7e60287 100644 --- a/src/core/Delegation.test.ts +++ b/src/core/Delegation.test.ts @@ -855,7 +855,7 @@ describe('simulate', () => { { "token": { "address": "0x706aa5c8e5cc2c67da21ee220718f6f6b154e75c", - "decimals": 18n, + "decimals": 18, "symbol": "EXP", }, "value": { diff --git a/src/core/Delegation.ts b/src/core/Delegation.ts index 0c4ef3ed..aafddf7b 100644 --- a/src/core/Delegation.ts +++ b/src/core/Delegation.ts @@ -672,7 +672,7 @@ export async function simulate< throw new BaseError('invalid decimals or symbol') return { address: erc20Addresses[i - 1]! as Address.Address, - decimals: decimals_, + decimals: Number(decimals_), symbol: symbol_, } })() diff --git a/src/core/Porto.ts b/src/core/Porto.ts index 2925554f..6cf68996 100644 --- a/src/core/Porto.ts +++ b/src/core/Porto.ts @@ -194,6 +194,8 @@ export type Store< [['zustand/subscribeWithSelector', never], ['zustand/persist', any]] > +const clientCache = new Map() + /** * Extracts a Viem Client from a Porto instance, and an optional chain ID. * By default, the Client for the current chain ID will be extracted. @@ -238,7 +240,8 @@ export function getClient< default_ = transport } - return createClient({ + if (clientCache.has(chain.id)) return clientCache.get(chain.id)! + const client = createClient({ chain, transport: relay ? fallback([ @@ -250,6 +253,8 @@ export function getClient< : default_, pollingInterval: 1_000, }) + clientCache.set(chain.id, client) + return client } export type Client = viem_Client< diff --git a/src/core/RpcSchema.ts b/src/core/RpcSchema.ts index cd9f3380..4dae1cb2 100644 --- a/src/core/RpcSchema.ts +++ b/src/core/RpcSchema.ts @@ -1,9 +1,10 @@ import type * as RpcSchema from 'ox/RpcSchema' +import type * as Key from './internal/key.js' import type * as internal from './internal/rpcSchema.js' export type Schema = RpcSchema.From< - | RpcSchema.Default + | Exclude | { Request: { method: 'porto_ping' @@ -58,4 +59,25 @@ export type Schema = RpcSchema.From< } ReturnType: undefined } + | { + Request: { + method: 'wallet_sendCalls' + params: [ + Omit< + RpcSchema.ExtractParams[0], + 'capabilities' + > & { + capabilities?: + | { + key?: { publicKey: Key.Rpc['publicKey'] } | undefined + } + | undefined + }, + ] + } + ReturnType: RpcSchema.ExtractReturnType< + RpcSchema.Wallet, + 'wallet_sendCalls' + > + } > diff --git a/src/core/internal/provider.ts b/src/core/internal/provider.ts index e9d67c72..9821263e 100644 --- a/src/core/internal/provider.ts +++ b/src/core/internal/provider.ts @@ -10,7 +10,7 @@ import * as Porto from '../Porto.js' import type * as Schema from '../RpcSchema.js' import type * as Call from './call.js' import * as Key from './key.js' -import type * as RpcSchema_internal from './rpcSchema.js' +import type * as Schema_internal from './rpcSchema.js' export type Provider = ox_Provider.Provider<{ includeEvents: true @@ -660,7 +660,7 @@ function requireParameter( } function assertKeys( - keys: readonly RpcSchema_internal.AuthorizeKeyParameters[] | undefined, + keys: readonly Schema_internal.AuthorizeKeyParameters[] | undefined, ) { if (!keys) return for (const key of keys) { diff --git a/src/remote/Hooks.ts b/src/remote/Hooks.ts index 68cc78a5..01bfb1bc 100644 --- a/src/remote/Hooks.ts +++ b/src/remote/Hooks.ts @@ -2,9 +2,50 @@ import { useStore } from 'zustand' import { useShallow } from 'zustand/shallow' import type * as Chains from '../core/Chains.js' -import type * as Porto from '../core/Porto.js' +import * as Porto from '../core/Porto.js' import type * as Remote from './Porto.js' +/** + * Hook to access and subscribe to the current account. + * + * @param porto - Porto instance. + * @returns Account. + */ +export function useAccount(porto: Pick, '_internal'>) { + return usePortoStore(porto, (x) => x.accounts[0]) +} + +/** + * Hook to access and subscribe to the current accounts. + * + * @param porto - Porto instance. + * @returns Accounts. + */ +export function useAccounts(porto: Pick, '_internal'>) { + return usePortoStore(porto, (x) => x.accounts) +} + +/** + * Hook to access and subscribe to the current chain. + * + * @param porto - Porto instance. + * @returns Chain. + */ +export function useChain(porto: Pick, '_internal'>) { + return usePortoStore(porto, (x) => x.chain) +} + +/** + * Hook to access and subscribe to the client of the Porto instance. + * + * @param porto - Porto instance. + * @returns Client. + */ +export function useClient(porto: Pick, '_internal'>) { + const chain = useChain(porto) + return Porto.getClient(porto, { chainId: chain.id }) +} + /** * Hook to access and subscribe to the store of the Porto instance. * diff --git a/src/remote/Porto.ts b/src/remote/Porto.ts index b18a0a39..8461b02c 100644 --- a/src/remote/Porto.ts +++ b/src/remote/Porto.ts @@ -5,7 +5,7 @@ import type * as Chains from '../core/Chains.js' import * as Implementation from '../core/Implementation.js' import * as Messenger from '../core/Messenger.js' import * as Porto_ from '../core/Porto.js' -import type { Schema } from '../core/RpcSchema.js' +import type * as RpcSchema from '../core/RpcSchema.js' import * as Storage from '../core/Storage.js' import type { ExactPartial } from '../core/internal/types.js' @@ -41,7 +41,7 @@ export type State< export type RemoteState = { requests: readonly (Porto_.QueuedRequest & { - request: RpcRequest.RpcRequest + request: RpcRequest.RpcRequest })[] }