Skip to content

Commit c66c815

Browse files
committed
Merge remote-tracking branch 'origin/v1.4-dev' into feat/get-node-status-in-sdk
2 parents 5491d3f + 94128bd commit c66c815

18 files changed

Lines changed: 270 additions & 62 deletions

File tree

CHANGELOG.md

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,54 @@
1+
## [1.4.0-dev.1](https://github.com/dashpay/platform/compare/v1.3.0...v1.4.0-dev.1) (2024-09-27)
2+
3+
4+
### ⚠ BREAKING CHANGES
5+
6+
* **sdk:** change default network to mainnet (#2161)
7+
* **dashmate:** confirm a node reset (#2160)
8+
* **platform:** withdrawals polishing and fixes for mainnet (#2166)
9+
* **platform:** do not switch to oldest quorums in validator set update (#2167)
10+
11+
### Features
12+
13+
* **dashmate:** confirm a node reset ([#2160](https://github.com/dashpay/platform/issues/2160))
14+
* **platform:** do not switch to oldest quorums in validator set update ([#2167](https://github.com/dashpay/platform/issues/2167))
15+
* **platform:** get current quorum info ([#2168](https://github.com/dashpay/platform/issues/2168))
16+
* **platform:** withdrawals polishing and fixes for mainnet ([#2166](https://github.com/dashpay/platform/issues/2166))
17+
* **sdk:** change default network to mainnet ([#2161](https://github.com/dashpay/platform/issues/2161))
18+
19+
20+
### Bug Fixes
21+
22+
* **dapi:** getStatus cache invalidation ([#2155](https://github.com/dashpay/platform/issues/2155))
23+
* **dapi:** invalid mainnet seed ports ([#2173](https://github.com/dashpay/platform/issues/2173))
24+
* **dashmate:** cannot read properties of undefined (reading 'expires') ([#2164](https://github.com/dashpay/platform/issues/2164))
25+
* **dashmate:** colors[updated] is not a function ([#2157](https://github.com/dashpay/platform/issues/2157))
26+
* **dashmate:** doctor fails collecting to big logs ([#2158](https://github.com/dashpay/platform/issues/2158))
27+
* **dashmate:** port marks as closed if ipv6 is not disabled ([#2162](https://github.com/dashpay/platform/issues/2162))
28+
* **dashmate:** remove confusing short flag name ([#2165](https://github.com/dashpay/platform/issues/2165))
29+
30+
31+
### Continuous integration
32+
33+
* build dashmate package on macos14
34+
35+
36+
### Documentation
37+
38+
* **dashmate:** document logging configuration ([#2156](https://github.com/dashpay/platform/issues/2156))
39+
40+
41+
### Tests
42+
43+
* **dashmate:** e2e tests failing due to DKG interval check ([#2171](https://github.com/dashpay/platform/issues/2171))
44+
45+
46+
### Miscellaneous Chores
47+
48+
* **dashmate:** do not call mint on masternodes ([#2172](https://github.com/dashpay/platform/issues/2172))
49+
* **platform:** protocol version 4 creation ([#2153](https://github.com/dashpay/platform/issues/2153))
50+
51+
152
## [1.3.0](https://github.com/dashpay/platform/compare/v1.2.0...v1.3.0) (2024-09-19)
253

354
### Features

packages/dapi/lib/externalApis/tenderdash/BlockchainListener.js

Lines changed: 25 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,12 @@ class BlockchainListener extends EventEmitter {
1313
*/
1414
constructor(tenderdashWsClient) {
1515
super();
16+
1617
this.wsClient = tenderdashWsClient;
18+
19+
this.processLogger = logger.child({
20+
process: 'BlockchainListener',
21+
});
1722
}
1823

1924
/**
@@ -30,14 +35,7 @@ class BlockchainListener extends EventEmitter {
3035
* Subscribe to blocks and transaction results
3136
*/
3237
start() {
33-
const processLogger = logger.child({
34-
process: 'BlockchainListener',
35-
});
36-
37-
processLogger.info('Subscribed to state transition results');
38-
3938
// Emit transaction results
40-
this.wsClient.subscribe(TX_QUERY);
4139
this.wsClient.on(TX_QUERY, (message) => {
4240
const [hashString] = (message.events || []).map((event) => {
4341
const hashAttribute = event.attributes.find((attribute) => attribute.key === 'hash');
@@ -53,15 +51,31 @@ class BlockchainListener extends EventEmitter {
5351
return;
5452
}
5553

56-
processLogger.trace(`received transaction result for ${hashString}`);
54+
this.processLogger.trace(`Received transaction result for ${hashString}`);
5755

5856
this.emit(BlockchainListener.getTransactionEventName(hashString), message);
5957
});
6058

61-
// TODO: It's not using
6259
// Emit blocks and contained transactions
63-
// this.wsClient.subscribe(NEW_BLOCK_QUERY);
64-
// this.wsClient.on(NEW_BLOCK_QUERY, (message) => this.emit(EVENTS.NEW_BLOCK, message));
60+
this.wsClient.on(NEW_BLOCK_QUERY, (message) => {
61+
this.processLogger.trace('Received new platform block');
62+
63+
this.emit(EVENTS.NEW_BLOCK, message);
64+
});
65+
66+
this.wsClient.on('connect', () => {
67+
this.#subscribe();
68+
});
69+
70+
if (this.wsClient.isConnected) {
71+
this.#subscribe();
72+
}
73+
}
74+
75+
#subscribe() {
76+
this.wsClient.subscribe(TX_QUERY);
77+
this.wsClient.subscribe(NEW_BLOCK_QUERY);
78+
this.processLogger.debug('Subscribed to platform blockchain events');
6579
}
6680
}
6781

packages/dapi/lib/grpcServer/handlers/platform/getStatusHandlerFactory.js

Lines changed: 24 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ const {
99
} = require('@dashevo/dapi-grpc');
1010

1111
const BlockchainListener = require('../../../externalApis/tenderdash/BlockchainListener');
12+
const logger = require('../../../logger');
1213

1314
/**
1415
* @param {BlockchainListener} blockchainListener
@@ -17,12 +18,23 @@ const BlockchainListener = require('../../../externalApis/tenderdash/BlockchainL
1718
* @return {getStatusHandler}
1819
*/
1920
function getStatusHandlerFactory(blockchainListener, driveClient, tenderdashRpcClient) {
20-
// Clean cache when new platform block committed
2121
let cachedResponse = null;
22+
let cleanCacheTimeout = null;
2223

23-
blockchainListener.on(BlockchainListener.EVENTS.NEW_BLOCK, () => {
24+
function cleanCache() {
2425
cachedResponse = null;
25-
});
26+
27+
// cancel scheduled cache cleanup
28+
if (cleanCacheTimeout !== null) {
29+
clearTimeout(cleanCacheTimeout);
30+
cleanCacheTimeout = null;
31+
}
32+
33+
logger.trace({ endpoint: 'getStatus' }, 'cleanup cache');
34+
}
35+
36+
// Clean cache when new platform block committed
37+
blockchainListener.on(BlockchainListener.EVENTS.NEW_BLOCK, cleanCache);
2638

2739
// DAPI Software version
2840
const packageJsonPath = path.resolve(__dirname, '..', '..', '..', '..', 'package.json');
@@ -210,6 +222,15 @@ function getStatusHandlerFactory(blockchainListener, driveClient, tenderdashRpcC
210222
cachedResponse = new GetStatusResponse();
211223
cachedResponse.setV0(v0);
212224

225+
// Cancel any existing scheduled cache cleanup
226+
if (cleanCacheTimeout !== null) {
227+
clearTimeout(cleanCacheTimeout);
228+
cleanCacheTimeout = null;
229+
}
230+
231+
// Clean cache in 3 minutes
232+
cleanCacheTimeout = setTimeout(cleanCache, 3 * 60 * 1000);
233+
213234
return cachedResponse;
214235
}
215236

packages/dapi/test/integration/externalApis/tenderdash/BlockchainListener.spec.js

Lines changed: 15 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,8 @@ describe('BlockchainListener', () => {
1515
({ sinon } = this);
1616
wsClientMock = new EventEmitter();
1717
wsClientMock.subscribe = sinon.stub();
18+
1819
blockchainListener = new BlockchainListener(wsClientMock);
19-
blockchainListener.start();
2020

2121
sinon.spy(blockchainListener, 'on');
2222
sinon.spy(blockchainListener, 'off');
@@ -84,19 +84,23 @@ describe('BlockchainListener', () => {
8484
});
8585

8686
describe('#start', () => {
87-
it('should subscribe to transaction events from WS client', () => {
88-
// TODO: We don't use it for now
89-
// expect(wsClientMock.subscribe).to.be.calledTwice();
90-
expect(wsClientMock.subscribe).to.be.calledOnce();
87+
it('should subscribe to transaction events from WS client if it is connected', () => {
88+
wsClientMock.isConnected = true;
89+
90+
blockchainListener.start();
91+
92+
expect(wsClientMock.subscribe).to.be.calledTwice();
9193
expect(wsClientMock.subscribe.firstCall).to.be.calledWithExactly(
9294
BlockchainListener.TX_QUERY,
9395
);
94-
// expect(wsClientMock.subscribe.secondCall).to.be.calledWithExactly(
95-
// BlockchainListener.NEW_BLOCK_QUERY,
96-
// );
96+
expect(wsClientMock.subscribe.secondCall).to.be.calledWithExactly(
97+
BlockchainListener.NEW_BLOCK_QUERY,
98+
);
9799
});
98100

99-
it.skip('should emit block when new block is arrived', (done) => {
101+
it('should emit block when new block is arrived', (done) => {
102+
blockchainListener.start();
103+
100104
blockchainListener.on(BlockchainListener.EVENTS.NEW_BLOCK, (message) => {
101105
expect(message).to.be.deep.equal(blockMessageMock);
102106

@@ -107,6 +111,8 @@ describe('BlockchainListener', () => {
107111
});
108112

109113
it('should emit transaction when transaction is arrived', (done) => {
114+
blockchainListener.start();
115+
110116
const topic = BlockchainListener.getTransactionEventName(transactionHash);
111117

112118
blockchainListener.on(topic, (message) => {

packages/dashmate/src/commands/reset.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ export default class ResetCommand extends ConfigBaseCommand {
99

1010
static flags = {
1111
...ConfigBaseCommand.flags,
12-
hard: Flags.boolean({ char: 'h', description: 'reset config as well as services and data', default: false }),
12+
hard: Flags.boolean({ description: 'reset config as well as services and data', default: false }),
1313
force: Flags.boolean({ char: 'f', description: 'skip running services check', default: false }),
1414
platform: Flags.boolean({ char: 'p', description: 'reset platform services and data only', default: false }),
1515
verbose: Flags.boolean({ char: 'v', description: 'use verbose mode for output', default: false }),

packages/dashmate/src/commands/wallet/mint.js

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,10 @@ Mint given amount of tDash to a new or specified address
5151
throw new Error('Only local network supports generation of dash');
5252
}
5353

54+
if (config.get('core.masternode.enable')) {
55+
throw new Error('A masternode doesn\'t support generation of dash');
56+
}
57+
5458
const tasks = new Listr(
5559
[
5660
{

packages/dashmate/src/config/configJsonSchema.js

Lines changed: 32 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -404,28 +404,40 @@ export default {
404404
filePath: {
405405
type: ['null', 'string'],
406406
minLength: 1,
407+
description: 'Write logs only to stdout if null. Provide an absolute file path on'
408+
+ ' the host machine to also write to a log file there. Use a log file if logs must be'
409+
+ ' retained since stdout logs are stored inside the docker container'
410+
+ ' and removed if the container is removed.',
407411
},
408412
debug: {
409413
type: 'object',
410414
properties: {
411415
enabled: {
412416
type: 'boolean',
417+
description: 'Enable debug logging. Equivalent to setting "debug=1" in the Core configuration file)',
413418
},
414419
ips: {
415420
type: 'boolean',
421+
description: 'Include IP addresses in debug output',
416422
},
417423
sourceLocations: {
418424
type: 'boolean',
425+
description: 'Prepend debug output with name of the originating source'
426+
+ ' location (source file, line number and function name)',
419427
},
420428
threadNames: {
421429
type: 'boolean',
430+
description: 'Prepend debug output with name of the originating thread (only'
431+
+ ' available on platforms supporting thread_local)',
422432
},
423433
timeMicros: {
424434
type: 'boolean',
435+
description: 'Add microsecond precision to debug timestamps',
425436
},
426437
includeOnly: {
427438
type: 'array',
428439
uniqueItems: true,
440+
description: 'Log all categories if empty. Otherwise, log only the specified categories.',
429441
items: {
430442
type: 'string',
431443
enum: ['net', 'tor', 'mempool', 'http', 'bench', 'zmq', 'walletdb', 'rpc', 'estimatefee',
@@ -437,6 +449,7 @@ export default {
437449
},
438450
exclude: {
439451
type: 'array',
452+
description: 'Exclude debugging information for one or more categories.',
440453
uniqueItems: true,
441454
items: {
442455
type: 'string',
@@ -654,10 +667,12 @@ export default {
654667
properties: {
655668
level: {
656669
type: 'string',
670+
description: 'Log level for gateway container logs',
657671
enum: ['trace', 'debug', 'info', 'warn', 'error', 'critical', 'off'],
658672
},
659673
accessLogs: {
660674
type: 'array',
675+
description: 'Envoy access logs',
661676
items: {
662677
oneOf: [
663678
{
@@ -667,7 +682,8 @@ export default {
667682
type: 'string',
668683
minLength: 1,
669684
enum: ['stdout', 'stderr'],
670-
description: 'Access log type: stdout, stderr or file',
685+
description: 'stdout, stderr or file (absolute file path on host'
686+
+ ' machine)',
671687
},
672688
format: {
673689
type: 'string',
@@ -693,7 +709,9 @@ export default {
693709
additionalProperties: {
694710
type: 'string',
695711
},
696-
description: 'JSON fields and values. If null, default template is used.',
712+
description: 'JSON fields and values. If null, default template is'
713+
+ ' used. More info:'
714+
+ ' https://www.envoyproxy.io/docs/envoy/latest/configuration/observability/access_log/usage#format-dictionaries',
697715
},
698716
},
699717
required: ['template'],
@@ -703,7 +721,9 @@ export default {
703721
properties: {
704722
template: {
705723
type: ['null', 'string'],
706-
description: 'Template string. If null, default template is used.',
724+
description: 'Template string. If null, default template is used.'
725+
+ ' More info:'
726+
+ ' https://www.envoyproxy.io/docs/envoy/latest/configuration/observability/access_log/usage#format-strings',
707727
},
708728
},
709729
required: ['template'],
@@ -827,6 +847,7 @@ export default {
827847
},
828848
logs: {
829849
type: 'object',
850+
description: 'Define Drive logs',
830851
propertyNames: {
831852
type: 'string',
832853
minLength: 1,
@@ -847,10 +868,13 @@ export default {
847868
},
848869
format: {
849870
type: 'string',
871+
description: 'Log format:'
872+
+ ' https://docs.rs/tracing-subscriber/latest/tracing_subscriber/fmt/format/index.html',
850873
enum: ['full', 'compact', 'pretty', 'json'],
851874
},
852875
color: {
853876
type: ['boolean', 'null'],
877+
description: 'Whether or not to use colorful output; defaults to autodetect',
854878
},
855879
},
856880
required: ['destination', 'level', 'format', 'color'],
@@ -1115,17 +1139,21 @@ export default {
11151139
level: {
11161140
type: 'string',
11171141
enum: ['trace', 'debug', 'info', 'warn', 'error'],
1142+
description: 'Log verbosity level',
11181143
},
11191144
format: {
11201145
type: 'string',
11211146
enum: ['plain', 'json'],
1147+
description: 'Log format: text or json',
11221148
},
11231149
path: {
11241150
type: ['string', 'null'],
11251151
minLength: 1,
1152+
description: 'Write to stdout only if null or to stdout and specified log'
1153+
+ ' file (absolute file path on host machine)',
11261154
},
11271155
},
1128-
required: ['level', 'format'],
1156+
required: ['level', 'format', 'path'],
11291157
additionalProperties: false,
11301158
},
11311159
rpc: {

packages/dashmate/src/doctor/analyse/analyseConfigFactory.js

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -134,6 +134,10 @@ and revoke the previous certificate in the ZeroSSL dashboard`,
134134
description: chalk`ZeroSSL certificate is not valid.`,
135135
solution: chalk`Please run {bold.cyanBright dashmate ssl zerossl obtain} to get a new one.`,
136136
},
137+
[ERRORS.ZERO_SSL_API_ERROR]: {
138+
description: ssl?.data?.error?.message,
139+
solution: chalk`Please contact ZeroSSL support if needed.`,
140+
},
137141
}[ssl.error] ?? {};
138142

139143
if (description) {

0 commit comments

Comments
 (0)