Skip to content

Commit 000bdeb

Browse files
authored
Merge pull request #1570 from multiversx/elastic-search-by-timestampMs
Add support for timestampMs for filtering
2 parents c513fd1 + 5e520d4 commit 000bdeb

29 files changed

Lines changed: 314 additions & 164 deletions

config/config.devnet-old.yaml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,10 @@ features:
6161
jwtSecret: ''
6262
nodeEpochsLeft:
6363
enabled: false
64+
chainSupernova:
65+
enabled: false
66+
activationEpoch: 2030
67+
activationTimestamp: 1864749472
6468
image:
6569
width: 600
6670
height: 600

config/config.devnet.yaml

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,10 @@ features:
7373
stakingV5:
7474
enabled: true
7575
activationEpoch: 4817
76+
chainSupernova:
77+
enabled: false
78+
activationEpoch: 2030
79+
activationTimestamp: 1864749472
7680
deprecatedRelayedV1V2:
7781
enabled: true
7882
activationEpoch: 4569
@@ -196,4 +200,4 @@ compression:
196200
enabled: true
197201
level: 6
198202
threshold: 1024
199-
chunkSize: 16384
203+
chunkSize: 16384

config/config.e2e-mocked.mainnet.yaml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,10 @@ features:
1616
maxExpirySeconds: 86400
1717
acceptedOrigins:
1818
- ''
19+
chainSupernova:
20+
enabled: false
21+
activationEpoch: 2030
22+
activationTimestamp: 1864749472
1923
cron:
2024
transactionProcessor: false
2125
transactionProcessorMaxLookBehind: 1000

config/config.e2e.mainnet.yaml

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,10 @@ features:
7171
stakingV5:
7272
enabled: true
7373
activationEpoch: 1951
74+
chainSupernova:
75+
enabled: false
76+
activationEpoch: 2030
77+
activationTimestamp: 1864749472
7478
nodeEpochsLeft:
7579
enabled: false
7680
transactionProcessor:
@@ -190,4 +194,4 @@ stakingV5Inflation:
190194
- 1262802
191195
nftProcess:
192196
parallelism: 1
193-
maxRetries: 3
197+
maxRetries: 3

config/config.mainnet.yaml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,10 @@ features:
7171
stakingV5:
7272
enabled: true
7373
activationEpoch: 1951
74+
chainSupernova:
75+
enabled: false
76+
activationEpoch: 2030
77+
activationTimestamp: 1864749472
7478
deprecatedRelayedV1V2:
7579
enabled: true
7680
activationEpoch: 1918

config/config.testnet.yaml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,10 @@ features:
7070
stakingV5:
7171
enabled: true
7272
activationEpoch: 2519
73+
chainSupernova:
74+
enabled: false
75+
activationEpoch: 2030
76+
activationTimestamp: 1864749472
7377
deprecatedRelayedV1V2:
7478
enabled: true
7579
activationEpoch: 2038

src/common/api-config/api.config.service.ts

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import { ConfigService } from '@nestjs/config';
44
import { DatabaseConnectionOptions } from '../persistence/entities/connection.options';
55
import { StatusCheckerThresholds } from './entities/status-checker-thresholds';
66
import { LogTopic } from '@multiversx/sdk-transaction-processor/lib/types/log-topic';
7+
import { TimeUtils } from 'src/utils/time.utils';
78

89
@Injectable()
910
export class ApiConfigService {
@@ -1067,4 +1068,26 @@ export class ApiConfigService {
10671068

10681069
return undefined;
10691070
}
1071+
1072+
isChainSupernovaEnabled(): boolean {
1073+
return this.configService.get<boolean>('features.chainSupernova.enabled') ?? false;
1074+
}
1075+
1076+
getSupernovaActivationEpoch(): number {
1077+
const epoch = this.configService.get<number>('features.chainSupernova.activationEpoch');
1078+
if (epoch == null) {
1079+
return TimeUtils.TIMESTAMP_IN_SECONDS_THRESHOLD + 1;
1080+
}
1081+
1082+
return epoch;
1083+
}
1084+
1085+
getSupernovaActivationTimestamp(): number {
1086+
const timestamp = this.configService.get<number>('features.chainSupernova.activationTimestamp');
1087+
if (timestamp == null) {
1088+
return TimeUtils.TIMESTAMP_IN_SECONDS_THRESHOLD + 1;
1089+
}
1090+
1091+
return timestamp;
1092+
}
10701093
}

src/common/indexer/elastic/elastic.indexer.helper.ts

Lines changed: 48 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ import { ApplicationFilter } from "src/endpoints/applications/entities/applicati
1919
import { NftType } from "../entities/nft.type";
2020
import { EventsFilter } from "src/endpoints/events/entities/events.filter";
2121
import { ScriptQuery } from "./script.query";
22+
import { TimeUtils } from "src/utils/time.utils";
2223

2324
@Injectable()
2425
export class ElasticIndexerHelper {
@@ -99,7 +100,14 @@ export class ElasticIndexerHelper {
99100
}
100101

101102
if (filter.before || filter.after) {
102-
elasticQuery = elasticQuery.withDateRangeFilter('timestamp', filter.before, filter.after);
103+
if (filter.before) {
104+
const timestampBeforeIdentifier = TimeUtils.isTimestampInSeconds(filter.before) ? 'timestamp' : 'timestampMs';
105+
elasticQuery = elasticQuery.withRangeFilter(timestampBeforeIdentifier, new RangeLowerThanOrEqual(filter.before));
106+
}
107+
if (filter.after) {
108+
const timestampAfterIdentifier = TimeUtils.isTimestampInSeconds(filter.after) ? 'timestamp' : 'timestampMs';
109+
elasticQuery = elasticQuery.withRangeFilter(timestampAfterIdentifier, new RangeGreaterThanOrEqual(filter.after));
110+
}
103111
}
104112

105113
if (filter.canCreate !== undefined) {
@@ -278,8 +286,13 @@ export class ElasticIndexerHelper {
278286
}
279287
}
280288

281-
if (filter.before || filter.after) {
282-
elasticQuery = elasticQuery.withDateRangeFilter('timestamp', filter.before, filter.after);
289+
if (filter.before) {
290+
const timestampBeforeIdentifier = TimeUtils.isTimestampInSeconds(filter.before) ? 'timestamp' : 'timestampMs';
291+
elasticQuery = elasticQuery.withRangeFilter(timestampBeforeIdentifier, new RangeLowerThanOrEqual(filter.before));
292+
}
293+
if (filter.after) {
294+
const timestampAfterIdentifier = TimeUtils.isTimestampInSeconds(filter.after) ? 'timestamp' : 'timestampMs';
295+
elasticQuery = elasticQuery.withRangeFilter(timestampAfterIdentifier, new RangeGreaterThanOrEqual(filter.after));
283296
}
284297

285298
if (filter.nonceBefore) {
@@ -408,8 +421,13 @@ export class ElasticIndexerHelper {
408421
elasticQuery = elasticQuery.withCondition(QueryConditionOptions.must, QueryType.Match('status', filter.status));
409422
}
410423

411-
if (filter.before || filter.after) {
412-
elasticQuery = elasticQuery.withDateRangeFilter('timestamp', filter.before, filter.after);
424+
if (filter.before) {
425+
const timestampBeforeIdentifier = TimeUtils.isTimestampInSeconds(filter.before) ? 'timestamp' : 'timestampMs';
426+
elasticQuery = elasticQuery.withRangeFilter(timestampBeforeIdentifier, new RangeLowerThanOrEqual(filter.before));
427+
}
428+
if (filter.after) {
429+
const timestampAfterIdentifier = TimeUtils.isTimestampInSeconds(filter.after) ? 'timestamp' : 'timestampMs';
430+
elasticQuery = elasticQuery.withRangeFilter(timestampAfterIdentifier, new RangeGreaterThanOrEqual(filter.after));
413431
}
414432

415433
if (filter.senderOrReceiver) {
@@ -552,8 +570,16 @@ export class ElasticIndexerHelper {
552570
.withMustMatchCondition('miniBlockHash', filter.miniBlockHash)
553571
.withMustMultiShouldCondition(filter.hashes, hash => QueryType.Match('_id', hash))
554572
.withMustMatchCondition('status', filter.status)
555-
.withMustMultiShouldCondition(filter.tokens, token => QueryType.Match('tokens', token, QueryOperator.AND))
556-
.withDateRangeFilter('timestamp', filter.before, filter.after);
573+
.withMustMultiShouldCondition(filter.tokens, token => QueryType.Match('tokens', token, QueryOperator.AND));
574+
575+
if (filter.before) {
576+
const timestampBeforeIdentifier = TimeUtils.isTimestampInSeconds(filter.before) ? 'timestamp' : 'timestampMs';
577+
elasticQuery = elasticQuery.withRangeFilter(timestampBeforeIdentifier, new RangeLowerThanOrEqual(filter.before));
578+
}
579+
if (filter.after) {
580+
const timestampAfterIdentifier = TimeUtils.isTimestampInSeconds(filter.after) ? 'timestamp' : 'timestampMs';
581+
elasticQuery = elasticQuery.withRangeFilter(timestampAfterIdentifier, new RangeGreaterThanOrEqual(filter.after));
582+
}
557583

558584
if (filter.functions && filter.functions.length > 0) {
559585
if (filter.functions.length === 1 && filter.functions[0] === '') {
@@ -658,8 +684,13 @@ export class ElasticIndexerHelper {
658684

659685
let elasticQuery = ElasticQuery.create().withCondition(QueryConditionOptions.must, mustQueries);
660686

661-
if (filter && (filter.before || filter.after)) {
662-
elasticQuery = elasticQuery.withDateRangeFilter('timestamp', filter.before, filter.after);
687+
if (filter && filter.before) {
688+
const timestampBeforeIdentifier = TimeUtils.isTimestampInSeconds(filter.before) ? 'timestamp' : 'timestampMs';
689+
elasticQuery = elasticQuery.withRangeFilter(timestampBeforeIdentifier, new RangeLowerThanOrEqual(filter.before));
690+
}
691+
if (filter && filter.after) {
692+
const timestampAfterIdentifier = TimeUtils.isTimestampInSeconds(filter.after) ? 'timestamp' : 'timestampMs';
693+
elasticQuery = elasticQuery.withRangeFilter(timestampAfterIdentifier, new RangeGreaterThanOrEqual(filter.after));
663694
}
664695

665696
if (filter && filter.identifiers) {
@@ -764,11 +795,13 @@ export class ElasticIndexerHelper {
764795
let elasticQuery = ElasticQuery.create();
765796

766797
if (filter.after) {
767-
elasticQuery = elasticQuery.withRangeFilter('timestamp', new RangeGreaterThanOrEqual(filter.after));
798+
const timestampIdentifier = TimeUtils.isTimestampInSeconds(filter.after) ? 'timestamp' : 'timestampMs';
799+
elasticQuery = elasticQuery.withRangeFilter(timestampIdentifier, new RangeGreaterThanOrEqual(filter.after));
768800
}
769801

770802
if (filter.before) {
771-
elasticQuery = elasticQuery.withRangeFilter('timestamp', new RangeLowerThanOrEqual(filter.before));
803+
const timestampIdentifier = TimeUtils.isTimestampInSeconds(filter.before) ? 'timestamp' : 'timestampMs';
804+
elasticQuery = elasticQuery.withRangeFilter(timestampIdentifier, new RangeLowerThanOrEqual(filter.before));
772805
}
773806

774807
return elasticQuery;
@@ -791,11 +824,13 @@ export class ElasticIndexerHelper {
791824
let elasticQuery = ElasticQuery.create();
792825

793826
if (filter.before) {
794-
elasticQuery = elasticQuery.withRangeFilter('timestamp', new RangeLowerThanOrEqual(filter.before));
827+
const timestampIdentifier = TimeUtils.isTimestampInSeconds(filter.before) ? 'timestamp' : 'timestampMs';
828+
elasticQuery = elasticQuery.withRangeFilter(timestampIdentifier, new RangeLowerThanOrEqual(filter.before));
795829
}
796830

797831
if (filter.after) {
798-
elasticQuery = elasticQuery.withRangeFilter('timestamp', new RangeGreaterThanOrEqual(filter.after));
832+
const timestampIdentifier = TimeUtils.isTimestampInSeconds(filter.after) ? 'timestamp' : 'timestampMs';
833+
elasticQuery = elasticQuery.withRangeFilter(timestampIdentifier, new RangeGreaterThanOrEqual(filter.after));
799834
}
800835

801836
if (filter.identifier) {

src/common/indexer/elastic/elastic.indexer.service.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ import { NftType } from "../entities/nft.type";
3030
import { EventsFilter } from "src/endpoints/events/entities/events.filter";
3131
import { Events } from "../entities/events";
3232
import { EsCircuitBreakerProxy } from "./circuit-breaker/circuit.breaker.proxy.service";
33+
import { TimeUtils } from "src/utils/time.utils";
3334

3435
@Injectable()
3536
export class ElasticIndexerService implements IndexerInterface {
@@ -1031,8 +1032,9 @@ export class ElasticIndexerService implements IndexerInterface {
10311032
}
10321033

10331034
async getBlockByTimestampAndShardId(timestamp: number, shardId: number): Promise<Block | undefined> {
1035+
const timestampIdentifier = TimeUtils.isTimestampInSeconds(timestamp) ? 'timestamp' : 'timestampMs';
10341036
const elasticQuery = ElasticQuery.create()
1035-
.withRangeFilter('timestamp', new RangeGreaterThanOrEqual(timestamp))
1037+
.withRangeFilter(timestampIdentifier, new RangeGreaterThanOrEqual(timestamp))
10361038
.withCondition(QueryConditionOptions.must, [QueryType.Match('shardId', shardId, QueryOperator.AND)])
10371039
.withSort([{ name: 'timestamp', order: ElasticSortOrder.ascending }]);
10381040

src/common/indexer/entities/block.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ export interface Block {
1212
size: number;
1313
sizeTxs: number;
1414
timestamp: number;
15+
timestampMs?: number;
1516
stateRootHash: string;
1617
prevHash: string;
1718
shardId: number;

0 commit comments

Comments
 (0)