Fetch logs with simulateTransaction when transactions fail

This commit is contained in:
Gary Wang 2020-12-10 04:10:13 +08:00
parent 42fec272c9
commit 3f21f90f77
6 changed files with 62 additions and 9 deletions

View File

@ -44,7 +44,7 @@
"build": "craco build",
"test": "craco test",
"eject": "react-scripts eject",
"prettier": "prettier --write ."
"prettier": "prettier --write src"
},
"eslintConfig": {
"extends": "react-app"

View File

@ -100,7 +100,8 @@ export default function ListNewMarketPage() {
} catch (e) {
console.warn(e);
notify({
message: 'Error listing new market: ' + e.message,
message: 'Error listing new market',
description: e.message,
type: 'error',
});
} finally {

View File

@ -28,7 +28,7 @@ const AddRemoveTokenButtons = styled.div`
margin-bottom: 16px;
`;
const DEFAULT_PROGRAM_ID = 'DL7L4cFHwmfNevZRg92rF5unbdUvFGoiuMrQ4aV7Nzsc';
const DEFAULT_PROGRAM_ID = 'CkMC9rHPB6xu7pQ3L49KUEYL6rcLJ25aKLLPcrNe5wLv';
export default function NewPoolPage() {
const connection = useConnection();
@ -100,7 +100,8 @@ export default function NewPoolPage() {
} catch (e) {
console.warn(e);
notify({
message: 'Error creating new pool: ' + e.message,
message: 'Error creating new pool',
description: e.message,
type: 'error',
});
} finally {

View File

@ -69,7 +69,8 @@ function PauseUnpauseTab({ poolInfo }: TabParams) {
await sendTransaction({ connection, wallet, transaction });
} catch (e) {
notify({
message: 'Error pausing pool: ' + e.message,
message: 'Error pausing pool',
description: e.message,
type: 'error',
});
} finally {
@ -88,7 +89,8 @@ function PauseUnpauseTab({ poolInfo }: TabParams) {
await sendTransaction({ connection, wallet, transaction });
} catch (e) {
notify({
message: 'Error unpausing pool: ' + e.message,
message: 'Error unpausing pool',
description: e.message,
type: 'error',
});
} finally {
@ -396,7 +398,8 @@ function useOnSubmitHandler(
}
} catch (e) {
notify({
message: `Error ${description}: ${e.message}`,
message: `Error ${description}`,
description: e.message,
type: 'error',
});
} finally {

View File

@ -119,8 +119,8 @@ function CreateRedeemTab({ poolInfo, mintInfo, tab }: CreateRedeemInnerPanel) {
message:
'Error ' +
(tab === 'create' ? 'creating' : 'redeeming') +
' pool tokens: ' +
e.message,
' pool tokens',
description: e.message,
type: 'error',
});
} finally {

View File

@ -4,9 +4,11 @@ import { getSelectedTokenAccountForMint } from './markets';
import {
Account,
AccountInfo,
Commitment,
Connection,
PublicKey,
RpcResponseAndContext,
SimulatedTransactionResponse,
SystemProgram,
Transaction,
TransactionSignature,
@ -720,6 +722,25 @@ export async function sendSignedTransaction({
if (err.timeout) {
throw new Error('Timed out awaiting confirmation on transaction');
}
let simulateResult: SimulatedTransactionResponse | null = null;
try {
simulateResult = (
await simulateTransaction(connection, signedTransaction, 'single')
).value;
} catch (e) {}
if (simulateResult && simulateResult.err) {
if (simulateResult.logs) {
for (let i = simulateResult.logs.length - 1; i >= 0; --i) {
const line = simulateResult.logs[i];
if (line.startsWith('Program log: ')) {
throw new Error(
'Transaction failed: ' + line.slice('Program log: '.length),
);
}
}
}
throw new Error(JSON.stringify(simulateResult.err));
}
throw new Error('Transaction failed');
} finally {
done = true;
@ -903,3 +924,30 @@ export async function getMultipleSolanaAccounts(
),
};
}
/** Copy of Connection.simulateTransaction that takes a commitment parameter. */
async function simulateTransaction(
connection: Connection,
transaction: Transaction,
commitment: Commitment,
): Promise<RpcResponseAndContext<SimulatedTransactionResponse>> {
// @ts-ignore
transaction.recentBlockhash = await connection._recentBlockhash(
// @ts-ignore
connection._disableBlockhashCaching,
);
const signData = transaction.serializeMessage();
// @ts-ignore
const wireTransaction = transaction._serialize(signData);
const encodedTransaction = wireTransaction.toString('base64');
const config: any = { encoding: 'base64', commitment };
const args = [encodedTransaction, config];
// @ts-ignore
const res = await connection._rpcRequest('simulateTransaction', args);
if (res.error) {
throw new Error('failed to simulate transaction: ' + res.error.message);
}
return res.result;
}