mirror of
https://github.com/alexgo-io/stacks-blockchain-api.git
synced 2026-01-12 22:43:34 +08:00
fix: address txs abi and reported total
* fix: get abi info when querying address txs * fix: query return type * fix: only parse abi json if it is a string * fix: keep stringify * fix: broken test * feat: move abi query to materialized view, fix count * chore: add test with contract call * chore: create incremental migration for materialized view changes * fix: undo vscode temp changes * chore: test contract-call function decoding in `/extended/v1/address/<contract-principal>/transactions` * chore: test contract-call function decoding in `/extended/v1/address/<standard-principal>/transactions` Co-authored-by: Matthew Little <zone117x@gmail.com>
This commit is contained in:
@@ -663,7 +663,7 @@ function parseDbTxTypeMetadata(dbTx: DbTx | DbMempoolTx): TransactionMetadata {
|
||||
let functionAbi: ClarityAbiFunction | undefined;
|
||||
const abi = dbTx.abi;
|
||||
if (abi) {
|
||||
const contractAbi: ClarityAbi = JSON.parse(JSON.stringify(abi));
|
||||
const contractAbi: ClarityAbi = typeof abi === 'string' ? JSON.parse(abi) : abi;
|
||||
functionAbi = contractAbi.functions.find(fn => fn.name === functionName);
|
||||
if (!functionAbi) {
|
||||
throw new Error(
|
||||
|
||||
@@ -5267,9 +5267,9 @@ export class PgDataStore
|
||||
!args.atSingleBlock &&
|
||||
args.limit + args.offset <= 50;
|
||||
const resultQuery = useMaterializedView
|
||||
? await client.query<TxQueryResult & { count: number }>(
|
||||
? await client.query<ContractTxQueryResult & { count: number }>(
|
||||
`
|
||||
SELECT ${TX_COLUMNS}, (COUNT(*) OVER())::integer as count
|
||||
SELECT ${TX_COLUMNS}, abi, count
|
||||
FROM latest_contract_txs
|
||||
WHERE contract_id = $1 AND block_height <= $4
|
||||
ORDER BY block_height DESC, microblock_sequence DESC, tx_index DESC
|
||||
@@ -5278,7 +5278,7 @@ export class PgDataStore
|
||||
`,
|
||||
[args.stxAddress, args.limit, args.offset, args.blockHeight]
|
||||
)
|
||||
: await client.query<TxQueryResult & { count: number }>(
|
||||
: await client.query<ContractTxQueryResult & { count: number }>(
|
||||
`
|
||||
WITH principal_txs AS (
|
||||
WITH event_txs AS (
|
||||
@@ -5298,14 +5298,24 @@ export class PgDataStore
|
||||
ON txs.tx_id = event_txs.tx_id
|
||||
WHERE txs.canonical = true AND txs.microblock_canonical = true
|
||||
)
|
||||
SELECT ${TX_COLUMNS}, (COUNT(*) OVER())::integer as count
|
||||
SELECT ${TX_COLUMNS},
|
||||
CASE
|
||||
WHEN principal_txs.type_id = $5 THEN (
|
||||
SELECT abi
|
||||
FROM smart_contracts
|
||||
WHERE smart_contracts.contract_id = principal_txs.contract_call_contract_id
|
||||
ORDER BY abi != 'null' DESC, canonical DESC, microblock_canonical DESC, block_height DESC
|
||||
LIMIT 1
|
||||
)
|
||||
END as abi,
|
||||
(COUNT(*) OVER())::integer as count
|
||||
FROM principal_txs
|
||||
${args.atSingleBlock ? 'WHERE block_height = $4' : 'WHERE block_height <= $4'}
|
||||
ORDER BY block_height DESC, microblock_sequence DESC, tx_index DESC
|
||||
LIMIT $2
|
||||
OFFSET $3
|
||||
`,
|
||||
[args.stxAddress, args.limit, args.offset, args.blockHeight]
|
||||
[args.stxAddress, args.limit, args.offset, args.blockHeight, DbTxTypeId.ContractCall]
|
||||
);
|
||||
const count = resultQuery.rowCount > 0 ? resultQuery.rows[0].count : 0;
|
||||
const parsed = resultQuery.rows.map(r => this.parseTxQueryResult(r));
|
||||
|
||||
146
src/migrations/1639152689764_latest_contract_txs_abi.ts
Normal file
146
src/migrations/1639152689764_latest_contract_txs_abi.ts
Normal file
@@ -0,0 +1,146 @@
|
||||
/* eslint-disable @typescript-eslint/camelcase */
|
||||
import { MigrationBuilder, ColumnDefinitions } from 'node-pg-migrate';
|
||||
|
||||
export const shorthands: ColumnDefinitions | undefined = undefined;
|
||||
|
||||
export async function up(pgm: MigrationBuilder): Promise<void> {
|
||||
pgm.dropMaterializedView('latest_contract_txs', { ifExists: true, cascade: true });
|
||||
pgm.createMaterializedView('latest_contract_txs', {}, `
|
||||
WITH contract_txs AS (
|
||||
SELECT
|
||||
contract_call_contract_id AS contract_id, tx_id,
|
||||
block_height, microblock_sequence, tx_index
|
||||
FROM txs
|
||||
WHERE
|
||||
contract_call_contract_id IS NOT NULL
|
||||
AND canonical = TRUE
|
||||
AND microblock_canonical = TRUE
|
||||
UNION
|
||||
SELECT
|
||||
smart_contract_contract_id AS contract_id, tx_id,
|
||||
block_height, microblock_sequence, tx_index
|
||||
FROM txs
|
||||
WHERE
|
||||
smart_contract_contract_id IS NOT NULL
|
||||
AND canonical = TRUE
|
||||
AND microblock_canonical = TRUE
|
||||
UNION
|
||||
SELECT
|
||||
sender_address AS contract_id, tx_id,
|
||||
block_height, microblock_sequence, tx_index
|
||||
FROM txs
|
||||
WHERE
|
||||
sender_address LIKE '%.%'
|
||||
AND canonical = TRUE
|
||||
AND microblock_canonical = TRUE
|
||||
UNION
|
||||
SELECT
|
||||
token_transfer_recipient_address AS contract_id, tx_id,
|
||||
block_height, microblock_sequence, tx_index
|
||||
FROM txs
|
||||
WHERE
|
||||
token_transfer_recipient_address LIKE '%.%'
|
||||
AND canonical = TRUE
|
||||
AND microblock_canonical = TRUE
|
||||
),
|
||||
numbered_txs AS (
|
||||
SELECT
|
||||
ROW_NUMBER() OVER (
|
||||
PARTITION BY contract_id
|
||||
ORDER BY block_height DESC, microblock_sequence DESC, tx_index DESC
|
||||
) AS r,
|
||||
COUNT(*) OVER (
|
||||
PARTITION BY contract_id
|
||||
)::integer AS count,
|
||||
contract_txs.*
|
||||
FROM contract_txs
|
||||
)
|
||||
SELECT
|
||||
numbered_txs.contract_id,
|
||||
txs.*,
|
||||
CASE
|
||||
WHEN txs.type_id = 2 THEN (
|
||||
SELECT abi
|
||||
FROM smart_contracts
|
||||
WHERE smart_contracts.contract_id = txs.contract_call_contract_id
|
||||
ORDER BY abi != 'null' DESC, canonical DESC, microblock_canonical DESC, block_height DESC
|
||||
LIMIT 1
|
||||
)
|
||||
END as abi,
|
||||
numbered_txs.count
|
||||
FROM numbered_txs
|
||||
INNER JOIN txs USING (tx_id)
|
||||
WHERE numbered_txs.r <= 50
|
||||
`);
|
||||
|
||||
pgm.createIndex('latest_contract_txs', 'contract_id');
|
||||
pgm.createIndex('latest_contract_txs', [
|
||||
{ name: 'block_height', sort: 'DESC' },
|
||||
{ name: 'microblock_sequence', sort: 'DESC'},
|
||||
{ name: 'tx_index', sort: 'DESC' }
|
||||
]);
|
||||
}
|
||||
|
||||
export async function down(pgm: MigrationBuilder): Promise<void> {
|
||||
// Go back to the previous materialized view version, otherwise `pgm` complains it can't infer the down migration.
|
||||
pgm.dropMaterializedView('latest_contract_txs', { ifExists: true, cascade: true });
|
||||
pgm.createMaterializedView('latest_contract_txs', {}, `
|
||||
WITH contract_txs AS (
|
||||
SELECT
|
||||
contract_call_contract_id AS contract_id, tx_id,
|
||||
block_height, microblock_sequence, tx_index
|
||||
FROM txs
|
||||
WHERE
|
||||
contract_call_contract_id IS NOT NULL
|
||||
AND canonical = TRUE
|
||||
AND microblock_canonical = TRUE
|
||||
UNION
|
||||
SELECT
|
||||
smart_contract_contract_id AS contract_id, tx_id,
|
||||
block_height, microblock_sequence, tx_index
|
||||
FROM txs
|
||||
WHERE
|
||||
smart_contract_contract_id IS NOT NULL
|
||||
AND canonical = TRUE
|
||||
AND microblock_canonical = TRUE
|
||||
UNION
|
||||
SELECT
|
||||
sender_address AS contract_id, tx_id,
|
||||
block_height, microblock_sequence, tx_index
|
||||
FROM txs
|
||||
WHERE
|
||||
sender_address LIKE '%.%'
|
||||
AND canonical = TRUE
|
||||
AND microblock_canonical = TRUE
|
||||
UNION
|
||||
SELECT
|
||||
token_transfer_recipient_address AS contract_id, tx_id,
|
||||
block_height, microblock_sequence, tx_index
|
||||
FROM txs
|
||||
WHERE
|
||||
token_transfer_recipient_address LIKE '%.%'
|
||||
AND canonical = TRUE
|
||||
AND microblock_canonical = TRUE
|
||||
),
|
||||
numbered_txs AS (
|
||||
SELECT
|
||||
ROW_NUMBER() OVER (
|
||||
PARTITION BY contract_id
|
||||
ORDER BY block_height DESC, microblock_sequence DESC, tx_index DESC
|
||||
) AS r,
|
||||
contract_txs.*
|
||||
FROM contract_txs
|
||||
)
|
||||
SELECT numbered_txs.contract_id, txs.*
|
||||
FROM numbered_txs
|
||||
INNER JOIN txs USING (tx_id)
|
||||
WHERE numbered_txs.r <= 50
|
||||
`);
|
||||
|
||||
pgm.createIndex('latest_contract_txs', 'contract_id');
|
||||
pgm.createIndex('latest_contract_txs', [
|
||||
{ name: 'block_height', sort: 'DESC' },
|
||||
{ name: 'microblock_sequence', sort: 'DESC'},
|
||||
{ name: 'tx_index', sort: 'DESC' }
|
||||
]);
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
import { getEnumDescription } from '../helpers';
|
||||
import { StacksMessageParsingError, NotImplementedError } from '../errors';
|
||||
import { ClarityValue, deserializeCV, BufferReader } from '@stacks/transactions';
|
||||
import { ClarityValue, deserializeCV, BufferReader, serializeCV } from '@stacks/transactions';
|
||||
|
||||
const MICROBLOCK_HEADER_SIZE =
|
||||
// 1-byte version number
|
||||
@@ -430,6 +430,17 @@ export function readClarityValueArray(input: BufferReader | Buffer): ClarityValu
|
||||
return values;
|
||||
}
|
||||
|
||||
export function createClarityValueArray(...input: ClarityValue[]): Buffer {
|
||||
const buffers = new Array<Buffer>(input.length);
|
||||
for (let i = 0; i < input.length; i++) {
|
||||
buffers[i] = serializeCV(input[i]);
|
||||
}
|
||||
const valueCountBuffer = Buffer.alloc(4);
|
||||
valueCountBuffer.writeUInt32BE(input.length);
|
||||
buffers.unshift(valueCountBuffer);
|
||||
return Buffer.concat(buffers);
|
||||
}
|
||||
|
||||
function readString(reader: BufferReader): string {
|
||||
const length = reader.readUInt32BE();
|
||||
const str = reader.readString(length, 'ascii');
|
||||
|
||||
@@ -16,9 +16,11 @@ import {
|
||||
ChainID,
|
||||
AnchorMode,
|
||||
intCV,
|
||||
uintCV,
|
||||
stringAsciiCV,
|
||||
} from '@stacks/transactions';
|
||||
import * as BN from 'bn.js';
|
||||
import { readTransaction } from '../p2p/tx';
|
||||
import { createClarityValueArray, readTransaction } from '../p2p/tx';
|
||||
import { getTxFromDataStore, getBlockFromDataStore } from '../api/controllers/db-controller';
|
||||
import {
|
||||
createDbTxFromCoreMsg,
|
||||
@@ -3877,6 +3879,8 @@ describe('api tests', () => {
|
||||
const testAddr2 = 'ST1HB64MAJ1MBV4CQ80GF01DZS4T1DSMX20ADCRA4';
|
||||
const testContractAddr = 'ST27W5M8BRKA7C5MZE2R1S1F4XTPHFWFRNHA9M04Y.hello-world';
|
||||
const testAddr4 = 'ST3DWSXBPYDB484QXFTR81K4AWG4ZB5XZNFF3H70C';
|
||||
const testAddr5 = 'ST3V11C6X2EBFN72RMS3B1NYQ1BX98F61GVYRDRXW';
|
||||
const testAddr6 = 'ST2F8G7616B2F8PYG216BX9AJCHP7YRK7ND7M0ZN3';
|
||||
|
||||
const block: DbBlock = {
|
||||
block_hash: '0x1234',
|
||||
@@ -4098,6 +4102,88 @@ describe('api tests', () => {
|
||||
createNFtEvents(testAddr2, testAddr1, 'tendies', 100),
|
||||
];
|
||||
|
||||
const contractJsonAbi = {
|
||||
maps: [],
|
||||
functions: [
|
||||
{
|
||||
args: [
|
||||
{ type: 'uint128', name: 'amount' },
|
||||
{ type: 'string-ascii', name: 'desc' },
|
||||
],
|
||||
name: 'test-contract-fn',
|
||||
access: 'public',
|
||||
outputs: {
|
||||
type: {
|
||||
response: {
|
||||
ok: 'uint128',
|
||||
error: 'none',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
],
|
||||
variables: [],
|
||||
fungible_tokens: [],
|
||||
non_fungible_tokens: [],
|
||||
};
|
||||
const contractLogEvent1: DbSmartContractEvent = {
|
||||
event_index: 4,
|
||||
tx_id: '0x421234',
|
||||
tx_index: 0,
|
||||
block_height: block.block_height,
|
||||
canonical: true,
|
||||
event_type: DbEventTypeId.SmartContractLog,
|
||||
contract_identifier: testContractAddr,
|
||||
topic: 'some-topic',
|
||||
value: serializeCV(bufferCVFromString('some val')),
|
||||
};
|
||||
const smartContract1: DbSmartContract = {
|
||||
tx_id: '0x421234',
|
||||
canonical: true,
|
||||
block_height: block.block_height,
|
||||
contract_id: testContractAddr,
|
||||
source_code: '(some-contract-src)',
|
||||
abi: JSON.stringify(contractJsonAbi),
|
||||
};
|
||||
const contractCall: DbTx = {
|
||||
tx_id: '0x1232',
|
||||
tx_index: 5,
|
||||
anchor_mode: 3,
|
||||
nonce: 0,
|
||||
raw_tx: Buffer.alloc(0),
|
||||
index_block_hash: block.index_block_hash,
|
||||
block_hash: block.block_hash,
|
||||
block_height: block.block_height,
|
||||
burn_block_time: block.burn_block_time,
|
||||
parent_burn_block_time: 1626122935,
|
||||
type_id: DbTxTypeId.ContractCall,
|
||||
coinbase_payload: Buffer.from('coinbase hi'),
|
||||
status: 1,
|
||||
raw_result: '0x0100000000000000000000000000000001', // u1
|
||||
canonical: true,
|
||||
microblock_canonical: true,
|
||||
microblock_sequence: I32_MAX,
|
||||
microblock_hash: '',
|
||||
parent_index_block_hash: '',
|
||||
parent_block_hash: '',
|
||||
post_conditions: Buffer.from([0x01, 0xf5]),
|
||||
fee_rate: 10n,
|
||||
sponsored: false,
|
||||
sponsor_address: testAddr1,
|
||||
sender_address: testContractAddr,
|
||||
origin_hash_mode: 1,
|
||||
event_count: 5,
|
||||
execution_cost_read_count: 0,
|
||||
execution_cost_read_length: 0,
|
||||
execution_cost_runtime: 0,
|
||||
execution_cost_write_count: 0,
|
||||
execution_cost_write_length: 0,
|
||||
contract_call_contract_id: testContractAddr,
|
||||
contract_call_function_name: 'test-contract-fn',
|
||||
contract_call_function_args: createClarityValueArray(uintCV(123456), stringAsciiCV('hello')),
|
||||
abi: JSON.stringify(contractJsonAbi),
|
||||
};
|
||||
|
||||
const dataStoreTxs = txs.map(dbTx => {
|
||||
return {
|
||||
tx: dbTx,
|
||||
@@ -4117,6 +4203,30 @@ describe('api tests', () => {
|
||||
stxEvents: events,
|
||||
ftEvents: ftEvents,
|
||||
nftEvents: nftEvents.flat(),
|
||||
contractLogEvents: [contractLogEvent1],
|
||||
smartContracts: [smartContract1],
|
||||
names: [],
|
||||
namespaces: [],
|
||||
});
|
||||
dataStoreTxs.push({
|
||||
tx: contractCall,
|
||||
stxLockEvents: [],
|
||||
stxEvents: [
|
||||
{
|
||||
canonical: true,
|
||||
event_type: DbEventTypeId.StxAsset,
|
||||
asset_event_type_id: DbAssetEventTypeId.Transfer,
|
||||
event_index: 0,
|
||||
tx_id: contractCall.tx_id,
|
||||
tx_index: contractCall.tx_index,
|
||||
block_height: contractCall.block_height,
|
||||
amount: 4321n,
|
||||
sender: testAddr5,
|
||||
recipient: testAddr6,
|
||||
},
|
||||
],
|
||||
ftEvents: [],
|
||||
nftEvents: [],
|
||||
contractLogEvents: [],
|
||||
smartContracts: [],
|
||||
names: [],
|
||||
@@ -4186,10 +4296,10 @@ describe('api tests', () => {
|
||||
expect(fetchAddrBalance2.type).toBe('application/json');
|
||||
const expectedResp2 = {
|
||||
stx: {
|
||||
balance: '101',
|
||||
balance: '91',
|
||||
total_sent: '15',
|
||||
total_received: '1350',
|
||||
total_fees_sent: '1234',
|
||||
total_fees_sent: '1244',
|
||||
total_miner_rewards_received: '0',
|
||||
burnchain_lock_height: 0,
|
||||
burnchain_unlock_height: 0,
|
||||
@@ -4221,10 +4331,10 @@ describe('api tests', () => {
|
||||
expect(fetchAddrStxBalance1.status).toBe(200);
|
||||
expect(fetchAddrStxBalance1.type).toBe('application/json');
|
||||
const expectedStxResp1 = {
|
||||
balance: '101',
|
||||
balance: '91',
|
||||
total_sent: '15',
|
||||
total_received: '1350',
|
||||
total_fees_sent: '1234',
|
||||
total_fees_sent: '1244',
|
||||
total_miner_rewards_received: '0',
|
||||
burnchain_lock_height: 0,
|
||||
burnchain_unlock_height: 0,
|
||||
@@ -4361,7 +4471,7 @@ describe('api tests', () => {
|
||||
const expectedResp4 = {
|
||||
limit: 20,
|
||||
offset: 0,
|
||||
total: 3,
|
||||
total: 4,
|
||||
results: [
|
||||
{
|
||||
tx_id: '0x12340005',
|
||||
@@ -4403,6 +4513,62 @@ describe('api tests', () => {
|
||||
execution_cost_write_count: 0,
|
||||
execution_cost_write_length: 0,
|
||||
},
|
||||
{
|
||||
tx_id: '0x1232',
|
||||
tx_status: 'success',
|
||||
tx_result: {
|
||||
hex: '0x0100000000000000000000000000000001', // u1
|
||||
repr: 'u1',
|
||||
},
|
||||
tx_type: 'contract_call',
|
||||
fee_rate: '10',
|
||||
is_unanchored: false,
|
||||
nonce: 0,
|
||||
anchor_mode: 'any',
|
||||
sender_address: 'ST27W5M8BRKA7C5MZE2R1S1F4XTPHFWFRNHA9M04Y.hello-world',
|
||||
sponsor_address: 'ST3J8EVYHVKH6XXPD61EE8XEHW4Y2K83861225AB1',
|
||||
sponsored: false,
|
||||
post_condition_mode: 'allow',
|
||||
post_conditions: [],
|
||||
block_hash: '0x1234',
|
||||
block_height: 1,
|
||||
burn_block_time: 39486,
|
||||
burn_block_time_iso: '1970-01-01T10:58:06.000Z',
|
||||
canonical: true,
|
||||
microblock_canonical: true,
|
||||
microblock_hash: '',
|
||||
microblock_sequence: I32_MAX,
|
||||
parent_block_hash: '',
|
||||
parent_burn_block_time: 1626122935,
|
||||
parent_burn_block_time_iso: '2021-07-12T20:48:55.000Z',
|
||||
tx_index: 5,
|
||||
contract_call: {
|
||||
contract_id: 'ST27W5M8BRKA7C5MZE2R1S1F4XTPHFWFRNHA9M04Y.hello-world',
|
||||
function_name: 'test-contract-fn',
|
||||
function_signature:
|
||||
'(define-public (test-contract-fn (amount uint) (desc string-ascii)))',
|
||||
function_args: [
|
||||
{
|
||||
hex: '0x010000000000000000000000000001e240',
|
||||
name: 'amount',
|
||||
repr: 'u123456',
|
||||
type: 'uint',
|
||||
},
|
||||
{
|
||||
hex: '0x0d0000000568656c6c6f',
|
||||
name: 'desc',
|
||||
repr: '"hello"',
|
||||
type: 'string-ascii',
|
||||
},
|
||||
],
|
||||
},
|
||||
event_count: 5,
|
||||
execution_cost_read_count: 0,
|
||||
execution_cost_read_length: 0,
|
||||
execution_cost_runtime: 0,
|
||||
execution_cost_write_count: 0,
|
||||
execution_cost_write_length: 0,
|
||||
},
|
||||
{
|
||||
tx_id: '0x12340003',
|
||||
tx_status: 'success',
|
||||
@@ -4486,6 +4652,76 @@ describe('api tests', () => {
|
||||
],
|
||||
};
|
||||
expect(JSON.parse(fetchAddrTx1.text)).toEqual(expectedResp4);
|
||||
|
||||
const fetchAddrTx2 = await supertest(api.server).get(
|
||||
`/extended/v1/address/${testAddr5}/transactions`
|
||||
);
|
||||
expect(fetchAddrTx2.status).toBe(200);
|
||||
expect(fetchAddrTx2.type).toBe('application/json');
|
||||
const expectedResp5 = {
|
||||
limit: 20,
|
||||
offset: 0,
|
||||
total: 1,
|
||||
results: [
|
||||
{
|
||||
tx_id: '0x1232',
|
||||
tx_status: 'success',
|
||||
tx_result: {
|
||||
hex: '0x0100000000000000000000000000000001', // u1
|
||||
repr: 'u1',
|
||||
},
|
||||
tx_type: 'contract_call',
|
||||
fee_rate: '10',
|
||||
is_unanchored: false,
|
||||
nonce: 0,
|
||||
anchor_mode: 'any',
|
||||
sender_address: 'ST27W5M8BRKA7C5MZE2R1S1F4XTPHFWFRNHA9M04Y.hello-world',
|
||||
sponsor_address: 'ST3J8EVYHVKH6XXPD61EE8XEHW4Y2K83861225AB1',
|
||||
sponsored: false,
|
||||
post_condition_mode: 'allow',
|
||||
post_conditions: [],
|
||||
block_hash: '0x1234',
|
||||
block_height: 1,
|
||||
burn_block_time: 39486,
|
||||
burn_block_time_iso: '1970-01-01T10:58:06.000Z',
|
||||
canonical: true,
|
||||
microblock_canonical: true,
|
||||
microblock_hash: '',
|
||||
microblock_sequence: I32_MAX,
|
||||
parent_block_hash: '',
|
||||
parent_burn_block_time: 1626122935,
|
||||
parent_burn_block_time_iso: '2021-07-12T20:48:55.000Z',
|
||||
tx_index: 5,
|
||||
contract_call: {
|
||||
contract_id: 'ST27W5M8BRKA7C5MZE2R1S1F4XTPHFWFRNHA9M04Y.hello-world',
|
||||
function_name: 'test-contract-fn',
|
||||
function_signature:
|
||||
'(define-public (test-contract-fn (amount uint) (desc string-ascii)))',
|
||||
function_args: [
|
||||
{
|
||||
hex: '0x010000000000000000000000000001e240',
|
||||
name: 'amount',
|
||||
repr: 'u123456',
|
||||
type: 'uint',
|
||||
},
|
||||
{
|
||||
hex: '0x0d0000000568656c6c6f',
|
||||
name: 'desc',
|
||||
repr: '"hello"',
|
||||
type: 'string-ascii',
|
||||
},
|
||||
],
|
||||
},
|
||||
event_count: 5,
|
||||
execution_cost_read_count: 0,
|
||||
execution_cost_read_length: 0,
|
||||
execution_cost_runtime: 0,
|
||||
execution_cost_write_count: 0,
|
||||
execution_cost_write_length: 0,
|
||||
},
|
||||
],
|
||||
};
|
||||
expect(JSON.parse(fetchAddrTx2.text)).toEqual(expectedResp5);
|
||||
});
|
||||
|
||||
test('list contract log events', async () => {
|
||||
|
||||
Reference in New Issue
Block a user