From 131d2b34d9d1f84782d749c9943a7da5ab9dab8a Mon Sep 17 00:00:00 2001 From: Florian Dold Date: Fri, 27 Mar 2020 23:37:02 +0530 Subject: [PATCH] generate cleaner history for recoup --- src/operations/history.ts | 1 + src/operations/recoup.ts | 39 ++++++++++++++++++++++----------------- src/types/dbTypes.ts | 11 +++++++++++ src/types/history.ts | 1 + 4 files changed, 35 insertions(+), 17 deletions(-) diff --git a/src/operations/history.ts b/src/operations/history.ts index c09aa8d30..b19b9f195 100644 --- a/src/operations/history.ts +++ b/src/operations/history.ts @@ -492,6 +492,7 @@ export async function getHistory( type: HistoryEventType.FundsRecouped, timestamp: rg.timestampFinished, eventId: makeEventId(HistoryEventType.FundsRecouped, rg.recoupGroupId), + numCoinsRecouped: rg.coinPubs.length, }); } }); diff --git a/src/operations/recoup.ts b/src/operations/recoup.ts index de2e6c9a8..4c6eaf3b6 100644 --- a/src/operations/recoup.ts +++ b/src/operations/recoup.ts @@ -72,10 +72,14 @@ async function incrementRecoupRetry( } async function putGroupAsFinished( + ws: InternalWalletState, tx: TransactionHandle, recoupGroup: RecoupGroupRecord, coinIdx: number, ): Promise { + if (recoupGroup.timestampFinished) { + return; + } recoupGroup.recoupFinishedPerCoin[coinIdx] = true; let allFinished = true; for (const b of recoupGroup.recoupFinishedPerCoin) { @@ -87,6 +91,16 @@ async function putGroupAsFinished( recoupGroup.timestampFinished = getTimestampNow(); recoupGroup.retryInfo = initRetryInfo(false); recoupGroup.lastError = undefined; + if (recoupGroup.scheduleRefreshCoins.length > 0) { + const refreshGroupId = await createRefreshGroup( + tx, + recoupGroup.scheduleRefreshCoins.map((x) => ({ coinPub: x })), + RefreshReason.Recoup, + ); + processRefreshGroup(ws, refreshGroupId.refreshGroupId).then((e) => { + console.error("error while refreshing after recoup", e); + }); + } } await tx.put(Stores.recoupGroups, recoupGroup); } @@ -108,7 +122,7 @@ async function recoupTipCoin( if (recoupGroup.recoupFinishedPerCoin[coinIdx]) { return; } - await putGroupAsFinished(tx, recoupGroup, coinIdx); + await putGroupAsFinished(ws, tx, recoupGroup, coinIdx); }); } @@ -179,7 +193,7 @@ async function recoupWithdrawCoin( updatedReserve.reserveStatus = ReserveRecordStatus.QUERYING_STATUS; await tx.put(Stores.coins, updatedCoin); await tx.put(Stores.reserves, updatedReserve); - await putGroupAsFinished(tx, recoupGroup, coinIdx); + await putGroupAsFinished(ws, tx, recoupGroup, coinIdx); }, ); @@ -227,7 +241,7 @@ async function recoupRefreshCoin( return; } - const refreshGroupId = await ws.db.runWithWriteTransaction( + await ws.db.runWithWriteTransaction( [Stores.coins, Stores.reserves, Stores.recoupGroups, Stores.refreshGroups], async (tx) => { const recoupGroup = await tx.get(Stores.recoupGroups, recoupGroupId); @@ -254,22 +268,12 @@ async function recoupRefreshCoin( "recoup: setting old coin amount to", Amounts.toString(oldCoin.currentAmount), ); + recoupGroup.scheduleRefreshCoins.push(oldCoin.coinPub); await tx.put(Stores.coins, revokedCoin); await tx.put(Stores.coins, oldCoin); - await putGroupAsFinished(tx, recoupGroup, coinIdx); - return await createRefreshGroup( - tx, - [{ coinPub: oldCoin.coinPub }], - RefreshReason.Recoup, - ); + await putGroupAsFinished(ws, tx, recoupGroup, coinIdx); }, ); - - if (refreshGroupId) { - processRefreshGroup(ws, refreshGroupId.refreshGroupId).then((e) => { - console.error("error while refreshing after recoup", e); - }); - } } async function resetRecoupGroupRetry( @@ -340,17 +344,18 @@ export async function createRecoupGroup( recoupFinishedPerCoin: coinPubs.map(() => false), // Will be populated later oldAmountPerCoin: [], + scheduleRefreshCoins: [], }; for (let coinIdx = 0; coinIdx < coinPubs.length; coinIdx++) { const coinPub = coinPubs[coinIdx]; const coin = await tx.get(Stores.coins, coinPub); if (!coin) { - await putGroupAsFinished(tx, recoupGroup, coinIdx); + await putGroupAsFinished(ws, tx, recoupGroup, coinIdx); continue; } if (Amounts.isZero(coin.currentAmount)) { - await putGroupAsFinished(tx, recoupGroup, coinIdx); + await putGroupAsFinished(ws, tx, recoupGroup, coinIdx); continue; } recoupGroup.oldAmountPerCoin[coinIdx] = coin.currentAmount; diff --git a/src/types/dbTypes.ts b/src/types/dbTypes.ts index c8c4ed617..5a0a653ee 100644 --- a/src/types/dbTypes.ts +++ b/src/types/dbTypes.ts @@ -1397,8 +1397,19 @@ export interface RecoupGroupRecord { */ recoupFinishedPerCoin: boolean[]; + /** + * We store old amount (i.e. before recoup) of recouped coins here, + * as the balance of a recouped coin is set to zero when the + * recoup group is created. + */ oldAmountPerCoin: AmountJson[]; + /** + * Public keys of coins that should be scheduled for refreshing + * after all individual recoups are done. + */ + scheduleRefreshCoins: string[]; + /** * Retry info. */ diff --git a/src/types/history.ts b/src/types/history.ts index f4a1d0631..b1ac0ef9d 100644 --- a/src/types/history.ts +++ b/src/types/history.ts @@ -349,6 +349,7 @@ export interface HistoryFundsDepositedToSelfEvent { */ export interface HistoryFundsRecoupedEvent { type: HistoryEventType.FundsRecouped; + numCoinsRecouped: number; } /**