Skip to content

Commit

Permalink
First trading sell test for BTC (#16889)
Browse files Browse the repository at this point in the history
* feat(e2e): Introduce a draft of trading sell test + rafactoring

refactors shared methods between sell and buy
adds more verifications of request payloads
simplifies the creation of Trade response

* feat(e2e): Extends sell flow till the send

new passphrase wallet for trading tests
few new locators
new .env file for tests
removes traces from CI

* fix(e2e): PR improvements and fixes

* fix(e2e): Minor fixes and improvements on PR
  • Loading branch information
Vere-Grey authored Feb 7, 2025
1 parent 8a6cb64 commit f5bc4a6
Show file tree
Hide file tree
Showing 31 changed files with 520 additions and 109 deletions.
7 changes: 0 additions & 7 deletions .github/workflows/test-suite-desktop-e2e.yml
Original file line number Diff line number Diff line change
Expand Up @@ -120,10 +120,3 @@ jobs:
COMPOSE_FILE: ./docker/docker-compose.suite-desktop-ci.yml
run: docker compose down

- name: Upload Playwright report
if: ${{ ! cancelled() }}
uses: actions/upload-artifact@v4
with:
name: playwright-report-${{ matrix.TEST_GROUP }}
path: ./packages/suite-desktop-core/playwright-report/
retention-days: 30
8 changes: 1 addition & 7 deletions .github/workflows/test-suite-web-e2e-pw.yml
Original file line number Diff line number Diff line change
Expand Up @@ -155,6 +155,7 @@ jobs:
CURRENTS_PROJECT_ID: Og0NOQ
CURRENTS_RECORD_KEY: ${{ secrets.CURRENTS_RECORD_KEY }}
CURRENTS_CI_BUILD_ID: pr-run-${{github.run_id}}
PASSPHRASE: ${{ secrets.E2E_TEST_PASSPHRASE }}
run: |
docker compose up -d ${{ matrix.CONTAINERS }}
echo "Starting Playwright Web test group ${{ matrix.TEST_GROUP }}"
Expand Down Expand Up @@ -185,10 +186,3 @@ jobs:
COMPOSE_FILE: ./docker/docker-compose.suite-ci-pw.yml
run: docker compose down

- name: Upload Playwright report
if: ${{ ! cancelled() }}
uses: actions/upload-artifact@v4
with:
name: playwright-report-${{ matrix.TEST_GROUP }}
path: ./packages/suite-desktop-core/playwright-report/
retention-days: 30
1 change: 1 addition & 0 deletions docs/tests/e2e-playwright-suite.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ Steps:
- ``export HOSTNAME=`hostname` ``
- `export DISPLAY=${HOSTNAME}:0`
1. In terminal window, navigate to `trezor-user-env` repo root and run `./run.sh`.
1. In workspace `packages/suite-desktop-core` create a `.env` file according to the `.example.env`

### Web

Expand Down
3 changes: 3 additions & 0 deletions packages/suite-desktop-core/.example.env
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@

# Secret wallet passphrase dedicated for automated Trading tests
PASSPHRASE=
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
{
"trade": {
"exchange": "banxa",
"fiatCurrency": "CZK",
"receiveCurrency": "solana",
"rate": 6106.42,
"wantCrypto": true,
"exp": "cRPhcsJWUUq9brG+zMXmog==",
"country": "CZ",
"paymentMethodName": "Credit Card",
"tags": ["wantCrypto"],
"fiatStringAmount": "3053.21",
"receiveStringAmount": "0.5",
"minFiat": 600,
"maxFiat": 50000,
"minCrypto": 0.10408553,
"maxCrypto": 8.67379421,
"paymentMethod": "creditCard",
"quoteId": "f9e89339-a0bb-4960-ae8e-cc543d651de3",
"partnerData2": "6098",
"paymentId": "8abad787-6328-46bf-9c65-4d9797008f93",
"orderId": "3e44be68-6827-4fa0-962b-85e1cbcbca2f",
"receiveAddress": "o6AySDQRrUa5Sp6XM9gqLogoibdufvxVyviFvR1PfaP"
},
"returnUrl": "http://localhost:8000/coinmarket-redirect#detail/sol/normal/0/8abad787-6328-46bf-9c65-4d9797008f93"
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"paymentId": "5e895ff7-c444-4371-a41f-c1735edca46c",
"status": "SUBMITTED",
"originalPaymentId": "e17a2bed-86c6-4974-9d87-9fc926b16614",
"partnerData": "",
"partnerData": "https://app.topperpay.com/?bt=eyJhbGciOiJFUzUxMiIsInR5cCI6IkpXVCIsImtpZCI6IjEwZjdkZGE4LTNlOGEtNDcyYi1hM2FhLWQzM2RjOTgwMDM4YyJ9.eyJpYXQiOjE3Mzg3NzU4ODQsImV4cCI6MTczODc3NTk0NCwianRpIjoiNWUxZTFhOGUtM2FiZi00NDRhLTk4YmUtOTAxNzk2OWY3YmY4Iiwic3ViIjoiNTUzNzI3NDgtZDRiZS00MTVmLWI0MDgtZDI2OWFkY2I3OWZlIiwicGFydG5lciI6eyJkaXNwbGF5TmFtZSI6IlRyZXpvciBTdWl0ZSIsImNvbnRpbnVlVXJsIjoiaHR0cDovL2xvY2FsaG9zdDo4MDAwL2NvaW5tYXJrZXQtcmVkaXJlY3QjZGV0YWlsL2J0Yy9ub3JtYWwvMC8zZWRkNTkyYi0wYWM4LTQ3ZGItYmVhMy00ODU2NzQ3NTI4ODMiLCJmZWUiOnsicGVyY2VudGFnZSI6IjEifX0sInNvdXJjZSI6eyJhbW91bnQiOiIxMjM0IiwiYXNzZXQiOiJDWksiLCJwYXltZW50TWV0aG9kIjp7Im5ldHdvcmsiOiJjYXJkIn19LCJ0YXJnZXQiOnsiYWRkcmVzcyI6ImJjMXE3Y2VxdmFxN2ZxeXl3eHFjeDdxbmZ4a2ZrMnlrcHNsYTlwZTgwcSIsImFzc2V0IjoiQlRDIiwibmV0d29yayI6ImJpdGNvaW4iLCJyZWNpcGllbnRFZGl0TW9kZSI6Im5vdC1lZGl0YWJsZSJ9fQ.AYeoeDtYLjZFeACH9-Rjtkd1R7hH5EpdIzSp30baeSLfwm1Val_3HVDLVtUNLsBHFeAx3-kacJxUts6ReX2N5R0-AC2_1lVxOCJhkRvzI5VDujguo-btsgFFBUkhWBlbHkXs5rV_861UOFSprdExrD4TL_r-wro73q7OAwPKsjIK8fPQ&theme=light",
"exchange": "topper",
"fiatCurrency": "CZK",
"receiveCurrency": "bitcoin",
Expand All @@ -26,7 +26,7 @@
"tradeForm": {
"form": {
"formMethod": "GET",
"formAction": "",
"formAction": "https://app.topperpay.com/?bt=eyJhbGciOiJFUzUxMiIsInR5cCI6IkpXVCIsImtpZCI6IjEwZjdkZGE4LTNlOGEtNDcyYi1hM2FhLWQzM2RjOTgwMDM4YyJ9.eyJpYXQiOjE3Mzg3NzU4ODQsImV4cCI6MTczODc3NTk0NCwianRpIjoiNWUxZTFhOGUtM2FiZi00NDRhLTk4YmUtOTAxNzk2OWY3YmY4Iiwic3ViIjoiNTUzNzI3NDgtZDRiZS00MTVmLWI0MDgtZDI2OWFkY2I3OWZlIiwicGFydG5lciI6eyJkaXNwbGF5TmFtZSI6IlRyZXpvciBTdWl0ZSIsImNvbnRpbnVlVXJsIjoiaHR0cDovL2xvY2FsaG9zdDo4MDAwL2NvaW5tYXJrZXQtcmVkaXJlY3QjZGV0YWlsL2J0Yy9ub3JtYWwvMC8zZWRkNTkyYi0wYWM4LTQ3ZGItYmVhMy00ODU2NzQ3NTI4ODMiLCJmZWUiOnsicGVyY2VudGFnZSI6IjEifX0sInNvdXJjZSI6eyJhbW91bnQiOiIxMjM0IiwiYXNzZXQiOiJDWksiLCJwYXltZW50TWV0aG9kIjp7Im5ldHdvcmsiOiJjYXJkIn19LCJ0YXJnZXQiOnsiYWRkcmVzcyI6ImJjMXE3Y2VxdmFxN2ZxeXl3eHFjeDdxbmZ4a2ZrMnlrcHNsYTlwZTgwcSIsImFzc2V0IjoiQlRDIiwibmV0d29yayI6ImJpdGNvaW4iLCJyZWNpcGllbnRFZGl0TW9kZSI6Im5vdC1lZGl0YWJsZSJ9fQ.AYeoeDtYLjZFeACH9-Rjtkd1R7hH5EpdIzSp30baeSLfwm1Val_3HVDLVtUNLsBHFeAx3-kacJxUts6ReX2N5R0-AC2_1lVxOCJhkRvzI5VDujguo-btsgFFBUkhWBlbHkXs5rV_861UOFSprdExrD4TL_r-wro73q7OAwPKsjIK8fPQ&theme=light",
"fields": {}
}
}
Expand Down
71 changes: 57 additions & 14 deletions packages/suite-desktop-core/e2e/fixtures/invity/index.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
import { cloneDeep } from 'lodash';

import { NetworkSymbol } from '@suite-common/wallet-config';

import buyList from './buy/list.json';
import buyQuotesBTC from './buy/quotes-bitcoin.json';
import buyQuotesEthereum from './buy/quotes-ethereum.json';
import buyQuotesSolana from './buy/quotes-solana.json';
import buyTradeBTCPayload from './buy/requests/trade-request-bitcoin.json';
import buyTradeSolanaPayload from './buy/requests/trade-request-solana.json';
import buyWatchPayload from './buy/requests/watch-request.json';
import buyTradeBTC from './buy/trade-bitcoin.json';
import buyTradeEthereum from './buy/trade-ethereum.json';
import buyTradeSolana from './buy/trade-solana.json';
Expand All @@ -17,7 +18,15 @@ import exchangeTrade from './exchange/trade.json';
import exchangeWatch from './exchange/watch.json';
import info from './info.json';
import sellList from './sell/list.json';
import { TradeRequest } from './types';
import sellQuotesBTC from './sell/quotes-bitcoin.json';
//Payloads
import sellQuotesPayload from './sell/requests/quotes-request.json';
import sellTradePayload from './sell/requests/trade-request.json';
import sellWatchPayload from './sell/requests/watch-request.json';
import sellTradeBTC from './sell/trade-bitcoin.json';
import sellWatch from './sell/watch.json';
//Types
import { SellTradeResponse, TradeResponse } from './types';

const invityUrl = 'https://exchange.trezor.io';

Expand All @@ -33,6 +42,18 @@ export const invityEndpoint = {
buyTrade: `${invityUrl}/api/v3/buy/trade`,
buyWatch: `${invityUrl}/api/v3/buy/watch/*`,
sellList: `${invityUrl}/api/v3/sell/list`,
sellQuotes: `${invityUrl}/api/v3/sell/fiat/quotes`,
sellTrade: `${invityUrl}/api/v3/sell/fiat/trade`,
sellWatch: `${invityUrl}/api/v3/sell/fiat/watch/*`,
};

export const invityRequest = {
buyTradeBTCPayload,
buyTradeSolanaPayload,
buyWatchPayload,
sellQuotesPayload,
sellTradePayload,
sellWatchPayload,
};

export const invityResponses = {
Expand All @@ -46,20 +67,39 @@ export const invityResponses = {
[invityEndpoint.buyQuotes]: buyQuotesBTC,
[invityEndpoint.buyWatch]: buyWatch,
[invityEndpoint.sellList]: sellList,
[invityEndpoint.sellQuotes]: sellQuotesBTC,
[invityEndpoint.sellTrade]: sellTradeBTC,
[invityEndpoint.sellWatch]: sellWatch,
};

// This modification allows us to skip the provider's part of the flow and go directly to the transaction detail.
export const createRedirectedTradeResponse = (params: {
symbol: NetworkSymbol;
tradeRequest: TradeRequest;
url: string;
}) => {
const redirectToDetail = `${params.url}coinmarket-redirect#detail/${params.symbol}/normal/0/${params.tradeRequest.trade.paymentId}`;
const modifiedTrade = cloneDeep(params.tradeRequest);
modifiedTrade.trade.partnerData = redirectToDetail;
modifiedTrade.tradeForm.form.formAction = redirectToDetail;
// This modification allows us to skip the provider's part of the flow and continue further.
export const createRedirectedTradeResponse = (
tradeResponse: TradeResponse | SellTradeResponse,
tradeRequest: any,
) => {
const modifiedResponse = cloneDeep(tradeResponse);
modifiedResponse.trade.partnerData = tradeRequest.returnUrl;
modifiedResponse.tradeForm.form.formAction = tradeRequest.returnUrl;
modifiedResponse.trade.paymentId = tradeRequest.trade.paymentId;
modifiedResponse.trade.orderId = tradeRequest.trade.orderId;
if ('refundAddress' in modifiedResponse.trade && tradeRequest.refundAddress) {
modifiedResponse.trade.refundAddress = tradeRequest.refundAddress;
}

return modifiedResponse;
};

export const getCompanyNameFromList = (name: string, type: 'buyList' | 'sellList') => {
const list = type === 'buyList' ? buyList : sellList;
const filteredItems = list.providers.filter(item => item.name === name);

if (filteredItems.length !== 1) {
throw new Error(
`Expected exactly one item, but found ${filteredItems.length}\n${JSON.stringify(filteredItems, null, 2)}`,
);
}

return modifiedTrade;
return filteredItems[0].companyName;
};

export {
Expand All @@ -78,4 +118,7 @@ export {
buyTradeSolana,
buyWatch,
sellList,
sellQuotesBTC,
sellTradeBTC,
sellWatch,
};
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,6 @@
"cosmos",
"binance-smart-chain--0x0e09fabb73bd3ade0a17ecc321fd13a19e81ce82",
"flow",
"fantom",
"ethereum--0xf57e7e7c23978c3caec3c3548e3d615c346e79ff",
"ethereum--0xc944e90c64b2c07662a292be6244bdf05cda44a7",
"near",
Expand Down Expand Up @@ -374,7 +373,9 @@
"tradedCoins": [
"cardano",
"avalanche-2",
"ethereum--0xbb0e17ef65f82ab018d8edd776e8dd940327b28b",
"bitcoin-cash",
"binancecoin",
"bitcoin",
"dogecoin",
"ethereum",
Expand All @@ -383,6 +384,12 @@
"ethereum--0x455e53cbb86018ac2b8092fdcd39d8444affc3f6",
"polygon-ecosystem-token",
"solana",
"tron",
"ethereum--0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48",
"polygon-pos--0x3c499c542cef5e3811e1192ce70d8cc03d5c3359",
"solana--EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v",
"ethereum--0xdac17f958d2ee523a2206206994597c13d831ec7",
"tron--TR7NHqjeKQxGTCi8q8ZY4pL8otSzgjLj6t",
"stellar",
"ripple"
],
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
[
{
"exchange": "moonpay-sell",
"fiatCurrency": "EUR",
"cryptoCurrency": "bitcoin",
"rate": 85907.69230769231,
"amountInCrypto": true,
"exp": "qtn7k13GIY/wauu7BvapWA==",
"country": "CZ",
"paymentMethodName": "Credit Card",
"fiatStringAmount": "55.84",
"cryptoStringAmount": "0.00065",
"minFiat": 20,
"maxFiat": 30000,
"minCrypto": 0.00006,
"maxCrypto": 30000,
"paymentMethod": "creditCard"
},
{
"exchange": "btcdirect-sell",
"fiatCurrency": "EUR",
"cryptoCurrency": "bitcoin",
"rate": 92153.84615384616,
"amountInCrypto": true,
"exp": "qtn7k13GIY/wauu7BvapWA==",
"country": "CZ",
"paymentMethodName": "Bank Transfer",
"fiatStringAmount": "59.90",
"cryptoStringAmount": "0.00065",
"minFiat": 31.04,
"maxFiat": 51736.36,
"minCrypto": 0.00032244,
"maxCrypto": 0.53742565,
"paymentMethod": "bankTransfer",
"validUntil": "2025-02-07T12:43:29Z"
},
{
"exchange": "btcdirect-sell",
"fiatCurrency": "EUR",
"cryptoCurrency": "bitcoin",
"rate": 92153.84615384616,
"amountInCrypto": true,
"exp": "qtn7k13GIY/wauu7BvapWA==",
"country": "CZ",
"paymentMethodName": "SEPA",
"fiatStringAmount": "59.90",
"cryptoStringAmount": "0.00065",
"minFiat": 31.04,
"maxFiat": 51736.36,
"minCrypto": 0.00032244,
"maxCrypto": 0.53742565,
"paymentMethod": "sepa",
"validUntil": "2025-02-07T12:43:29Z"
},
{
"exchange": "moonpay-sell",
"fiatCurrency": "EUR",
"cryptoCurrency": "bitcoin",
"rate": 85907.69230769231,
"amountInCrypto": true,
"exp": "qtn7k13GIY/wauu7BvapWA==",
"country": "CZ",
"paymentMethodName": "SEPA",
"fiatStringAmount": "55.84",
"cryptoStringAmount": "0.00065",
"minFiat": 20,
"maxFiat": 30000,
"minCrypto": 0.00006,
"maxCrypto": 30000,
"paymentMethod": "sepa"
},
{
"error": "Amount too low, minimum is 0.00065 0.00083102.",
"exchange": "banxa-sell",
"fiatCurrency": "EUR",
"cryptoCurrency": "bitcoin",
"rate": 90969.23076923077,
"amountInCrypto": true,
"exp": "qtn7k13GIY/wauu7BvapWA==",
"country": "CZ",
"paymentMethodName": "Bank Transfer",
"fiatStringAmount": "59.13",
"cryptoStringAmount": "0.00065000",
"minFiat": 80,
"maxFiat": 50000,
"minCrypto": 0.00083102,
"maxCrypto": 0.51938878,
"paymentMethod": "bankTransfer",
"partnerData2": "6057"
}
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
{
"amountInCrypto": true,
"cryptoCurrency": "bitcoin",
"fiatCurrency": "EUR",
"country": "CZ",
"cryptoStringAmount": "0.00065",
"fiatStringAmount": "",
"flows": ["BANK_ACCOUNT", "PAYMENT_GATE"]
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
{
"trade": {
"exchange": "moonpay-sell",
"fiatCurrency": "EUR",
"cryptoCurrency": "bitcoin",
"rate": 85907.69230769231,
"amountInCrypto": true,
"exp": "qtn7k13GIY/wauu7BvapWA==",
"country": "CZ",
"paymentMethodName": "Credit Card",
"fiatStringAmount": "55.84",
"cryptoStringAmount": "0.00065",
"minFiat": 20,
"maxFiat": 30000,
"minCrypto": 0.00006,
"maxCrypto": 30000,
"paymentMethod": "creditCard",
"paymentId": "227c5679-53df-45a6-ae83-9f4ebf9ecce7",
"orderId": "4839ba2d-dd85-49b3-ae73-5ab1b526e66f",
"refundAddress": "bc1qw0r95wvsqxumq3km0q8kqyjdard2u8ahaw4y2n"
},
"returnUrl": "http://localhost:8000/coinmarket-redirect#sell-offers/btc/normal/0/p-qc/CZ/EUR/0.00065/bitcoin/4839ba2d-dd85-49b3-ae73-5ab1b526e66f"
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
{
"refundAddress": "bc1qw0r95wvsqxumq3km0q8kqyjdard2u8ahaw4y2n",
"paymentId": "227c5679-53df-45a6-ae83-9f4ebf9ecce7",
"status": "SUBMITTED",
"partnerData": "https://sell.moonpay.com/?apiKey=pk_live_1wuWa2Z1O2qG8izvpLkMOvBFbAPgWpfn&baseCurrencyCode=btc&quoteCurrencyCode=eur&baseCurrencyAmount=0.00065&lockAmount=true&externalTransactionId=227c5679-53df-45a6-ae83-9f4ebf9ecce7&redirectURL=http%3A%2F%2Flocalhost%3A8000%2Fcoinmarket-redirect%23sell-offers%2Fbtc%2Fnormal%2F0%2Fp-qc%2FCZ%2FEUR%2F0.00065%2Fbitcoin%2F4839ba2d-dd85-49b3-ae73-5ab1b526e66f&showWalletAddressForm=true&colorCode=%2300bfd9&language=CZ&signature=Nduwv4haCHiSgzeb1%2FaBUu8lN1r8aKg%2FN%2F2Io9JDYY0%3D",
"exchange": "moonpay-sell",
"fiatCurrency": "EUR",
"cryptoCurrency": "bitcoin",
"rate": 85907.69230769231,
"amountInCrypto": true,
"exp": "qtn7k13GIY/wauu7BvapWA==",
"country": "CZ",
"paymentMethodName": "Credit Card",
"fiatStringAmount": "55.84",
"cryptoStringAmount": "0.00065",
"minFiat": 20,
"maxFiat": 30000,
"minCrypto": 0.00006,
"maxCrypto": 30000,
"paymentMethod": "creditCard",
"orderId": "4839ba2d-dd85-49b3-ae73-5ab1b526e66f"
}
Loading

0 comments on commit f5bc4a6

Please sign in to comment.