|
|
|
@ -49,29 +49,35 @@ class NonceTracker { |
|
|
|
|
await this._globalMutexFree() |
|
|
|
|
// await lock free, then take lock
|
|
|
|
|
const releaseLock = await this._takeMutex(address) |
|
|
|
|
// evaluate multiple nextNonce strategies
|
|
|
|
|
const nonceDetails = {} |
|
|
|
|
const networkNonceResult = await this._getNetworkNextNonce(address) |
|
|
|
|
const highestLocallyConfirmed = this._getHighestLocallyConfirmed(address) |
|
|
|
|
const nextNetworkNonce = networkNonceResult.nonce |
|
|
|
|
const highestSuggested = Math.max(nextNetworkNonce, highestLocallyConfirmed) |
|
|
|
|
|
|
|
|
|
const pendingTxs = this.getPendingTransactions(address) |
|
|
|
|
const localNonceResult = this._getHighestContinuousFrom(pendingTxs, highestSuggested) || 0 |
|
|
|
|
|
|
|
|
|
nonceDetails.params = { |
|
|
|
|
highestLocallyConfirmed, |
|
|
|
|
highestSuggested, |
|
|
|
|
nextNetworkNonce, |
|
|
|
|
try { |
|
|
|
|
// evaluate multiple nextNonce strategies
|
|
|
|
|
const nonceDetails = {} |
|
|
|
|
const networkNonceResult = await this._getNetworkNextNonce(address) |
|
|
|
|
const highestLocallyConfirmed = this._getHighestLocallyConfirmed(address) |
|
|
|
|
const nextNetworkNonce = networkNonceResult.nonce |
|
|
|
|
const highestSuggested = Math.max(nextNetworkNonce, highestLocallyConfirmed) |
|
|
|
|
|
|
|
|
|
const pendingTxs = this.getPendingTransactions(address) |
|
|
|
|
const localNonceResult = this._getHighestContinuousFrom(pendingTxs, highestSuggested) || 0 |
|
|
|
|
|
|
|
|
|
nonceDetails.params = { |
|
|
|
|
highestLocallyConfirmed, |
|
|
|
|
highestSuggested, |
|
|
|
|
nextNetworkNonce, |
|
|
|
|
} |
|
|
|
|
nonceDetails.local = localNonceResult |
|
|
|
|
nonceDetails.network = networkNonceResult |
|
|
|
|
|
|
|
|
|
const nextNonce = Math.max(networkNonceResult.nonce, localNonceResult.nonce) |
|
|
|
|
assert(Number.isInteger(nextNonce), `nonce-tracker - nextNonce is not an integer - got: (${typeof nextNonce}) "${nextNonce}"`) |
|
|
|
|
|
|
|
|
|
// return nonce and release cb
|
|
|
|
|
return { nextNonce, nonceDetails, releaseLock } |
|
|
|
|
} catch (err) { |
|
|
|
|
// release lock if we encounter an error
|
|
|
|
|
releaseLock() |
|
|
|
|
throw err |
|
|
|
|
} |
|
|
|
|
nonceDetails.local = localNonceResult |
|
|
|
|
nonceDetails.network = networkNonceResult |
|
|
|
|
|
|
|
|
|
const nextNonce = Math.max(networkNonceResult.nonce, localNonceResult.nonce) |
|
|
|
|
assert(Number.isInteger(nextNonce), `nonce-tracker - nextNonce is not an integer - got: (${typeof nextNonce}) "${nextNonce}"`) |
|
|
|
|
|
|
|
|
|
// return nonce and release cb
|
|
|
|
|
return { nextNonce, nonceDetails, releaseLock } |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
async _getCurrentBlock () { |
|
|
|
@ -85,8 +91,8 @@ class NonceTracker { |
|
|
|
|
|
|
|
|
|
async _globalMutexFree () { |
|
|
|
|
const globalMutex = this._lookupMutex('global') |
|
|
|
|
const release = await globalMutex.acquire() |
|
|
|
|
release() |
|
|
|
|
const releaseLock = await globalMutex.acquire() |
|
|
|
|
releaseLock() |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
async _takeMutex (lockId) { |
|
|
|
|