Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/dry-wasps-love.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"thirdweb": patch
---

More reliable list of chains shown in token selection UI in SwapWidget based on origin and destination chain selections
49 changes: 46 additions & 3 deletions packages/thirdweb/src/bridge/Chains.ts
Original file line number Diff line number Diff line change
Expand Up @@ -54,12 +54,30 @@
*/
export async function chains(options: chains.Options): Promise<chains.Result> {
const { client } = options;

return withCache(
async () => {
const clientFetch = getClientFetch(client);
const url = new URL(`${getThirdwebBaseUrl("bridge")}/v1/chains`);

if (options.testnet) {
url.searchParams.set("testnet", options.testnet.toString());
}

Check warning on line 64 in packages/thirdweb/src/bridge/Chains.ts

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/bridge/Chains.ts#L63-L64

Added lines #L63 - L64 were not covered by tests

// set type or originChainId or destinationChainId
if ("type" in options && options.type) {
url.searchParams.set("type", options.type);

Check warning on line 68 in packages/thirdweb/src/bridge/Chains.ts

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/bridge/Chains.ts#L68

Added line #L68 was not covered by tests
} else if ("originChainId" in options && options.originChainId) {
url.searchParams.set("originChainId", options.originChainId.toString());
} else if (

Check warning on line 71 in packages/thirdweb/src/bridge/Chains.ts

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/bridge/Chains.ts#L70-L71

Added lines #L70 - L71 were not covered by tests
"destinationChainId" in options &&
options.destinationChainId

Check warning on line 73 in packages/thirdweb/src/bridge/Chains.ts

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/bridge/Chains.ts#L73

Added line #L73 was not covered by tests
) {
url.searchParams.set(
"destinationChainId",
options.destinationChainId.toString(),
);
}

Check warning on line 79 in packages/thirdweb/src/bridge/Chains.ts

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/bridge/Chains.ts#L75-L79

Added lines #L75 - L79 were not covered by tests

const response = await clientFetch(url.toString());
if (!response.ok) {
const errorJson = await response.json();
Expand All @@ -75,7 +93,7 @@
return data;
},
{
cacheKey: "bridge-chains",
cacheKey: `bridge-chains-${JSON.stringify(options)}`,
cacheTime: 1000 * 60 * 60 * 1, // 1 hours
},
);
Expand All @@ -95,7 +113,32 @@
type Options = {
/** Your thirdweb client */
client: ThirdwebClient;
};

/**
* If true, returns only testnet chains. Defaults to false.
*/
testnet?: boolean;
} & (
| {
/**
* setting type=origin: Returns all chains that can be used as origin,
* setting type=destination: Returns all chains that can be used as destination
*/
type?: "origin" | "destination";
}
| {
/**
* setting originChainId=X: Returns destination chains reachable from chain X
*/
originChainId?: number;
}
| {
/**
* setting destinationChainId=X: Returns origin chains reachable from chain X
*/
destinationChainId?: number;
}
);

/**
* Result returned from fetching supported bridge chains.
Expand Down
17 changes: 11 additions & 6 deletions packages/thirdweb/src/react/web/ui/Bridge/FundWallet.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@
import { useActiveWalletInfo } from "./swap-widget/hooks.js";
import { SelectToken } from "./swap-widget/select-token-ui.js";
import type { ActiveWalletInfo } from "./swap-widget/types.js";
import { useBridgeChains } from "./swap-widget/use-bridge-chains.js";
import { useBridgeChain } from "./swap-widget/use-bridge-chains.js";

type FundWalletProps = {
/**
Expand Down Expand Up @@ -211,6 +211,11 @@
autoFocusCrossIcon={false}
>
<SelectToken
type="buy"
selections={{
buyChainId: props.selectedToken?.chainId,
sellChainId: undefined,
}}

Check warning on line 218 in packages/thirdweb/src/react/web/ui/Bridge/FundWallet.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/FundWallet.tsx#L214-L218

Added lines #L214 - L218 were not covered by tests
activeWalletInfo={activeWalletInfo}
onClose={() => setIsTokenSelectionOpen(false)}
client={props.client}
Expand Down Expand Up @@ -403,11 +408,11 @@
presetOptions: [number, number, number];
}) {
const theme = useCustomTheme();
const chainQuery = useBridgeChains(props.client);
const chain = chainQuery.data?.find(
(chain) => chain.chainId === props.selectedToken?.data?.chainId,
);

const chainQuery = useBridgeChain({
chainId: props.selectedToken?.data?.chainId,
client: props.client,
});
const chain = chainQuery.data;

Check warning on line 415 in packages/thirdweb/src/react/web/ui/Bridge/FundWallet.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/FundWallet.tsx#L411-L415

Added lines #L411 - L415 were not covered by tests
const fiatPricePerToken = props.selectedToken?.data?.prices[props.currency];

const { fiatValue, tokenValue } = getAmounts(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -366,7 +366,7 @@ function SwapWidgetContent(
}, [buyToken, sellToken, isPersistEnabled]);

// preload requests
useBridgeChains(props.client);
useBridgeChains({ client: props.client });

// if wallet suddenly disconnects, show screen 1
if (screen.id === "1:swap-ui" || !activeWalletInfo) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
import { Spacer } from "../../components/Spacer.js";
import { Text } from "../../components/text.js";
import { SearchInput } from "./SearchInput.js";
import { useBridgeChains } from "./use-bridge-chains.js";
import { useBridgeChainsWithFilters } from "./use-bridge-chains.js";
import { cleanedChainName } from "./utils.js";

type SelectBuyTokenProps = {
Expand All @@ -24,13 +24,23 @@
onSelectChain: (chain: BridgeChain) => void;
selectedChain: BridgeChain | undefined;
isMobile: boolean;
type: "buy" | "sell";
selections: {
buyChainId: number | undefined;
sellChainId: number | undefined;
};
};

/**
* @internal
*/
export function SelectBridgeChain(props: SelectBuyTokenProps) {
const chainQuery = useBridgeChains(props.client);
const chainQuery = useBridgeChainsWithFilters({
client: props.client,
type: props.type,
buyChainId: props.selections.buyChainId,
sellChainId: props.selections.sellChainId,
});

Check warning on line 43 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx#L38-L43

Added lines #L38 - L43 were not covered by tests

return (
<SelectBridgeChainUI
Expand Down Expand Up @@ -126,7 +136,7 @@
{props.isPending &&
new Array(20).fill(0).map(() => (
// biome-ignore lint/correctness/useJsxKeyInIterable: ok
<ChainButtonSkeleton />
<ChainButtonSkeleton isMobile={props.isMobile} />

Check warning on line 139 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx#L139

Added line #L139 was not covered by tests
))}

{filteredChains.length === 0 && !props.isPending && (
Expand All @@ -148,18 +158,24 @@
);
}

function ChainButtonSkeleton() {
function ChainButtonSkeleton(props: { isMobile: boolean }) {
const iconSizeValue = props.isMobile ? iconSize.lg : iconSize.md;

Check warning on line 162 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx#L161-L162

Added lines #L161 - L162 were not covered by tests
return (
<div
style={{
display: "flex",
alignItems: "center",
gap: spacing.sm,
padding: `${spacing.sm} ${spacing.sm}`,
padding: props.isMobile
? `${spacing.sm} ${spacing.sm}`
: `${spacing.xs} ${spacing.xs}`,

Check warning on line 171 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx#L169-L171

Added lines #L169 - L171 were not covered by tests
}}
>
<Skeleton height={`${iconSize.lg}px`} width={`${iconSize.lg}px`} />
<Skeleton height={fontSize.md} width="160px" />
<Skeleton height={`${iconSizeValue}px`} width={`${iconSizeValue}px`} />
<Skeleton
height={props.isMobile ? fontSize.md : fontSize.sm}
width="160px"
/>

Check warning on line 178 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-chain.tsx#L174-L178

Added lines #L174 - L178 were not covered by tests
</div>
);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@
import { SelectChainButton } from "./SelectChainButton.js";
import { SelectBridgeChain } from "./select-chain.js";
import type { ActiveWalletInfo, TokenSelection } from "./types.js";
import { useBridgeChains } from "./use-bridge-chains.js";
import { useBridgeChainsWithFilters } from "./use-bridge-chains.js";
import {
type TokenBalance,
useTokenBalances,
Expand All @@ -43,6 +43,11 @@
selectedToken: TokenSelection | undefined;
setSelectedToken: (token: TokenSelection) => void;
activeWalletInfo: ActiveWalletInfo | undefined;
type: "buy" | "sell";
selections: {
buyChainId: number | undefined;
sellChainId: number | undefined;
};
};

function findChain(chains: BridgeChain[], activeChainId: number | undefined) {
Expand All @@ -58,7 +63,13 @@
* @internal
*/
export function SelectToken(props: SelectTokenUIProps) {
const chainQuery = useBridgeChains(props.client);
const chainQuery = useBridgeChainsWithFilters({
client: props.client,
type: props.type,
buyChainId: props.selections.buyChainId,
sellChainId: props.selections.sellChainId,
});

Check warning on line 71 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx#L66-L71

Added lines #L66 - L71 were not covered by tests

const [search, _setSearch] = useState("");
const debouncedSearch = useDebouncedValue(search, 500);
const [limit, setLimit] = useState(INITIAL_LIMIT);
Expand Down Expand Up @@ -146,6 +157,11 @@
selectedToken: TokenSelection | undefined;
setSelectedToken: (token: TokenSelection) => void;
showMore: (() => void) | undefined;
type: "buy" | "sell";
selections: {
buyChainId: number | undefined;
sellChainId: number | undefined;
};
},
) {
const isMobile = useIsMobile();
Expand Down Expand Up @@ -203,6 +219,8 @@
>
<LeftContainer>
<SelectBridgeChain
type={props.type}
selections={props.selections}

Check warning on line 223 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx#L222-L223

Added lines #L222 - L223 were not covered by tests
onBack={() => setScreen("select-token")}
client={props.client}
isMobile={false}
Expand Down Expand Up @@ -269,6 +287,8 @@
setScreen("select-token");
}}
selectedChain={props.selectedChain}
type={props.type}
selections={props.selections}

Check warning on line 291 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx#L290-L291

Added lines #L290 - L291 were not covered by tests
/>
);
}
Expand Down Expand Up @@ -467,16 +487,16 @@
</Container>

{!props.selectedChain && (
<div
<Container
flex="column"
center="both"
expand

Check warning on line 493 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx#L490-L493

Added lines #L490 - L493 were not covered by tests
style={{
display: "flex",
alignItems: "center",
justifyContent: "center",
minHeight: "300px",
}}
>
<Spinner color="secondaryText" size="xl" />
</div>
</Container>

Check warning on line 499 in packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx

View check run for this annotation

Codecov / codecov/patch

packages/thirdweb/src/react/web/ui/Bridge/swap-widget/select-token-ui.tsx#L499

Added line #L499 was not covered by tests
)}

{props.selectedChain && (
Expand Down
Loading
Loading