Commit c18c5c91 authored by tom goriunov's avatar tom goriunov Committed by GitHub

Read verified contract: error of query execution is not displayed (#1190)

Fixes #1126
parent e2a293c6
...@@ -110,9 +110,14 @@ export interface SmartContractQueryMethodReadError { ...@@ -110,9 +110,14 @@ export interface SmartContractQueryMethodReadError {
result: { result: {
code: number; code: number;
message: string; message: string;
raw?: string;
} | { } | {
error: string; error: string;
} | {
raw: string;
} | {
method_call: string;
method_id: string;
parameters: Array<{ 'name': string; 'type': string; 'value': string }>;
}; };
} }
......
...@@ -44,29 +44,3 @@ test('base view +@mobile +@dark-mode', async({ mount, page }) => { ...@@ -44,29 +44,3 @@ test('base view +@mobile +@dark-mode', async({ mount, page }) => {
await expect(component).toHaveScreenshot(); await expect(component).toHaveScreenshot();
}); });
test('error result', async({ mount, page }) => {
await page.route(CONTRACT_READ_METHODS_API_URL, (route) => route.fulfill({
status: 200,
body: JSON.stringify(contractMethodsMock.read),
}));
await page.route(CONTRACT_QUERY_METHOD_API_URL, (route) => route.fulfill({
status: 200,
body: JSON.stringify(contractMethodsMock.readResultError),
}));
const component = await mount(
<TestApp>
<ContractRead addressHash={ addressHash }/>
</TestApp>,
{ hooksConfig },
);
await component.getByText(/expand all/i).click();
await component.getByPlaceholder(/address/i).type('address-hash');
await component.getByText(/query/i).click();
const section = page.locator('section', { hasText: 'FLASHLOAN_PREMIUM_TOTAL' });
await expect(section).toHaveScreenshot();
});
import { test, expect } from '@playwright/experimental-ct-react';
import React from 'react';
import type { ContractMethodReadResult } from './types';
import * as contractMethodsMock from 'mocks/contract/methods';
import TestApp from 'playwright/TestApp';
import ContractReadResult from './ContractReadResult';
const item = contractMethodsMock.read[0];
const onSettle = () => Promise.resolve();
test.use({ viewport: { width: 500, height: 500 } });
test('default error', async({ mount }) => {
const result: ContractMethodReadResult = {
is_error: true,
result: {
error: 'I am an error',
},
};
const component = await mount(
<TestApp>
<ContractReadResult item={ item } onSettle={ onSettle } result={ result }/>
</TestApp>,
);
await expect(component).toHaveScreenshot();
});
test('error with code', async({ mount }) => {
const result: ContractMethodReadResult = {
is_error: true,
result: {
message: 'I am an error',
code: -32017,
},
};
const component = await mount(
<TestApp>
<ContractReadResult item={ item } onSettle={ onSettle } result={ result }/>
</TestApp>,
);
await expect(component).toHaveScreenshot();
});
test('raw error', async({ mount }) => {
const result: ContractMethodReadResult = {
is_error: true,
result: {
raw: '49276d20616c7761797320726576657274696e67207769746820616e206572726f72',
},
};
const component = await mount(
<TestApp>
<ContractReadResult item={ item } onSettle={ onSettle } result={ result }/>
</TestApp>,
);
await expect(component).toHaveScreenshot();
});
test('complex error', async({ mount }) => {
const result: ContractMethodReadResult = {
is_error: true,
result: {
method_call: 'SomeCustomError(address addr, uint256 balance)',
method_id: '50289a9f',
parameters: [
{ name: 'addr', type: 'address', value: '0x850e73b42f48e91ebaedf8f00a74f6147e485c5a' },
{ name: 'balance', type: 'uint256', value: '14' },
],
},
};
const component = await mount(
<TestApp>
<ContractReadResult item={ item } onSettle={ onSettle } result={ result }/>
</TestApp>,
);
await expect(component).toHaveScreenshot();
});
test('success', async({ mount }) => {
const result: ContractMethodReadResult = {
is_error: false,
result: {
names: [ 'address' ],
output: [ { type: 'address', value: '0x0000000000000000000000000000000000000000' } ],
},
};
const component = await mount(
<TestApp>
<ContractReadResult item={ item } onSettle={ onSettle } result={ result }/>
</TestApp>,
);
await expect(component).toHaveScreenshot();
});
...@@ -6,6 +6,15 @@ import type { SmartContractReadMethod } from 'types/api/contract'; ...@@ -6,6 +6,15 @@ import type { SmartContractReadMethod } from 'types/api/contract';
import hexToUtf8 from 'lib/hexToUtf8'; import hexToUtf8 from 'lib/hexToUtf8';
const ContractReadResultError = ({ children }: {children: React.ReactNode}) => {
return (
<Alert status="error" mt={ 3 } p={ 4 } borderRadius="md" fontSize="sm" wordBreak="break-word" whiteSpace="pre-wrap">
{ children }
</Alert>
);
};
interface Props { interface Props {
item: SmartContractReadMethod; item: SmartContractReadMethod;
result: ContractMethodReadResult; result: ContractMethodReadResult;
...@@ -20,19 +29,27 @@ const ContractReadResult = ({ item, result, onSettle }: Props) => { ...@@ -20,19 +29,27 @@ const ContractReadResult = ({ item, result, onSettle }: Props) => {
}, [ onSettle ]); }, [ onSettle ]);
if ('status' in result) { if ('status' in result) {
return <Alert status="error" mt={ 3 } p={ 4 } borderRadius="md" fontSize="sm" wordBreak="break-word">{ result.statusText }</Alert>; return <ContractReadResultError>{ result.statusText }</ContractReadResultError>;
} }
if (result.is_error) { if (result.is_error) {
const message = 'error' in result.result ? result.result.error : result.result.message; if ('error' in result.result) {
const decoded = 'raw' in result.result && result.result.raw ? `\nRevert reason: ${ hexToUtf8(result.result.raw) }` : ''; return <ContractReadResultError>{ result.result.error }</ContractReadResultError>;
}
return (
<Alert status="error" mt={ 3 } p={ 4 } borderRadius="md" fontSize="sm" wordBreak="break-word" whiteSpace="pre-wrap"> if ('message' in result.result) {
{ message } return <ContractReadResultError>[{ result.result.code }] { result.result.message }</ContractReadResultError>;
{ decoded } }
</Alert>
); if ('raw' in result.result) {
return <ContractReadResultError>{ `Revert reason: ${ hexToUtf8(result.result.raw) }` }</ContractReadResultError>;
}
if ('method_id' in result.result) {
return <ContractReadResultError>{ JSON.stringify(result.result, undefined, 2) }</ContractReadResultError>;
}
return <ContractReadResultError>Something went wrong.</ContractReadResultError>;
} }
return ( return (
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment