Skip to content
Merged
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
22 changes: 15 additions & 7 deletions src/components/crosschain/IntentForm.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,10 @@ import {
DEFAULT_TESTNET_CHAIN_ID_STR,
isSupportedTestnetEvmChain,
} from "../../constants/chains";
import { getMidenFaucetDecimals } from "../../constants/miden-tokens";
import {
getMidenFaucetDecimals,
isPragmaSupportedMidenAsset,
} from "../../constants/miden-tokens";
import { EPOCH_TESTNET_TOKENS } from "../../constants/evm-tokens";
import { midenscanNoteUrl } from "../../lib/explorers";
import {
Expand Down Expand Up @@ -62,13 +65,18 @@ export function IntentForm({
const { address } = useAccount();
const walletChainId = useChainId();

const supportedMidenAssets = midenAssets.filter((asset) =>
isPragmaSupportedMidenAsset(asset, network),
);
const unsupportedAssetCount =
midenAssets.length - supportedMidenAssets.length;
const [selectedAssetId, setSelectedAssetId] = useState("");
const selectedAssetIdIsAvailable = midenAssets.some(
const selectedAssetIdIsAvailable = supportedMidenAssets.some(
(asset) => asset.assetId === selectedAssetId,
);
const resolvedSelectedAssetId = selectedAssetIdIsAvailable
? selectedAssetId
: (midenAssets[0]?.assetId ?? "");
: (supportedMidenAssets[0]?.assetId ?? "");

// Follows the connected wallet until the user overrides a field. Not
// useState defaults: the wallet connects after this mounts.
Expand Down Expand Up @@ -106,13 +114,12 @@ export function IntentForm({
destination.evmAddress.trim(),
);

const selectedAsset = midenAssets.find(
const selectedAsset = supportedMidenAssets.find(
(a) => a.assetId.toLowerCase() === resolvedSelectedAssetId.toLowerCase(),
);
// Use the hardcoded faucet→decimals map only for display formatting. Do not
// fall back to the wallet adapter's reported decimals (often defaults to 8
// and silently mis-scales). Unknown faucets remain selectable and display
// their quoted amount in raw units.
// and silently mis-scales).
const midenFaucetDecimals = resolvedSelectedAssetId
? getMidenFaucetDecimals(resolvedSelectedAssetId, network)
: undefined;
Expand Down Expand Up @@ -231,10 +238,11 @@ export function IntentForm({

<div className="mt-4 space-y-4">
<IntentSourceAssetField
assets={midenAssets ?? []}
assets={supportedMidenAssets}
selectedAssetId={resolvedSelectedAssetId}
selectedAsset={selectedAsset}
isLoadingAssets={isLoadingMidenAssets}
unsupportedAssetCount={unsupportedAssetCount}
onSelect={(assetId) => {
setSelectedAssetId(assetId);
onClearQuote();
Expand Down
20 changes: 18 additions & 2 deletions src/components/crosschain/intent/IntentSourceAssetField.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ interface Props {
selectedAssetId: string;
selectedAsset?: MidenAssetOption;
isLoadingAssets: boolean;
unsupportedAssetCount: number;
onSelect: (assetId: string) => void;
}

Expand All @@ -21,6 +22,7 @@ export function IntentSourceAssetField({
selectedAssetId,
selectedAsset,
isLoadingAssets,
unsupportedAssetCount,
onSelect,
}: Props) {
return (
Expand All @@ -46,9 +48,23 @@ export function IntentSourceAssetField({
{selectedAsset?.amount?.toString() ?? "—"}
</span>
</p>
{!isLoadingAssets && assets.length === 0 && (
{!isLoadingAssets &&
assets.length === 0 &&
unsupportedAssetCount === 0 && (
<p className="text-xs text-amber-800">
No Miden assets found in this wallet. Fund it before bridging.
</p>
)}
{!isLoadingAssets && assets.length === 0 && unsupportedAssetCount > 0 && (
<p className="text-xs text-amber-800">
No Miden assets found in this wallet. Fund it before bridging.
No Pragma-priced assets found. This bridge supports USDC, USDT, DAI,
WETH, and WBTC.
</p>
)}
{!isLoadingAssets && assets.length > 0 && unsupportedAssetCount > 0 && (
<p className="text-xs text-neutral-500">
{unsupportedAssetCount} unsupported wallet
{unsupportedAssetCount === 1 ? " asset is" : " assets are"} hidden.
</p>
)}
</div>
Expand Down
21 changes: 21 additions & 0 deletions src/constants/miden-tokens.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,14 @@
import { normalizeMidenIdToHex } from "../services/epoch-bridge";
import type { MidenNetwork } from "../config/miden";

const PRAGMA_SUPPORTED_MIDEN_SYMBOLS = new Set([
"USDC",
"USDT",
"DAI",
"WETH",
"WBTC",
]);

/**
* Hardcoded Miden testnet faucet → decimals map.
*
Expand Down Expand Up @@ -41,3 +49,16 @@ export function getMidenFaucetDecimals(
return undefined;
}
}

/** Returns whether the solver has a Pragma price feed for this wallet asset. */
export function isPragmaSupportedMidenAsset(
asset: { assetId: string; symbol?: string },
network: MidenNetwork,
): boolean {
const symbol = asset.symbol?.trim().toUpperCase();
if (symbol && PRAGMA_SUPPORTED_MIDEN_SYMBOLS.has(symbol)) return true;

// Metadata can arrive after the wallet asset list. Keep known testnet faucets
// available while their symbol is still loading.
return getMidenFaucetDecimals(asset.assetId, network) !== undefined;
}
Loading