Skip to content

Commit 6a3952e

Browse files
committed
fix: optimize
1 parent e4f7531 commit 6a3952e

File tree

4 files changed

+79
-63
lines changed

4 files changed

+79
-63
lines changed

migrations/1756158854953_principal-txs.js

Lines changed: 20 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,14 @@ exports.up = pgm => {
2525
type: 'boolean',
2626
notNull: true,
2727
},
28+
stx_sent: {
29+
type: 'bigint',
30+
notNull: true,
31+
},
32+
stx_received: {
33+
type: 'bigint',
34+
notNull: true,
35+
},
2836
block_height: {
2937
type: 'integer',
3038
notNull: true,
@@ -54,17 +62,19 @@ exports.up = pgm => {
5462
notNull: true,
5563
},
5664
});
57-
5865
pgm.createIndex('principal_txs', 'tx_id');
59-
pgm.createIndex('principal_txs', 'principal', {
60-
where: 'canonical = TRUE AND microblock_canonical = TRUE',
61-
});
62-
pgm.createIndex('principal_txs', [
63-
{ name: 'block_height', sort: 'DESC' },
64-
{ name: 'microblock_sequence', sort: 'DESC' },
65-
{ name: 'tx_index', sort: 'DESC' },
66-
]);
67-
66+
pgm.createIndex(
67+
'principal_txs',
68+
[
69+
{ name: 'principal' },
70+
{ name: 'block_height', sort: 'DESC' },
71+
{ name: 'microblock_sequence', sort: 'DESC' },
72+
{ name: 'tx_index', sort: 'DESC' },
73+
],
74+
{
75+
where: 'canonical = TRUE AND microblock_canonical = TRUE',
76+
}
77+
);
6878
pgm.addConstraint(
6979
'principal_txs',
7080
'unique_principal_tx_id_index_block_hash_microblock_hash',

src/datastore/common.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1700,6 +1700,8 @@ export interface PrincipalTxsInsertValues {
17001700
microblock_sequence: number;
17011701
tx_index: number;
17021702
canonical: boolean;
1703+
stx_sent: bigint;
1704+
stx_received: bigint;
17031705
microblock_canonical: boolean;
17041706
stx_balance_affected: boolean;
17051707
ft_balance_affected: boolean;

src/datastore/pg-store-v2.ts

Lines changed: 20 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ import {
4343
parseAccountTransferSummaryTxQueryResult,
4444
POX4_SYNTHETIC_EVENT_COLUMNS,
4545
parseDbPoxSyntheticEvent,
46+
prefixedCols,
4647
} from './helpers';
4748
import { SyntheticPoxEventName } from '../pox-helpers';
4849

@@ -532,49 +533,27 @@ export class PgStoreV2 extends BasePgStoreModule {
532533
return await this.sqlTransaction(async sql => {
533534
const limit = args.limit ?? TransactionLimitParamSchema.default;
534535
const offset = args.offset ?? 0;
535-
536-
const eventCond = sql`
537-
tx_id = address_txs.tx_id
538-
AND index_block_hash = address_txs.index_block_hash
539-
AND microblock_hash = address_txs.microblock_hash
540-
`;
541536
const resultQuery = await sql<(AddressTransfersTxQueryResult & { count: number })[]>`
542-
WITH address_txs AS (
543-
SELECT tx_id, index_block_hash, microblock_hash, COUNT(*)::int AS count
544-
FROM principal_txs
545-
WHERE principal = ${args.address} AND canonical = TRUE AND microblock_canonical = TRUE
546-
)
547537
SELECT
548-
${sql(TX_COLUMNS)},
549-
(
550-
SELECT COALESCE(SUM(amount), 0)
551-
FROM stx_events
552-
WHERE ${eventCond} AND sender = ${args.address}
553-
) +
554-
CASE
555-
WHEN (txs.sponsored = false AND txs.sender_address = ${args.address})
556-
OR (txs.sponsored = true AND txs.sponsor_address = ${args.address})
557-
THEN txs.fee_rate ELSE 0
558-
END AS stx_sent,
559-
(
560-
SELECT COALESCE(SUM(amount), 0)
561-
FROM stx_events
562-
WHERE ${eventCond} AND recipient = ${args.address}
563-
) AS stx_received,
564-
stx_transfer_event_count AS stx_transfer,
565-
stx_mint_event_count AS stx_mint,
566-
stx_burn_event_count AS stx_burn,
567-
ft_transfer_event_count AS ft_transfer,
568-
ft_mint_event_count AS ft_mint,
569-
ft_burn_event_count AS ft_burn,
570-
nft_transfer_event_count AS nft_transfer,
571-
nft_mint_event_count AS nft_mint,
572-
nft_burn_event_count AS nft_burn,
573-
count
574-
FROM address_txs
575-
INNER JOIN txs USING (tx_id, index_block_hash, microblock_hash)
576-
WHERE canonical = TRUE AND microblock_canonical = TRUE
577-
ORDER BY block_height DESC, microblock_sequence DESC, tx_index DESC
538+
${sql(prefixedCols(TX_COLUMNS, 't'))},
539+
p.stx_sent,
540+
p.stx_received,
541+
p.stx_transfer_event_count AS stx_transfer,
542+
p.stx_mint_event_count AS stx_mint,
543+
p.stx_burn_event_count AS stx_burn,
544+
p.ft_transfer_event_count AS ft_transfer,
545+
p.ft_mint_event_count AS ft_mint,
546+
p.ft_burn_event_count AS ft_burn,
547+
p.nft_transfer_event_count AS nft_transfer,
548+
p.nft_mint_event_count AS nft_mint,
549+
p.nft_burn_event_count AS nft_burn,
550+
COUNT(*) OVER()::int AS count
551+
FROM principal_txs AS p
552+
INNER JOIN txs AS t USING (tx_id, index_block_hash, microblock_hash)
553+
WHERE p.principal = ${args.address}
554+
AND p.canonical = TRUE
555+
AND p.microblock_canonical = TRUE
556+
ORDER BY p.block_height DESC, p.microblock_sequence DESC, p.tx_index DESC
578557
LIMIT ${limit}
579558
OFFSET ${offset}
580559
`;

src/datastore/pg-write-store.ts

Lines changed: 37 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1383,28 +1383,51 @@ export class PgWriteStore extends PgStore {
13831383
for (const { tx, stxEvents, ftEvents, nftEvents } of txs) {
13841384
// Mark principals who participated in this transaction, along with the type of token balance
13851385
// they affected.
1386-
const principals = new Map<string, { stx: boolean; ft: boolean; nft: boolean }>();
1387-
const addPrincipal = (principal: string, affected?: 'stx' | 'ft' | 'nft') => {
1388-
const flags = principals.get(principal) || { stx: false, ft: false, nft: false };
1389-
if (affected) {
1390-
principals.set(principal, { ...flags, [affected]: true });
1386+
const principals = new Map<
1387+
string,
1388+
{ stx: boolean; ft: boolean; nft: boolean; stx_sent: bigint; stx_received: bigint }
1389+
>();
1390+
const addPrincipal = (
1391+
principal: string,
1392+
assetType?: 'stx' | 'ft' | 'nft',
1393+
stx_sent?: bigint,
1394+
stx_received?: bigint
1395+
) => {
1396+
const sent = stx_sent ?? BigInt(0);
1397+
const received = stx_received ?? BigInt(0);
1398+
const entry = principals.get(principal) || {
1399+
stx: false,
1400+
ft: false,
1401+
nft: false,
1402+
stx_sent: sent,
1403+
stx_received: received,
1404+
};
1405+
if (assetType) {
1406+
principals.set(principal, {
1407+
...entry,
1408+
[assetType]: true,
1409+
stx_sent: entry.stx_sent + sent,
1410+
stx_received: entry.stx_received + received,
1411+
});
13911412
} else {
1392-
principals.set(principal, flags);
1413+
principals.set(principal, entry);
13931414
}
13941415
};
13951416

1396-
// Add sender but only mark as stx if not sponsored, otherwise they didn't pay a fee
1417+
// Add sender but only mark as stx if not sponsored, otherwise they didn't pay a fee. Do not
1418+
// record amounts yet because that will be included in stx_events below.
13971419
addPrincipal(tx.sender_address, tx.sponsor_address ? undefined : 'stx');
1398-
if (tx.sponsor_address) addPrincipal(tx.sponsor_address, 'stx');
1420+
if (tx.sponsor_address) addPrincipal(tx.sponsor_address, 'stx', BigInt(tx.fee_rate));
13991421
if (tx.token_transfer_recipient_address)
14001422
addPrincipal(tx.token_transfer_recipient_address, 'stx');
1401-
// Add contract call and smart contract ids, no stx spent
1423+
1424+
// Add contract call and smart contract ids, no stx spent yet.
14021425
if (tx.contract_call_contract_id) addPrincipal(tx.contract_call_contract_id);
14031426
if (tx.smart_contract_contract_id) addPrincipal(tx.smart_contract_contract_id);
14041427

14051428
for (const event of stxEvents) {
1406-
if (event.sender) addPrincipal(event.sender, 'stx');
1407-
if (event.recipient) addPrincipal(event.recipient, 'stx');
1429+
if (event.sender) addPrincipal(event.sender, 'stx', event.amount);
1430+
if (event.recipient) addPrincipal(event.recipient, 'stx', BigInt(0), event.amount);
14081431
}
14091432
for (const event of ftEvents) {
14101433
if (event.sender) addPrincipal(event.sender, 'ft');
@@ -1414,7 +1437,7 @@ export class PgWriteStore extends PgStore {
14141437
if (event.sender) addPrincipal(event.sender, 'nft');
14151438
if (event.recipient) addPrincipal(event.recipient, 'nft');
14161439
}
1417-
for (const [principal, { stx, ft, nft }] of principals.entries()) {
1440+
for (const [principal, { stx, ft, nft, stx_sent, stx_received }] of principals.entries()) {
14181441
values.push({
14191442
principal,
14201443
tx_id: tx.tx_id,
@@ -1428,6 +1451,8 @@ export class PgWriteStore extends PgStore {
14281451
stx_balance_affected: stx,
14291452
ft_balance_affected: ft,
14301453
nft_balance_affected: nft,
1454+
stx_sent,
1455+
stx_received,
14311456
});
14321457
}
14331458
}

0 commit comments

Comments
 (0)