@0xsequence/connect
Version:
Connect package for Sequence Web SDK
400 lines • 13.6 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.decodeTransactions = exports.ByteSignature = exports.encodeTransactions = exports.DecodingType = void 0;
const indexer_1 = require("@0xsequence/indexer");
const viem_1 = require("viem");
var DecodingType;
(function (DecodingType) {
DecodingType["APPROVE"] = "approve";
DecodingType["TRANSFER"] = "transfer";
DecodingType["SWAP"] = "swap";
DecodingType["AWARD_ITEM"] = "awardItem";
DecodingType["UNIMPLEMENTED"] = "unimplemented";
DecodingType["UNKNOWN"] = "unknown";
})(DecodingType || (exports.DecodingType = DecodingType = {}));
// Transform decoded contract call arguments to a object format
const transformArgs = (args) => {
return Object.fromEntries(args.map((arg, i) => [
arg.name && !arg.name.startsWith('unnamed') ? arg.name : `_${i}`,
Array.isArray(arg.value)
? arg.type.startsWith('(') && (arg.type.endsWith(')') || arg.type.endsWith(')[]'))
? transformArgs(arg.value)
: arg.value
: arg.value
]));
};
const createTxnData = (to, call, value, data) => {
const args = transformArgs(call.args);
const byteSignature = (0, viem_1.slice)(data, 0, 4);
let objs = [];
switch (call.signature) {
case 'execute((bool,bool,uint256,address,uint256,bytes)[],uint256,bytes)':
case 'selfExecute((bool,bool,uint256,address,uint256,bytes)[])': {
const txns = call.args[0].value;
objs = txns.map(txn => {
const data = (0, viem_1.toHex)(txn.data);
const value = (0, viem_1.toHex)(BigInt(txn.value));
return txn.call
? createTxnData(txn.target, txn.call, value, data)
: {
to: txn.target,
signature: '',
byteSignature: (0, viem_1.slice)(data, 0, 4),
methodName: '',
args: {},
objs: [],
value,
data
};
});
}
}
return {
to,
signature: call.signature,
byteSignature,
methodName: call.function,
args,
objs,
value: (0, viem_1.toHex)(BigInt(value)),
data: data
};
};
const encodeTransactions = (transactions) => {
return transactions
.map(transaction => {
if ('target' in transaction) {
return transaction;
}
else {
return { ...transaction, target: transaction.to };
}
})
.map(transaction => ({
delegateCall: transaction.delegateCall ?? false,
revertOnError: transaction.revertOnError ?? false,
gasLimit: transaction.gasLimit ?? 0,
target: transaction.target ?? '0x0000000000000000000000000000000000000000',
value: transaction.value ?? 0,
data: transaction.data ?? '0x'
}));
};
exports.encodeTransactions = encodeTransactions;
var ByteSignature;
(function (ByteSignature) {
ByteSignature["SEQUENCE_DEPLOY"] = "0x32c02a14";
ByteSignature["SEQUENCE_PUBLISH_CONFIG"] = "0x44d466c2";
ByteSignature["SEQUENCE_UPDATE_IMAGE_HASH"] = "0x29561426";
ByteSignature["SEQUENCE_UPDATE_IMPLEMENTATION"] = "0x025b22bc";
ByteSignature["SEQUENCE_REQUIRE_SESSION_NONCE"] = "0x8853baa0";
ByteSignature["EXECUTE"] = "0x7a9a1628";
ByteSignature["SELF_EXECUTE"] = "0x61c2926c";
ByteSignature["APPROVE"] = "0x095ea7b3";
ByteSignature["TRANSFER"] = "0xa9059cbb";
ByteSignature["DEPOSIT"] = "0xd0e30db0";
ByteSignature["WITHDRAW"] = "0x2e1a7d4d";
ByteSignature["ERC721_SAFE_TRANSFER_FROM"] = "0x42842e0e";
ByteSignature["ERC721_SAFE_TRANSFER_FROM_WITH_DATA"] = "0xb88d4fde";
ByteSignature["ERC1155_SAFE_TRANSFER_FROM"] = "0xf242432a";
ByteSignature["ERC1155_SAFE_BATCH_TRANSFER_FROM"] = "0x2eb2c2d6";
ByteSignature["NIFTYSWAP_BUY_TOKENS"] = "0xd93e8aaa";
ByteSignature["TRANSFORM_ERC20"] = "0x415565b0";
ByteSignature["OUTBOUND_TRANSFER_TO"] = "0xa44bbb15";
ByteSignature["CELER_SEND"] = "0xa5977fbb";
ByteSignature["UNISWAPV3_MULTICALL"] = "0x5ae401dc";
ByteSignature["UNISWAPV2_SWAP_EXACT_TOKENS_FOR_TOKENS"] = "0x38ed1739";
ByteSignature["UNISWAPV2_SWAP_TOKENS_FOR_EXACT_TOKENS"] = "0x8803dbee";
ByteSignature["UNISWAPV2_SWAP_EXACT_ETH_FOR_TOKENS"] = "0x7ff36ab5";
ByteSignature["UNISWAPV2_SWAP_ETH_FOR_EXACT_TOKENS"] = "0xfb3bdb41";
ByteSignature["UNISWAPV2_SWAP_TOKENS_FOR_EXACT_ETH"] = "0x4a25d94a";
ByteSignature["UNISWAPV2_SWAP_EXACT_TOKENS_FOR_ETH"] = "0x18cbafe5";
// For demo NFT contract
ByteSignature["AWARD_ITEM"] = "0xcf378343";
})(ByteSignature || (exports.ByteSignature = ByteSignature = {}));
const decodeTxnData = async (apiClient, txns) => {
const callData = (0, viem_1.encodeFunctionData)({ abi: mainModuleAbi, functionName: 'selfExecute', args: [txns] });
try {
const { call } = await apiClient.decodeContractCall({ callData });
return createTxnData('', call, 0, callData);
}
catch (err) {
throw err;
}
};
const decodeTransactions = async (apiClient, accountAddress, txns) => {
const encodedTxns = (0, exports.encodeTransactions)(txns);
const decodedTxnDatas = (await decodeTxnData(apiClient, encodedTxns)).objs;
const from = (0, viem_1.getAddress)(accountAddress);
const txnProps = encodedTxns.map((txn, i) => {
const decodedTxnData = decodedTxnDatas[i];
const data = txn.data.toString();
const value = BigInt(txn.value).toString();
const target = txn.target;
if (data === '0x' || !data) {
// this is a native token transfer
return {
signature: '',
byteSignature: '',
type: DecodingType.TRANSFER,
methodName: 'nativeTokenTransfer',
transferType: indexer_1.TxnTransferType.SEND,
contractAddress: viem_1.zeroAddress,
contractType: indexer_1.ContractType.UNKNOWN,
from,
to: (0, viem_1.getAddress)(txn.target),
tokenIds: ['0'],
amounts: [value],
target,
value
};
}
if (!decodedTxnData) {
return undefined;
}
const contractAddress = (0, viem_1.getAddress)(txn.target);
const baseDecoding = {
type: DecodingType.UNIMPLEMENTED,
signature: decodedTxnData.signature,
byteSignature: decodedTxnData.byteSignature,
methodName: decodedTxnData.methodName,
target,
value
};
switch (decodedTxnData.byteSignature) {
case ByteSignature.TRANSFER: {
const { args } = decodedTxnData;
return {
...baseDecoding,
type: DecodingType.TRANSFER,
transferType: indexer_1.TxnTransferType.SEND,
contractAddress,
contractType: indexer_1.ContractType.ERC20,
from,
to: (0, viem_1.getAddress)(args.recipient),
tokenIds: ['0'],
amounts: [String(args.amount)]
};
}
case ByteSignature.ERC721_SAFE_TRANSFER_FROM:
case ByteSignature.ERC721_SAFE_TRANSFER_FROM_WITH_DATA: {
const args = decodedTxnData.args;
return {
...baseDecoding,
type: DecodingType.TRANSFER,
transferType: indexer_1.TxnTransferType.SEND,
contractAddress,
contractType: indexer_1.ContractType.ERC721,
from,
to: (0, viem_1.getAddress)(args.to),
tokenIds: [args.tokenId],
amounts: ['1']
};
}
case ByteSignature.ERC1155_SAFE_TRANSFER_FROM: {
const args = decodedTxnData.args;
return {
...baseDecoding,
type: DecodingType.TRANSFER,
transferType: indexer_1.TxnTransferType.SEND,
contractAddress,
contractType: indexer_1.ContractType.ERC1155,
from,
to: (0, viem_1.getAddress)(args._to),
tokenIds: [args._id],
amounts: [args._amount]
};
}
case ByteSignature.ERC1155_SAFE_BATCH_TRANSFER_FROM: {
const { args } = decodedTxnData;
return {
...baseDecoding,
type: DecodingType.TRANSFER,
transferType: indexer_1.TxnTransferType.SEND,
contractAddress,
contractType: indexer_1.ContractType.ERC1155,
from,
to: (0, viem_1.getAddress)(args._to),
tokenIds: args._ids,
amounts: args._amounts
};
}
case ByteSignature.AWARD_ITEM: {
const { args } = decodedTxnData;
return {
...baseDecoding,
type: DecodingType.AWARD_ITEM,
contractAddress,
to: (0, viem_1.getAddress)(args._0),
amount: '1'
};
}
}
return undefined;
});
return txnProps.flatMap(txn => {
if (txn) {
return [txn];
}
return [];
});
};
exports.decodeTransactions = decodeTransactions;
const mainModuleAbi = [
{
type: 'function',
name: 'nonce',
constant: true,
inputs: [],
outputs: [
{
type: 'uint256'
}
],
payable: false,
stateMutability: 'view'
},
{
type: 'function',
name: 'readNonce',
constant: true,
inputs: [
{
type: 'uint256'
}
],
outputs: [
{
type: 'uint256'
}
],
payable: false,
stateMutability: 'view'
},
{
type: 'function',
name: 'updateImplementation',
constant: false,
inputs: [
{
type: 'address'
}
],
outputs: [],
payable: false,
stateMutability: 'nonpayable'
},
{
type: 'function',
name: 'selfExecute',
constant: false,
inputs: [
{
components: [
{
type: 'bool',
name: 'delegateCall'
},
{
type: 'bool',
name: 'revertOnError'
},
{
type: 'uint256',
name: 'gasLimit'
},
{
type: 'address',
name: 'target'
},
{
type: 'uint256',
name: 'value'
},
{
type: 'bytes',
name: 'data'
}
],
type: 'tuple[]'
}
],
outputs: [],
payable: false,
stateMutability: 'nonpayable'
},
{
type: 'function',
name: 'execute',
constant: false,
inputs: [
{
components: [
{
type: 'bool',
name: 'delegateCall'
},
{
type: 'bool',
name: 'revertOnError'
},
{
type: 'uint256',
name: 'gasLimit'
},
{
type: 'address',
name: 'target'
},
{
type: 'uint256',
name: 'value'
},
{
type: 'bytes',
name: 'data'
}
],
type: 'tuple[]'
},
{
type: 'uint256'
},
{
type: 'bytes'
}
],
outputs: [],
payable: false,
stateMutability: 'nonpayable'
},
{
type: 'function',
name: 'createContract',
inputs: [
{
type: 'bytes'
}
],
payable: true,
stateMutability: 'payable'
},
{
type: 'function',
name: 'setExtraImageHash',
constant: false,
inputs: [
{
type: 'bytes32',
name: 'imageHash'
},
{
type: 'uint256',
name: 'expiration'
}
],
outputs: [],
payable: false,
stateMutability: 'nonpayable'
}
];
//# sourceMappingURL=txnDecoding.js.map