Skip to content
Open
Show file tree
Hide file tree
Changes from 13 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
28 changes: 28 additions & 0 deletions apps/cowswap-e2e-tests/src/support/mockBridgeSupportedTokens.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import type { BrowserContext } from '@playwright/test'

export interface MockedBridgeToken {
address: string
symbol: string
name: string
decimals: number
chainId: number
}

/**
* Stubs the Bungee/Socket bridge provider's `/dest-tokens` endpoint (`BungeeApi.getBuyTokens` in
* `@cowprotocol/sdk-bridging`), which both `useBridgeSupportedTokens` (resolving/listing buyable
* tokens on a target chain) and `useRoutesAvailability` (is this destination chain reachable at
* all) call under the hood — mocking this one REST call satisfies both, since Bungee is the only
* enabled provider (`bridgingSdk.setAvailableProviders([bungeeBridgeProvider.info.dappId])`).
* Response shape: `{ success: true, result: TokenInfo[] }`, where the SDK maps each entry's
* `logoURI` to `logoUrl` and otherwise passes it through as-is.
*/
export function mockBridgeSupportedTokens(context: BrowserContext, tokens: MockedBridgeToken[]): void {
void context.route(/bungee-manual\/dest-tokens/i, async (route) => {
await route.fulfill({
status: 200,
contentType: 'application/json',
body: JSON.stringify({ success: true, result: tokens }),
})
})
}
24 changes: 24 additions & 0 deletions apps/cowswap-e2e-tests/src/support/mockHookLogo.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
import path from 'path'

import type { BrowserContext, Route } from '@playwright/test'

const BUILD_CUSTOM_HOOK_LOGO_PATH = path.resolve(
__dirname,
'../../../cowswap-frontend/src/modules/hooksStore/dapps/BuildHookApp/build.png',
)

/**
* Stubs `hookDappsRegistry.ts`'s `BUILD_CUSTOM_HOOK.image` — a `raw.githubusercontent.com` URL with no
* test-side mock and no frontend-side `onError` fallback (`HookItem` just renders `<img src={...} />`
* with nothing to show if the request fails). Any hiccup reaching GitHub from the test runner renders a
* bare placeholder box instead of the hook's hard-hat icon. Fulfilling from the same `build.png` already
* checked into the frontend source removes that live network dependency entirely.
*/
export function mockHookLogo(context: BrowserContext): void {
void context.route(
/raw\.githubusercontent\.com\/cowprotocol\/cowswap\/.*\/BuildHookApp\/build\.png/i,
async (route: Route) => {
await route.fulfill({ status: 200, contentType: 'image/png', path: BUILD_CUSTOM_HOOK_LOGO_PATH })
},
)
}
25 changes: 25 additions & 0 deletions apps/cowswap-e2e-tests/src/support/mockHooksSimulation.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import type { BrowserContext, Route } from '@playwright/test'

/**
* Stubs the Tenderly bundle-simulation endpoint (`bundleSimulation.ts`'s `simulateBundle`, hit at
* `{BFF_BASE_URL}/{chainId}/simulation/simulateBundle`) that `useTenderlyBundleSimulation` POSTs to
* once the trade-confirmation screen mounts with at least one hook attached. Real endpoint, never
* mocked before this — `HookItem` renders "Simulation successful"/"Simulation failed" straight off
* each response entry's `status` boolean, positionally matched to the posted pre/post hooks.
*/
export function mockHooksSimulation(context: BrowserContext, opts: { status?: boolean } = {}): void {
const status = opts.status ?? true

void context.route(/bff\.(?:barn\.)?cow\.fi\/\d+\/simulation\/simulateBundle/i, async (route: Route) => {
const postedHooks = JSON.parse(route.request().postData() || '[]') as unknown[]
const body = postedHooks.map((_, index) => ({
link: `https://dashboard.tenderly.co/mock-simulation-${index}`,
status,
id: `mock-simulation-${index}`,
cumulativeBalancesDiff: {},
stateDiff: [],
gasUsed: '21000',
}))
await route.fulfill({ status: 200, contentType: 'application/json', body: JSON.stringify(body) })
})
}
39 changes: 39 additions & 0 deletions apps/cowswap-e2e-tests/src/support/mockTokenLogos.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
import type { BrowserContext, Route } from '@playwright/test'

// This suite's Sepolia test-token deployments (`WETH`/`USDC` in `market-orders.spec.ts`) aren't on
// any token list, so every URL `useTokenLogoUrl` tries — keyed off these same addresses on every
// chain it checks — 403s against the real CDN (verified directly). Redirecting to each token's real
// mainnet counterpart resolves to the actual brand icon instead of a broken image or a letter avatar.
const REAL_MAINNET_ADDRESS: Record<string, string> = {
'0xfff9976782d46cc05630d1f6ebab18b2324d6b14': '0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2', // WETH
'0xbe72e441bf55620febc26715db68d3494213d8cb': '0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48', // USDC
}
Comment thread
coderabbitai[bot] marked this conversation as resolved.

const LOGO_PATH_RE = /\/token-lists\/images\/\d+\/(0x[a-fA-F0-9]{40})\/logo\.png$/i

/**
* Stubs `cowprotocolTokenLogoUrl`'s CDN endpoint (`files.cow.fi/token-lists/images/:chainId/:address/logo.png`)
* for this suite's test-token addresses, redirecting each to its real mainnet counterpart's logo
* (same technique as `route.fetch()`'s upstream-merge helpers elsewhere in this folder, just fetching
* a different URL instead of the same one). Anything not in `REAL_MAINNET_ADDRESS` falls back to a
* plain 404, matching the real CDN's own behavior for an unlisted token — that keeps `TokenLogo`'s
* `onError` fallback (`SingleLetterLogo`) intact rather than masking it with a fake "successful" image.
*/
export function mockTokenLogos(context: BrowserContext): void {
void context.route(/files\.cow\.fi\/token-lists\/images\//i, async (route: Route) => {
const match = new URL(route.request().url()).pathname.match(LOGO_PATH_RE)
const realAddress = match && REAL_MAINNET_ADDRESS[match[1].toLowerCase()]

if (!realAddress) {
await route.fulfill({ status: 404 })
return
}

try {
const response = await route.fetch({ url: `https://files.cow.fi/token-lists/images/1/${realAddress}/logo.png` })
await route.fulfill({ response })
} catch {
await route.fulfill({ status: 404 })
}
})
}
Loading
Loading