Skip to content

Commit fbe9f54

Browse files
fix: the projection now always stores blocks when it reaches tip - k
1 parent b0c08fd commit fbe9f54

File tree

5 files changed

+40
-3
lines changed

5 files changed

+40
-3
lines changed

packages/cardano-services/src/Projection/prepareTypeormProjection.ts

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ import {
3131
storeUtxo,
3232
willStoreAddresses,
3333
willStoreAssets,
34+
willStoreBlockData,
3435
willStoreHandleMetadata,
3536
willStoreHandles,
3637
willStoreNftMetadata,
@@ -371,6 +372,7 @@ export const prepareTypeormProjection = (
371372
.map((store) => Object.entries(storeOperators).find(([_, operator]) => store === operator)!)
372373
.map(([storeName]) => willStore[storeName as keyof StoreOperators])
373374
.filter(isNotNil);
375+
374376
return {
375377
__debug: {
376378
entities: selectedEntities.map((Entity) => keyOf(entities, Entity)),
@@ -383,8 +385,10 @@ export const prepareTypeormProjection = (
383385
mappers: selectedMappers,
384386
stores: selectedStores,
385387
willStore: <T extends ProjectionEvent>(evt: T) =>
388+
evt.eventType === ChainSyncEventType.RollBackward ||
386389
// eslint-disable-next-line @typescript-eslint/no-explicit-any
387-
evt.eventType === ChainSyncEventType.RollBackward || willStoreCheckers.some((check) => check(evt as any))
390+
willStoreCheckers.some((check) => check(evt as any)) ||
391+
willStoreBlockData(evt)
388392
};
389393
};
390394

packages/cardano-services/test/Projection/createTypeormProjection.test.ts

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import {
66
TokensEntity,
77
createDataSource
88
} from '@cardano-sdk/projection-typeorm';
9+
import { Cardano, ChainSyncEventType } from '@cardano-sdk/core';
910
import { ChainSyncDataSet, chainSyncData, logger } from '@cardano-sdk/util-dev';
1011
import { ProjectionName, createTypeormProjection, prepareTypeormProjection } from '../../src';
1112
import { lastValueFrom } from 'rxjs';
@@ -57,6 +58,12 @@ describe('createTypeormProjection', () => {
5758
.filter((evt) => (evt as any).block && (evt as any).block.body.length === 0)
5859
.map((evt) => (evt as any).block.header.hash);
5960

61+
// Make sure our empty blocks are outside the stability window.
62+
for (const event of data.allEvents) {
63+
if (event.eventType === ChainSyncEventType.RollForward && emptyBlocksHashes.includes(event.block.header.hash))
64+
event.tip.blockNo = Cardano.BlockNo(Number.MAX_SAFE_INTEGER);
65+
}
66+
6067
const projection$ = createTypeormProjection({
6168
blocksBufferLength: 10,
6269
cardanoNode: data.cardanoNode,

packages/projection-typeorm/src/TypeormStabilityWindowBuffer.ts

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,16 @@ export interface TypeormStabilityWindowBufferProps extends WithLogger {
2121
reconnectionConfig: ReconnectionConfig;
2222
}
2323

24+
export const willStoreBlockData = ({
25+
genesisParameters,
26+
block,
27+
tip
28+
}: {
29+
genesisParameters: Cardano.CompactGenesis;
30+
block: Cardano.Block;
31+
tip: Cardano.Tip;
32+
}) => block.header.blockNo >= tip.blockNo - genesisParameters.securityParameter;
33+
2434
export class TypeormStabilityWindowBuffer implements StabilityWindowBuffer {
2535
readonly #queryRunner$: Observable<QueryRunner>;
2636
readonly #retryBackoffConfig: RetryBackoffConfig;

packages/projection-typeorm/test/TypeormStabilityWindowBuffer.test.ts

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,8 @@ import {
33
BlockEntity,
44
TypeormStabilityWindowBuffer,
55
WithTypeormContext,
6-
createObservableConnection
6+
createObservableConnection,
7+
willStoreBlockData
78
} from '../src';
89
import { Cardano, ChainSyncEventType } from '@cardano-sdk/core';
910
import { DataSource, NoConnectionForRepositoryError, QueryRunner, Repository } from 'typeorm';
@@ -23,6 +24,12 @@ const createBlockDataEntity = (block: Cardano.Block, blockEntity: BlockEntity):
2324
data: block
2425
});
2526

27+
const createCustomEvent = (secParameter: number, blockNo: number, tipBlockNo: number) => ({
28+
block: { header: { blockNo } } as Cardano.Block,
29+
genesisParameters: { securityParameter: secParameter } as Cardano.CompactGenesis,
30+
tip: { blockNo: tipBlockNo } as Cardano.Tip
31+
});
32+
2633
describe('TypeormStabilityWindowBuffer', () => {
2734
const entities = [BlockEntity, BlockDataEntity];
2835
const securityParameter = 50;
@@ -170,4 +177,14 @@ describe('TypeormStabilityWindowBuffer', () => {
170177
});
171178
});
172179
});
180+
181+
describe('willStoreBlockData', () => {
182+
it('returns false when block is outside stability window', () => {
183+
expect(willStoreBlockData(createCustomEvent(10, 1, 500))).toBe(false);
184+
});
185+
186+
it('returns true when block is within stability window', () => {
187+
expect(willStoreBlockData(createCustomEvent(10, 490, 500))).toBe(true);
188+
});
189+
});
173190
});

yarn-project.nix

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1420,7 +1420,6 @@ cacheEntries = {
14201420
"fs-minipass@npm:3.0.0" = { filename = "fs-minipass-npm-3.0.0-3692c14b65-b72e9fe426.zip"; sha512 = "b72e9fe426e39f05b35bf237c8218b7ab3f68a65f325725ad7b4e431ff5a10725946fc62883b78446c07515ab938d25fdde3d08fb5ac8693f7f9eb9990da21f0"; };
14211421
"fs.realpath@npm:1.0.0" = { filename = "fs.realpath-npm-1.0.0-c8f05d8126-99ddea01a7.zip"; sha512 = "99ddea01a7e75aa276c250a04eedeffe5662bce66c65c07164ad6264f9de18fb21be9433ead460e54cff20e31721c811f4fb5d70591799df5f85dce6d6746fd0"; };
14221422
"fsevents@npm:2.3.2" = { filename = "fsevents-npm-2.3.2-a881d6ac9f-97ade64e75.zip"; sha512 = "97ade64e75091afee5265e6956cb72ba34db7819b4c3e94c431d4be2b19b8bb7a2d4116da417950c3425f17c8fe693d25e20212cac583ac1521ad066b77ae31f"; };
1423-
"fsevents@patch:fsevents@npm%3A2.3.2#~builtin<compat/fsevents>::version=2.3.2&hash=18f3a7" = { filename = "fsevents-patch-3340e2eb10-8.zip"; sha512 = "edbd0fd80be379c14409605f77e52fdc78a119e17f875e8b90a220c3e5b29e54a1477c21d91fd30b957ea4866406dc3ff87b61432d2840ff8866b309e5866140"; };
14241423
"ftp@npm:0.3.10" = { filename = "ftp-npm-0.3.10-348fb9ac23-ddd313c1d4.zip"; sha512 = "ddd313c1d44eb7429f3a7d77a0155dc8fe86a4c64dca58f395632333ce4b4e74c61413c6e0ef66ea3f3d32d905952fbb6d028c7117d522f793eb1fa282e17357"; };
14251424
"function-bind@npm:1.1.1" = { filename = "function-bind-npm-1.1.1-b56b322ae9-b32fbaebb3.zip"; sha512 = "b32fbaebb3f8ec4969f033073b43f5c8befbb58f1a79e12f1d7490358150359ebd92f49e72ff0144f65f2c48ea2a605bff2d07965f548f6474fd8efd95bf361a"; };
14261425
"function.prototype.name@npm:1.1.5" = { filename = "function.prototype.name-npm-1.1.5-e776a642bb-acd21d733a.zip"; sha512 = "acd21d733a9b649c2c442f067567743214af5fa248dbeee69d8278ce7df3329ea5abac572be9f7470b4ec1cd4d8f1040e3c5caccf98ebf2bf861a0deab735c27"; };

0 commit comments

Comments
 (0)