Skip to content

Commit

Permalink
Merge pull request #2654 from decentdao/hotfix/v0.4.1
Browse files Browse the repository at this point in the history
Hotfix/v0.4.1
  • Loading branch information
adamgall authored Jan 7, 2025
2 parents 489e794 + 4cbc577 commit 6d0d2b8
Show file tree
Hide file tree
Showing 4 changed files with 60 additions and 23 deletions.
2 changes: 1 addition & 1 deletion package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "decent-interface",
"version": "0.4.0",
"version": "0.4.1",
"private": true,
"dependencies": {
"@amplitude/analytics-browser": "^2.11.1",
Expand Down
4 changes: 2 additions & 2 deletions src/components/ui/forms/ABISelector.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -38,10 +38,10 @@ export default function ABISelector({ target, onChange }: IABISelector) {
const requestFunc = ({ method, params }: { method: any; params: any }) =>
client.request({ method, params });

const proxy = await detectProxyTarget(ensAddress || target, requestFunc);
const implementationAddress = await detectProxyTarget(ensAddress || target, requestFunc);

const response = await axios.get(
`${etherscanAPIUrl}&module=contract&action=getabi&address=${proxy || ensAddress || target}`,
`${etherscanAPIUrl}&module=contract&action=getabi&address=${implementationAddress || ensAddress || target}`,
);
const responseData = response.data;

Expand Down
75 changes: 56 additions & 19 deletions src/hooks/utils/useSafeDecoder.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
import axios from 'axios';
import detectProxyTarget from 'evm-proxy-detection';
import { useCallback } from 'react';
import { Address, encodePacked, keccak256 } from 'viem';
import { Address, decodeFunctionData, encodePacked, Hex, keccak256 } from 'viem';
import { usePublicClient } from 'wagmi';
import { useNetworkConfigStore } from '../../providers/NetworkConfig/useNetworkConfigStore';
import { DecodedTransaction, DecodedTxParam } from '../../types';
import { buildSafeApiUrl, parseMultiSendTransactions } from '../../utils';
Expand All @@ -10,7 +12,8 @@ import { DBObjectKeys, useIndexedDB } from './cache/useLocalDB';
* Handles decoding and caching transactions via the Safe API.
*/
export const useSafeDecoder = () => {
const { safeBaseURL } = useNetworkConfigStore();
const client = usePublicClient();
const { safeBaseURL, etherscanAPIUrl } = useNetworkConfigStore();
const [setValue, getValue] = useIndexedDB(DBObjectKeys.DECODED_TRANSACTIONS);
const decode = useCallback(
async (value: string, to: Address, data?: string): Promise<DecodedTransaction[]> => {
Expand All @@ -19,7 +22,7 @@ export const useSafeDecoder = () => {
return [
{
target: to,
value: value,
value,
function: 'n/a',
parameterTypes: ['n/a'],
parameterValues: ['n/a'],
Expand All @@ -35,29 +38,63 @@ export const useSafeDecoder = () => {

let decoded: DecodedTransaction | DecodedTransaction[];
try {
const decodedData = (
await axios.post(buildSafeApiUrl(safeBaseURL, '/data-decoder/'), {
to: to,
data: data,
})
).data;
if (decodedData.parameters && decodedData.method === 'multiSend') {
const internalTransactionsMap = new Map<number, DecodedTransaction>();
parseMultiSendTransactions(internalTransactionsMap, decodedData.parameters);
decoded = [...internalTransactionsMap.values()].flat();
} else {
try {
const decodedData = (
await axios.post(buildSafeApiUrl(safeBaseURL, '/data-decoder/'), {
to,
data,
})
).data;
if (decodedData.parameters && decodedData.method === 'multiSend') {
const internalTransactionsMap = new Map<number, DecodedTransaction>();
parseMultiSendTransactions(internalTransactionsMap, decodedData.parameters);
decoded = [...internalTransactionsMap.values()].flat();
} else {
decoded = [
{
target: to,
value,
function: decodedData.method,
parameterTypes: decodedData.parameters.map((param: DecodedTxParam) => param.type),
parameterValues: decodedData.parameters.map((param: DecodedTxParam) => param.value),
decodingFailed: false,
},
];
}
} catch (e) {
console.error('Error decoding transaction using Safe API. Trying to decode with ABI', e);
if (!client) {
throw new Error('Client not found');
}
const requestFunc = ({ method, params }: { method: any; params: any }) =>
client.request({ method, params });
const implementationAddress = await detectProxyTarget(to, requestFunc);
const response = await axios.get(
`${etherscanAPIUrl}&module=contract&action=getabi&address=${implementationAddress || to}`,
);
const responseData = response.data;
const abi = JSON.parse(responseData.result);
const decodedData = decodeFunctionData({
abi,
data: data as Hex,
});
const functionAbi = abi.find((abiItem: any) => abiItem.name === decodedData.functionName);
decoded = [
{
target: to,
value: value,
function: decodedData.method,
parameterTypes: decodedData.parameters.map((param: DecodedTxParam) => param.type),
parameterValues: decodedData.parameters.map((param: DecodedTxParam) => param.value),
value,
function: decodedData.functionName,
parameterTypes: functionAbi.inputs.map((input: any) => input.type),
parameterValues: decodedData.args,
decodingFailed: false,
},
];
}
} catch (e) {
console.error(
'Error decoding transaction using ABI. Returning empty decoded transaction',
e,
);
return [
{
target: to,
Expand All @@ -77,7 +114,7 @@ export const useSafeDecoder = () => {

return decoded;
},
[getValue, safeBaseURL, setValue],
[getValue, safeBaseURL, etherscanAPIUrl, setValue, client],
);
return decode;
};

0 comments on commit 6d0d2b8

Please sign in to comment.