-
Notifications
You must be signed in to change notification settings - Fork 0
/
MemPool.js
109 lines (78 loc) · 2.81 KB
/
MemPool.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
'use strict';
const BitcoinMessage = require('bitcoinjs-message');
const ValidationRequest = require('./ValidationRequest.js');
const ValidRequest = require('./ValidRequest.js');
/**
* Temporary stores requests waiting for validation.
* @param timeout - defines how long requests should be available for validation
*/
class MemPool {
constructor(timeout) {
this.timeoutRequests = [];
this.mempool = [];
this.mempoolValid = [];
this.validationTimeout = timeout;
}
addRequestValidation(address){
const self = this;
const req = this.mempool[address];
if (!req){
this.mempool[address] = new ValidationRequest(
address,
this.currentTimestamp(),
this.validationTimeout / 1000);
this.timeoutRequests[address] =
setTimeout(() => {
self.removeValidationRequest(address);
}, this.validationTimeout);
return this.mempool[address];
}
return this.verifyTimeLeft(req);
}
validateRequestByWallet(address, signature) {
return new Promise((resolve, reject) => {
const req = this.mempool[address];
if (req && this.verifyTimeLeft(req).validationWindow > 0) {
if (this.verifySignature(req, signature)){
return resolve(this.moveToValidMempool(req));
}
reject(`Failed to verify signature for validation request with address: '${address}'`);
}
else {
reject(`No pending validation request for address: '${address}'`);
}
});
}
verifyAddressRequest(address){
if (this.mempoolValid[address] !== undefined) {
delete this.mempoolValid[address];
return true;
}
return false;
}
verifyTimeLeft(req){
const timeElapse = this.currentTimestamp() - req.requestTimeStamp;
const timeLeft = (this.validationTimeout / 1000) - timeElapse;
req.validationWindow = timeLeft;
return req;
}
verifySignature(req, signature){
req.messageSignature = BitcoinMessage.verify(req.message, req.walletAddress, signature);
return req.messageSignature;
}
moveToValidMempool(req){
const validRequest = new ValidRequest(req);
this.mempoolValid[req.walletAddress] = validRequest;
delete this.timeoutRequests[req.walletAddress];
delete this.mempool[req.walletAddress];
return validRequest;
}
currentTimestamp() {
return (new Date().getTime().toString().slice(0,-3));
}
removeValidationRequest(address){
delete this.mempool[address];
delete this.timeoutRequests[address];
}
}
module.exports = MemPool;