fix cash-in-txs updating
This commit is contained in:
parent
fc33339997
commit
6a6075c120
3 changed files with 56 additions and 21 deletions
|
|
@ -9,8 +9,6 @@ const mapValuesWithKey = _.mapValues.convert({cap: false})
|
|||
|
||||
module.exports = {post, monitorPending}
|
||||
|
||||
const UPDATEABLE_FIELDS = ['fee', 'txHash', 'phone', 'error', 'send',
|
||||
'cryptoAtoms', 'fiat', 'timedout']
|
||||
const PENDING_INTERVAL = '1 day'
|
||||
const MAX_PENDING = 10
|
||||
|
||||
|
|
@ -43,10 +41,11 @@ function post (tx, pi) {
|
|||
|
||||
return db.tx(transaction)
|
||||
.then(txVector => {
|
||||
const [oldTx, newTx, newBills] = txVector
|
||||
const [oldTx,, newBills] = txVector
|
||||
const oldBills = oldTx ? oldTx.bills : []
|
||||
|
||||
return postProcess(txVector, pi)
|
||||
.then(changes => update(newTx, changes))
|
||||
.then(changes => update(oldTx, changes))
|
||||
.then(tx => _.merge({bills: _.concat(oldBills, newBills)}, tx))
|
||||
})
|
||||
}
|
||||
|
|
@ -57,17 +56,54 @@ function nilEqual (a, b) {
|
|||
return undefined
|
||||
}
|
||||
|
||||
function isMonotonic (oldField, newField, fieldKey) {
|
||||
if (_.isNil(newField)) return false
|
||||
if (_.isBoolean(oldField)) return oldField === newField || !oldField
|
||||
if (oldField.isBigNumber) return oldField.lte(newField)
|
||||
if (_.isNumber(oldField)) return oldField <= newField
|
||||
|
||||
throw new Error(`Unexpected value: ${oldField}`)
|
||||
}
|
||||
|
||||
function ensureRatchet (oldField, newField, fieldKey) {
|
||||
const monotonic = ['cryptoAtoms', 'fiat', 'send', 'sendConfirmed', 'operatorCompleted', 'timedout']
|
||||
const free = ['sendPending', 'error', 'errorCode']
|
||||
|
||||
if (_.isNil(oldField)) return true
|
||||
if (_.includes(fieldKey, monotonic)) return isMonotonic(oldField, newField, fieldKey)
|
||||
|
||||
if (_.includes(fieldKey, free)) {
|
||||
if (_.isNil(newField)) return false
|
||||
return true
|
||||
}
|
||||
|
||||
logger.error('This field [%s] should never change', fieldKey)
|
||||
logger.error('oldField: %j', oldField)
|
||||
logger.error('newField: %j', newField)
|
||||
throw new Error(`This field [${fieldKey}] should never change`)
|
||||
}
|
||||
|
||||
function diff (oldTx, newTx) {
|
||||
let updatedTx = {}
|
||||
|
||||
UPDATEABLE_FIELDS.forEach(fieldKey => {
|
||||
if (oldTx && _.isEqualWith(nilEqual, oldTx[fieldKey], newTx[fieldKey])) return
|
||||
if (!oldTx) throw new Error('oldTx must not be null')
|
||||
if (!newTx) throw new Error('newTx must not be null')
|
||||
|
||||
// We never null out an existing field
|
||||
if (oldTx && _.isNil(newTx[fieldKey])) return
|
||||
_.forEach(fieldKey => {
|
||||
const oldField = oldTx[fieldKey]
|
||||
const newField = newTx[fieldKey]
|
||||
if (fieldKey === 'bills') return
|
||||
if (_.isEqualWith(nilEqual, oldField, newField)) return
|
||||
|
||||
updatedTx[fieldKey] = newTx[fieldKey]
|
||||
})
|
||||
if (!ensureRatchet(oldField, newField, fieldKey)) {
|
||||
logger.warn('Value from lamassu-machine would violate ratchet [%s]', fieldKey)
|
||||
logger.warn('Old tx: %j', oldTx)
|
||||
logger.warn('New tx: %j', newTx)
|
||||
return
|
||||
}
|
||||
|
||||
updatedTx[fieldKey] = newField
|
||||
}, _.keys(newTx))
|
||||
|
||||
return updatedTx
|
||||
}
|
||||
|
|
@ -85,6 +121,11 @@ function toObj (row) {
|
|||
return
|
||||
}
|
||||
|
||||
if (key === 'device_time') {
|
||||
newObj[objKey] = parseInt(row[key], 10)
|
||||
return
|
||||
}
|
||||
|
||||
newObj[objKey] = row[key]
|
||||
})
|
||||
|
||||
|
|
@ -128,14 +169,14 @@ function insertNewBills (billRows, tx) {
|
|||
.then(() => bills)
|
||||
}
|
||||
|
||||
function upsert (oldTx, tx) {
|
||||
function upsert (oldTx, newTx) {
|
||||
if (!oldTx) {
|
||||
return insert(tx)
|
||||
.then(newTx => [oldTx, newTx])
|
||||
return insert(newTx)
|
||||
.then(tx => [oldTx, tx])
|
||||
}
|
||||
|
||||
return update(tx, diff(oldTx, tx))
|
||||
.then(newTx => [oldTx, newTx])
|
||||
return update(oldTx, diff(oldTx, newTx))
|
||||
.then(tx => [oldTx, tx])
|
||||
}
|
||||
|
||||
function insert (tx) {
|
||||
|
|
@ -235,7 +276,6 @@ function monitorPending (settings) {
|
|||
}
|
||||
|
||||
return db.any(sql, [PENDING_INTERVAL, MAX_PENDING])
|
||||
.then(_.tap(console.log))
|
||||
.then(rows => Promise.all(_.map(processPending, rows)))
|
||||
.catch(logger.error)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -17,7 +17,6 @@ function sendMessage (account, rec) {
|
|||
from: account.fromNumber
|
||||
}
|
||||
|
||||
|
||||
return client.sendMessage(opts)
|
||||
.catch(err => {
|
||||
if (_.includes(err.code, BAD_NUMBER_CODES)) {
|
||||
|
|
|
|||
|
|
@ -44,15 +44,11 @@ function balance (settings, cryptoCode) {
|
|||
}
|
||||
|
||||
function sendCoins (settings, toAddress, cryptoAtoms, cryptoCode) {
|
||||
console.log('DEBUG40')
|
||||
return fetchWallet(settings, cryptoCode)
|
||||
.then(r => {
|
||||
console.log('DEBUG41')
|
||||
return r.wallet.sendCoins(r.account, toAddress, cryptoAtoms, cryptoCode)
|
||||
.then(res => {
|
||||
console.log('DEBUG42')
|
||||
mem.clear(module.exports.balance)
|
||||
console.log('DEBUG43: %j', res)
|
||||
return res
|
||||
})
|
||||
})
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue