gnunet-svn
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[taler-wallet-core] branch master updated: taler-harness: test aborting


From: gnunet
Subject: [taler-wallet-core] branch master updated: taler-harness: test aborting refreshes
Date: Wed, 06 Mar 2024 11:02:17 +0100

This is an automated email from the git hooks/post-receive script.

dold pushed a commit to branch master
in repository wallet-core.

The following commit(s) were added to refs/heads/master by this push:
     new 541886750 taler-harness: test aborting refreshes
541886750 is described below

commit 541886750eb1bc32b9aa0323868dd24776baf0eb
Author: Florian Dold <florian@dold.me>
AuthorDate: Wed Mar 6 11:02:13 2024 +0100

    taler-harness: test aborting refreshes
---
 .../src/integrationtests/test-wallet-refresh.ts    | 60 ++++++++++++++-
 packages/taler-harness/tsconfig.json               |  2 +-
 packages/taler-wallet-core/src/index.ts            |  2 +
 .../taler-wallet-core/src/pay-peer-pull-debit.ts   | 50 ++++++-------
 packages/taler-wallet-core/src/refresh.ts          | 85 +++++++++++-----------
 5 files changed, 127 insertions(+), 72 deletions(-)

diff --git a/packages/taler-harness/src/integrationtests/test-wallet-refresh.ts 
b/packages/taler-harness/src/integrationtests/test-wallet-refresh.ts
index b86dfadcf..f1c544a4e 100644
--- a/packages/taler-harness/src/integrationtests/test-wallet-refresh.ts
+++ b/packages/taler-harness/src/integrationtests/test-wallet-refresh.ts
@@ -20,12 +20,15 @@
 import {
   AmountString,
   NotificationType,
+  TransactionIdStr,
   TransactionMajorState,
   TransactionType,
   j2s,
 } from "@gnu-taler/taler-util";
-import { WalletApiOperation } from "@gnu-taler/taler-wallet-core";
-import { parseTransactionIdentifier } from 
"../../../taler-wallet-core/src/transactions.js";
+import {
+  WalletApiOperation,
+  parseTransactionIdentifier,
+} from "@gnu-taler/taler-wallet-core";
 import { GlobalTestState, generateRandomPayto } from "../harness/harness.js";
 import {
   createSimpleTestkudosEnvironmentV2,
@@ -139,6 +142,59 @@ export async function runWalletRefreshTest(t: 
GlobalTestState) {
       bal2.balances[0].available,
     );
   }
+
+  const wres = await withdrawViaBankV2(t, {
+    walletClient,
+    bank,
+    exchange,
+    amount: "TESTKUDOS:20",
+  });
+
+  await wres.withdrawalFinishedCond;
+
+  // Test failing a refresh transaction
+  {
+    await exchange.stop();
+
+    let refreshTransactionId: TransactionIdStr | undefined = undefined;
+
+    const refreshCreatedCond = walletClient.waitForNotificationCond((x) => {
+      if (
+        x.type === NotificationType.TransactionStateTransition &&
+        parseTransactionIdentifier(x.transactionId)?.tag ===
+          TransactionType.Refresh
+      ) {
+        refreshTransactionId = x.transactionId as TransactionIdStr;
+        return true;
+      }
+      return false;
+    });
+
+    const depositGroupResult = await walletClient.client.call(
+      WalletApiOperation.CreateDepositGroup,
+      {
+        amount: "TESTKUDOS:10.5" as AmountString,
+        depositPaytoUri: generateRandomPayto("foo"),
+      },
+    );
+
+    await refreshCreatedCond;
+
+    t.assertTrue(!!refreshTransactionId);
+
+    await walletClient.call(WalletApiOperation.FailTransaction, {
+      transactionId: refreshTransactionId,
+    });
+
+    const txn = await walletClient.call(WalletApiOperation.GetTransactionById, 
{
+      transactionId: refreshTransactionId,
+    });
+
+    t.assertDeepEqual(txn.type, TransactionType.Refresh);
+    t.assertDeepEqual(txn.txState.major, TransactionMajorState.Failed);
+
+    t.assertTrue(!!refreshTransactionId);
+  }
 }
 
 runWalletRefreshTest.suites = ["wallet"];
diff --git a/packages/taler-harness/tsconfig.json 
b/packages/taler-harness/tsconfig.json
index 3d0b501b3..0453aaff0 100644
--- a/packages/taler-harness/tsconfig.json
+++ b/packages/taler-harness/tsconfig.json
@@ -21,7 +21,7 @@
     "baseUrl": "./src",
     "typeRoots": ["./node_modules/@types"]
   },
-  "include": ["src/**/*", "../taler-util/src/merchant-api-types.ts"],
+  "include": ["src/**/*"],
   "references": [
     {
       "path": "../taler-wallet-core/"
diff --git a/packages/taler-wallet-core/src/index.ts 
b/packages/taler-wallet-core/src/index.ts
index fa984fc8f..fe2d3af15 100644
--- a/packages/taler-wallet-core/src/index.ts
+++ b/packages/taler-wallet-core/src/index.ts
@@ -32,6 +32,8 @@ export * from "./versions.js";
 export * from "./wallet-api-types.js";
 export * from "./wallet.js";
 
+export { parseTransactionIdentifier } from "./transactions.js";
+
 export { createPairTimeline } from "./denominations.js";
 
 // FIXME: Should these really be exported?!
diff --git a/packages/taler-wallet-core/src/pay-peer-pull-debit.ts 
b/packages/taler-wallet-core/src/pay-peer-pull-debit.ts
index 7348a30ce..2418f08da 100644
--- a/packages/taler-wallet-core/src/pay-peer-pull-debit.ts
+++ b/packages/taler-wallet-core/src/pay-peer-pull-debit.ts
@@ -26,7 +26,6 @@
 import {
   AcceptPeerPullPaymentResponse,
   Amounts,
-  CancellationToken,
   CoinRefreshRequest,
   ConfirmPeerPullDebitRequest,
   ContractTermsUtil,
@@ -95,7 +94,7 @@ import {
   notifyTransition,
   parseTransactionIdentifier,
 } from "./transactions.js";
-import { InternalWalletState, WalletExecutionContext } from "./wallet.js";
+import { WalletExecutionContext } from "./wallet.js";
 
 const logger = new Logger("pay-peer-pull-debit.ts");
 
@@ -552,15 +551,9 @@ export async function processPeerPullDebit(
 
   switch (peerPullInc.status) {
     case PeerPullDebitRecordStatus.PendingDeposit:
-      return await processPeerPullDebitPendingDeposit(
-        wex,
-        peerPullInc,
-      );
+      return await processPeerPullDebitPendingDeposit(wex, peerPullInc);
     case PeerPullDebitRecordStatus.AbortingRefresh:
-      return await processPeerPullDebitAbortingRefresh(
-        wex,
-        peerPullInc,
-      );
+      return await processPeerPullDebitAbortingRefresh(wex, peerPullInc);
   }
   return TaskRunResult.finished();
 }
@@ -791,23 +784,26 @@ export async function preparePeerPullDebit(
     coinSelRes.result.coins,
   );
 
-  await wex.db.runReadWriteTx(["peerPullDebit", "contractTerms"], async (tx) 
=> {
-    await tx.contractTerms.put({
-      h: contractTermsHash,
-      contractTermsRaw: contractTerms,
-    }),
-      await tx.peerPullDebit.add({
-        peerPullDebitId,
-        contractPriv: contractPriv,
-        exchangeBaseUrl: exchangeBaseUrl,
-        pursePub: pursePub,
-        timestampCreated: timestampPreciseToDb(TalerPreciseTimestamp.now()),
-        contractTermsHash,
-        amount: contractTerms.amount,
-        status: PeerPullDebitRecordStatus.DialogProposed,
-        totalCostEstimated: Amounts.stringify(totalAmount),
-      });
-  });
+  await wex.db.runReadWriteTx(
+    ["peerPullDebit", "contractTerms"],
+    async (tx) => {
+      await tx.contractTerms.put({
+        h: contractTermsHash,
+        contractTermsRaw: contractTerms,
+      }),
+        await tx.peerPullDebit.add({
+          peerPullDebitId,
+          contractPriv: contractPriv,
+          exchangeBaseUrl: exchangeBaseUrl,
+          pursePub: pursePub,
+          timestampCreated: timestampPreciseToDb(TalerPreciseTimestamp.now()),
+          contractTermsHash,
+          amount: contractTerms.amount,
+          status: PeerPullDebitRecordStatus.DialogProposed,
+          totalCostEstimated: Amounts.stringify(totalAmount),
+        });
+    },
+  );
 
   return {
     amount: contractTerms.amount,
diff --git a/packages/taler-wallet-core/src/refresh.ts 
b/packages/taler-wallet-core/src/refresh.ts
index c6ece1536..9c272ad18 100644
--- a/packages/taler-wallet-core/src/refresh.ts
+++ b/packages/taler-wallet-core/src/refresh.ts
@@ -107,7 +107,7 @@ import { getCandidateWithdrawalDenomsTx } from 
"./withdraw.js";
 const logger = new Logger("refresh.ts");
 
 export class RefreshTransactionContext implements TransactionContext {
-  public transactionId: TransactionIdStr;
+  readonly transactionId: TransactionIdStr;
   readonly taskId: TaskIdStr;
 
   constructor(
@@ -126,53 +126,54 @@ export class RefreshTransactionContext implements 
TransactionContext {
 
   async deleteTransaction(): Promise<void> {
     const refreshGroupId = this.refreshGroupId;
-    const ws = this.wex;
-    await ws.db.runReadWriteTx(["refreshGroups", "tombstones"], async (tx) => {
-      const rg = await tx.refreshGroups.get(refreshGroupId);
-      if (rg) {
-        await tx.refreshGroups.delete(refreshGroupId);
-        await tx.tombstones.put({
-          id: TombstoneTag.DeleteRefreshGroup + ":" + refreshGroupId,
-        });
-      }
-    });
+    await this.wex.db.runReadWriteTx(
+      ["refreshGroups", "tombstones"],
+      async (tx) => {
+        const rg = await tx.refreshGroups.get(refreshGroupId);
+        if (rg) {
+          await tx.refreshGroups.delete(refreshGroupId);
+          await tx.tombstones.put({
+            id: TombstoneTag.DeleteRefreshGroup + ":" + refreshGroupId,
+          });
+        }
+      },
+    );
   }
 
   async suspendTransaction(): Promise<void> {
     const { wex, refreshGroupId, transactionId } = this;
-    let res = await wex.db.runReadWriteTx(["refreshGroups"], async (tx) => {
-      const dg = await tx.refreshGroups.get(refreshGroupId);
-      if (!dg) {
-        logger.warn(
-          `can't suspend refresh group, refreshGroupId=${refreshGroupId} not 
found`,
-        );
-        return undefined;
-      }
-      const oldState = computeRefreshTransactionState(dg);
-      switch (dg.operationStatus) {
-        case RefreshOperationStatus.Finished:
+    let transitionInfo = await wex.db.runReadWriteTx(
+      ["refreshGroups"],
+      async (tx) => {
+        const dg = await tx.refreshGroups.get(refreshGroupId);
+        if (!dg) {
+          logger.warn(
+            `can't suspend refresh group, refreshGroupId=${refreshGroupId} not 
found`,
+          );
           return undefined;
-        case RefreshOperationStatus.Pending: {
-          dg.operationStatus = RefreshOperationStatus.Suspended;
-          await tx.refreshGroups.put(dg);
-          return {
-            oldTxState: oldState,
-            newTxState: computeRefreshTransactionState(dg),
-          };
         }
-        case RefreshOperationStatus.Suspended:
-          return undefined;
-      }
-      return undefined;
-    });
-    if (res) {
-      wex.ws.notify({
-        type: NotificationType.TransactionStateTransition,
-        transactionId,
-        oldTxState: res.oldTxState,
-        newTxState: res.newTxState,
-      });
-    }
+        const oldState = computeRefreshTransactionState(dg);
+        switch (dg.operationStatus) {
+          case RefreshOperationStatus.Finished:
+          case RefreshOperationStatus.Suspended:
+          case RefreshOperationStatus.Failed:
+            return undefined;
+          case RefreshOperationStatus.Pending: {
+            dg.operationStatus = RefreshOperationStatus.Suspended;
+            await tx.refreshGroups.put(dg);
+            break;
+          }
+          default:
+            assertUnreachable(dg.operationStatus);
+        }
+        return {
+          oldTxState: oldState,
+          newTxState: computeRefreshTransactionState(dg),
+        };
+      },
+    );
+    wex.taskScheduler.stopShepherdTask(this.taskId);
+    notifyTransition(wex, transactionId, transitionInfo);
   }
 
   async abortTransaction(): Promise<void> {

-- 
To stop receiving notification emails like this one, please contact
gnunet@gnunet.org.



reply via email to

[Prev in Thread] Current Thread [Next in Thread]