diff options
37 files changed, 664 insertions, 451 deletions
diff --git a/packages/taler-harness/src/harness/harness.ts b/packages/taler-harness/src/harness/harness.ts index 8f1f3f452..926a0c93b 100644 --- a/packages/taler-harness/src/harness/harness.ts +++ b/packages/taler-harness/src/harness/harness.ts @@ -563,7 +563,7 @@ export async function pingProc( return; } catch (e: any) { logger.warn(`service ${serviceName} not ready:`, e.toString()); - logger.info(`waiting ${nextDelay}ms`); + logger.info(`waiting ${nextDelay}ms on ${serviceName}`); await delayMs(nextDelay); nextDelay = backoffIncrement(nextDelay); } @@ -905,7 +905,7 @@ export class FakebankService config.setString("bank", "max_debt", bc.maxDebt ?? `${bc.currency}:100`); config.setString("bank", "ram_limit", `${1024}`); const cfgFilename = testDir + "/bank.conf"; - config.write(cfgFilename); + config.write(cfgFilename, { excludeDefaults: true }); return new FakebankService(gc, bc, cfgFilename); } @@ -934,7 +934,7 @@ export class FakebankService } const config = Configuration.load(this.configFile); config.setString("bank", "suggested_exchange", e.baseUrl); - config.write(this.configFile); + config.write(this.configFile, { excludeDefaults: true }); } get baseUrl(): string { @@ -1037,7 +1037,9 @@ export class ExchangeService implements ExchangeServiceInterface { name: exchangeName, roundUnit: config.getString("taler", "currency_round_unit").required(), }; - const privFile = config.getPath("exchange", "master_priv_file").required(); + const privFile = config + .getPath("exchange-offline", "master_priv_file") + .required(); const eddsaPriv = fs.readFileSync(privFile); const keyPair: EddsaKeyPair = { eddsaPriv, @@ -1135,7 +1137,7 @@ export class ExchangeService implements ExchangeServiceInterface { changeConfig(f: (config: Configuration) => void) { const config = Configuration.load(this.configFilename); f(config); - config.write(this.configFilename); + config.write(this.configFilename, { excludeDefaults: true }); } static create(gc: GlobalTestState, e: ExchangeConfig) { @@ -1184,10 +1186,16 @@ export class ExchangeService implements ExchangeServiceInterface { fs.mkdirSync(path.dirname(masterPrivFile), { recursive: true }); + if (fs.existsSync(masterPrivFile)) { + throw new Error( + "master priv file already exists, can't create new exchange config", + ); + } + fs.writeFileSync(masterPrivFile, Buffer.from(exchangeMasterKey.eddsaPriv)); const cfgFilename = testDir + `/exchange-${e.name}.conf`; - config.write(cfgFilename); + config.write(cfgFilename, { excludeDefaults: true }); return new ExchangeService(gc, e, cfgFilename, exchangeMasterKey); } @@ -1196,13 +1204,13 @@ export class ExchangeService implements ExchangeServiceInterface { offeredCoins.forEach((cc) => setCoin(config, cc(this.exchangeConfig.currency)), ); - config.write(this.configFilename); + config.write(this.configFilename, { excludeDefaults: true }); } addCoinConfigList(ccs: CoinConfig[]) { const config = Configuration.load(this.configFilename); ccs.forEach((cc) => setCoin(config, cc)); - config.write(this.configFilename); + config.write(this.configFilename, { excludeDefaults: true }); } enableAgeRestrictions(maskStr: string) { @@ -1213,7 +1221,7 @@ export class ExchangeService implements ExchangeServiceInterface { "age_groups", maskStr, ); - config.write(this.configFilename); + config.write(this.configFilename, { excludeDefaults: true }); } get masterPub() { @@ -1234,7 +1242,7 @@ export class ExchangeService implements ExchangeServiceInterface { ): Promise<void> { const config = Configuration.load(this.configFilename); await f(config); - config.write(this.configFilename); + config.write(this.configFilename, { excludeDefaults: true }); } async addBankAccount( @@ -1274,7 +1282,7 @@ export class ExchangeService implements ExchangeServiceInterface { "password", exchangeBankAccount.accountPassword, ); - config.write(this.configFilename); + config.write(this.configFilename, { excludeDefaults: true }); } exchangeHttpProc: ProcessWrapper | undefined; @@ -1535,19 +1543,25 @@ export class ExchangeService implements ExchangeServiceInterface { ); } - async start(opts: { skipSetup?: boolean } = {}): Promise<void> { + async dbinit() { + await sh( + this.globalState, + "exchange-dbinit", + `taler-exchange-dbinit -c "${this.configFilename}"`, + ); + } + + async start( + opts: { skipDbinit?: boolean; skipKeyup?: boolean } = {}, + ): Promise<void> { if (this.isRunning()) { throw Error("exchange is already running"); } - const skipSetup = opts.skipSetup ?? false; + const skipDbinit = opts.skipDbinit ?? false; - if (!skipSetup) { - await sh( - this.globalState, - "exchange-dbinit", - `taler-exchange-dbinit -c "${this.configFilename}"`, - ); + if (!skipDbinit) { + await this.dbinit(); } this.helperCryptoEddsaProc = this.globalState.spawnService( @@ -1579,7 +1593,10 @@ export class ExchangeService implements ExchangeServiceInterface { ); await this.pingUntilAvailable(); - if (!skipSetup) { + + const skipKeyup = opts.skipKeyup ?? false; + + if (!skipKeyup) { await this.keyup(); } else { logger.info("skipping keyup"); @@ -1921,16 +1938,23 @@ export class MerchantService implements MerchantServiceInterface { } } - async start(opts: { skipSetup?: boolean } = {}): Promise<void> { - const skipSetup = opts.skipSetup ?? false; + async dbinit() { + await runCommand( + this.globalState, + "merchant-dbinit", + "taler-merchant-dbinit", + ["-c", this.configFilename], + ); + } + + /** + * Start the merchant, + */ + async start(opts: { skipDbinit?: boolean } = {}): Promise<void> { + const skipSetup = opts.skipDbinit ?? false; if (!skipSetup) { - await runCommand( - this.globalState, - "merchant-dbinit", - "taler-merchant-dbinit", - ["-c", this.configFilename], - ); + await this.dbinit(); } this.proc = this.globalState.spawnService( @@ -1964,7 +1988,7 @@ export class MerchantService implements MerchantServiceInterface { "${TALER_DATA_HOME}/merchant/merchant.priv", ); config.setString("merchantdb-postgres", "config", mc.database); - config.write(cfgFilename); + config.write(cfgFilename, { excludeDefaults: true }); return new MerchantService(gc, mc, cfgFilename); } @@ -1982,7 +2006,7 @@ export class MerchantService implements MerchantServiceInterface { this.merchantConfig.currency, ); config.setString(`merchant-exchange-${e.name}`, "master_key", e.masterPub); - config.write(this.configFilename); + config.write(this.configFilename, { excludeDefaults: true }); } async addDefaultInstance(): Promise<void> { @@ -2303,7 +2327,8 @@ export class WalletService { try { await tryUnixConnect(this.socketPath); } catch (e) { - logger.info(`connection attempt failed: ${e}`); + logger.info(`wallet connection attempt failed: ${e}`); + logger.info(`waiting on wallet for ${nextDelay}ms`); await delayMs(nextDelay); nextDelay = backoffIncrement(nextDelay); continue; diff --git a/packages/taler-harness/src/harness/helpers.ts b/packages/taler-harness/src/harness/helpers.ts index 932854a1e..d41ffdd00 100644 --- a/packages/taler-harness/src/harness/helpers.ts +++ b/packages/taler-harness/src/harness/helpers.ts @@ -230,6 +230,11 @@ export async function useSharedTestkudosEnvironment(t: GlobalTestState) { logger.info(`previous setup done: ${prevSetupDone}`); + + // Wallet has longer startup-time and no dependencies, + // so we start it rather early. + const walletStartProm = createWalletDaemonWithClient(t, { name: "wallet" }) + if (fs.existsSync(sharedDir + "/bank.conf")) { logger.info("reusing existing bank"); bank = BankService.fromExistingConfig(t, { @@ -249,15 +254,19 @@ export async function useSharedTestkudosEnvironment(t: GlobalTestState) { logger.info("setting up exchange"); const exchangeName = "testexchange-1"; - const exchangeConfigFilename = sharedDir + `/exchange-${exchangeName}}`; + const exchangeConfigFilename = sharedDir + `/exchange-${exchangeName}.conf`; + + logger.info(`exchange config filename: ${exchangeConfigFilename}`); let exchange: ExchangeService; if (fs.existsSync(exchangeConfigFilename)) { + logger.info("reusing existing exchange config"); exchange = ExchangeService.fromExistingConfig(t, exchangeName, { overridePath: sharedDir, }); } else { + logger.info("creating new exchange config"); exchange = ExchangeService.create(t, { name: "testexchange-1", currency: "TESTKUDOS", @@ -305,22 +314,29 @@ export async function useSharedTestkudosEnvironment(t: GlobalTestState) { logger.info("basic setup done, starting services"); + if (!prevSetupDone) { + // Must be done sequentially, due to a concurrency + // issue in the *-dbinit tools. + await exchange.dbinit(); + await merchant.dbinit(); + } + const bankStart = async () => { await bank.start(); - await bank.pingUntilAvailable(); }; const exchangeStart = async () => { await exchange.start({ - skipSetup: prevSetupDone, + skipDbinit: true, + skipKeyup: prevSetupDone, }); await exchange.pingUntilAvailable(); }; const merchStart = async () => { await merchant.start({ - skipSetup: prevSetupDone, + skipDbinit: true, }); await merchant.pingUntilAvailable(); @@ -345,24 +361,22 @@ export async function useSharedTestkudosEnvironment(t: GlobalTestState) { } }; - const walletStart = async () => { - return await createWalletDaemonWithClient(t, { name: "wallet" }); - }; + await bankStart() const res = await Promise.all([ exchangeStart(), merchStart(), - bankStart(), - walletStart(), + undefined, + walletStartProm, ]); const walletClient = res[3].walletClient; const walletService = res[3].walletService; - console.log("setup done!"); - fs.writeFileSync(sharedDir + "/setup-done", "OK"); + logger.info("setup done!"); + return { commonDb: db, exchange, @@ -515,7 +529,7 @@ export async function createWalletDaemonWithClient( const walletClient = new WalletClient({ unixPath: walletService.socketPath, onNotification(n) { - console.log("got notification", n); + console.log(`got ${args.name} notification`, n); if (args.handleNotification) { args.handleNotification(n); } @@ -789,6 +803,8 @@ export async function applyTimeTravel( /** * Make a simple payment and check that it succeeded. + * + * @deprecated */ export async function makeTestPayment( t: GlobalTestState, diff --git a/packages/taler-harness/src/index.ts b/packages/taler-harness/src/index.ts index ec99232f5..a172bc9da 100644 --- a/packages/taler-harness/src/index.ts +++ b/packages/taler-harness/src/index.ts @@ -208,8 +208,10 @@ deploymentCli const bankAccessApiClient = new BankAccessApiClient({ baseUrl: args.tipTopup.bankAccessUrl, - username: args.tipTopup.bankAccount, - password: args.tipTopup.bankPassword, + auth: { + username: args.tipTopup.bankAccount, + password: args.tipTopup.bankPassword, + }, allowHttp: true, }); @@ -219,10 +221,12 @@ deploymentCli console.log("payto URI:", paytoUri); - const transactions = await bankAccessApiClient.getTransactions(); + const transactions = await bankAccessApiClient.getTransactions( + args.tipTopup.bankAccount, + ); console.log("transactions:", j2s(transactions)); - await bankAccessApiClient.createTransaction({ + await bankAccessApiClient.createTransaction(args.tipTopup.bankAccount, { amount, paytoUri, }); diff --git a/packages/taler-harness/src/integrationtests/test-age-restrictions-mixed-merchant.ts b/packages/taler-harness/src/integrationtests/test-age-restrictions-mixed-merchant.ts index 8bf71b63d..970acbb72 100644 --- a/packages/taler-harness/src/integrationtests/test-age-restrictions-mixed-merchant.ts +++ b/packages/taler-harness/src/integrationtests/test-age-restrictions-mixed-merchant.ts @@ -17,12 +17,15 @@ /** * Imports. */ +import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { defaultCoinConfig } from "../harness/denomStructures.js"; import { GlobalTestState, WalletCli } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, makeTestPayment, + createSimpleTestkudosEnvironmentV2, + withdrawViaBankV2, + makeTestPaymentV2, + createWalletDaemonWithClient, } from "../harness/helpers.js"; /** @@ -32,11 +35,11 @@ export async function runAgeRestrictionsMixedMerchantTest(t: GlobalTestState) { // Set up test environment const { - wallet: walletOne, + walletClient: walletOne, bank, exchange, merchant, - } = await createSimpleTestkudosEnvironment( + } = await createSimpleTestkudosEnvironmentV2( t, defaultCoinConfig.map((x) => x("TESTKUDOS")), { @@ -45,14 +48,19 @@ export async function runAgeRestrictionsMixedMerchantTest(t: GlobalTestState) { }, ); - const walletTwo = new WalletCli(t, "walletTwo"); - const walletThree = new WalletCli(t, "walletThree"); + const { walletClient: walletTwo } = await createWalletDaemonWithClient(t, { + name: "w2", + }); + + const { walletClient: walletThree } = await createWalletDaemonWithClient(t, { + name: "w3", + }); { - const wallet = walletOne; + const walletClient = walletOne; - await withdrawViaBank(t, { - wallet, + await withdrawViaBankV2(t, { + walletClient, bank, exchange, amount: "TESTKUDOS:20", @@ -66,15 +74,16 @@ export async function runAgeRestrictionsMixedMerchantTest(t: GlobalTestState) { minimum_age: 9, }; - await makeTestPayment(t, { wallet, merchant, order }); - await wallet.runUntilDone(); + await makeTestPaymentV2(t, { walletClient, merchant, order }); + await walletClient.call( + WalletApiOperation.TestingWaitTransactionsFinal, + {}, + ); } { - const wallet = walletTwo; - - await withdrawViaBank(t, { - wallet, + await withdrawViaBankV2(t, { + walletClient: walletTwo, bank, exchange, amount: "TESTKUDOS:20", @@ -87,15 +96,13 @@ export async function runAgeRestrictionsMixedMerchantTest(t: GlobalTestState) { fulfillment_url: "taler://fulfillment-success/thx", }; - await makeTestPayment(t, { wallet, merchant, order }); - await wallet.runUntilDone(); + await makeTestPaymentV2(t, { walletClient: walletTwo, merchant, order }); + await walletTwo.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); } { - const wallet = walletThree; - - await withdrawViaBank(t, { - wallet, + await withdrawViaBankV2(t, { + walletClient: walletThree, bank, exchange, amount: "TESTKUDOS:20", @@ -108,8 +115,8 @@ export async function runAgeRestrictionsMixedMerchantTest(t: GlobalTestState) { minimum_age: 9, }; - await makeTestPayment(t, { wallet, merchant, order }); - await wallet.runUntilDone(); + await makeTestPaymentV2(t, { walletClient: walletThree, merchant, order }); + await walletThree.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); } } diff --git a/packages/taler-harness/src/integrationtests/test-bank-api.ts b/packages/taler-harness/src/integrationtests/test-bank-api.ts index a0e1c2085..9ac16980b 100644 --- a/packages/taler-harness/src/integrationtests/test-bank-api.ts +++ b/packages/taler-harness/src/integrationtests/test-bank-api.ts @@ -17,23 +17,22 @@ /** * Imports. */ -import { - GlobalTestState, - WalletCli, - ExchangeService, - setupDb, - BankService, - MerchantService, - getPayto, -} from "../harness/harness.js"; import { createEddsaKeyPair, encodeCrock } from "@gnu-taler/taler-util"; -import { defaultCoinConfig } from "../harness/denomStructures.js"; import { - BankApi, BankAccessApi, + BankApi, CreditDebitIndicator, WireGatewayApiClient, } from "@gnu-taler/taler-wallet-core"; +import { defaultCoinConfig } from "../harness/denomStructures.js"; +import { + BankService, + ExchangeService, + GlobalTestState, + MerchantService, + getPayto, + setupDb, +} from "../harness/harness.js"; /** * Run test for basic, bank-integrated withdrawal. diff --git a/packages/taler-harness/src/integrationtests/test-claim-loop.ts b/packages/taler-harness/src/integrationtests/test-claim-loop.ts index 921391283..32706c28b 100644 --- a/packages/taler-harness/src/integrationtests/test-claim-loop.ts +++ b/packages/taler-harness/src/integrationtests/test-claim-loop.ts @@ -17,13 +17,13 @@ /** * Imports. */ +import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; +import { URL } from "url"; import { GlobalTestState, MerchantPrivateApi } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, + createSimpleTestkudosEnvironmentV2, + withdrawViaBankV2, } from "../harness/helpers.js"; -import { URL } from "url"; -import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; /** * Run test for the merchant's order lifecycle. @@ -34,10 +34,15 @@ import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; export async function runClaimLoopTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { + walletClient, + bank, + exchange, + amount: "TESTKUDOS:20", + }); // Set up order. const orderResp = await MerchantPrivateApi.createOrder(merchant, "default", { @@ -61,7 +66,7 @@ export async function runClaimLoopTest(t: GlobalTestState) { // Make wallet claim the unpaid order. t.assertTrue(orderStatusBefore.order_status === "unpaid"); const talerPayUri = orderStatusBefore.taler_pay_uri; - await wallet.client.call(WalletApiOperation.PreparePayForUri, { + await walletClient.call(WalletApiOperation.PreparePayForUri, { talerPayUri, }); diff --git a/packages/taler-harness/src/integrationtests/test-denom-unoffered.ts b/packages/taler-harness/src/integrationtests/test-denom-unoffered.ts index 27c336ea6..1b9b91603 100644 --- a/packages/taler-harness/src/integrationtests/test-denom-unoffered.ts +++ b/packages/taler-harness/src/integrationtests/test-denom-unoffered.ts @@ -22,18 +22,20 @@ import { Wallet, WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState, MerchantPrivateApi } from "../harness/harness.js"; import { createSimpleTestkudosEnvironment, + createSimpleTestkudosEnvironmentV2, withdrawViaBank, + withdrawViaBankV2, } from "../harness/helpers.js"; export async function runDenomUnofferedTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { walletClient, bank, exchange, amount: "TESTKUDOS:20" }); // Make the exchange forget the denomination. // Effectively we completely reset the exchange, @@ -67,7 +69,7 @@ export async function runDenomUnofferedTest(t: GlobalTestState) { // Make wallet pay for the order - const preparePayResult = await wallet.client.call( + const preparePayResult = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri: orderStatus.taler_pay_uri, @@ -78,11 +80,11 @@ export async function runDenomUnofferedTest(t: GlobalTestState) { preparePayResult.status === PreparePayResultType.PaymentPossible, ); - const confirmResp = await wallet.client.call(WalletApiOperation.ConfirmPay, { + const confirmResp = await walletClient.call(WalletApiOperation.ConfirmPay, { proposalId: preparePayResult.proposalId, }); - const tx = await wallet.client.call(WalletApiOperation.GetTransactionById, { + const tx = await walletClient.call(WalletApiOperation.GetTransactionById, { transactionId: confirmResp.transactionId, }); @@ -96,21 +98,21 @@ export async function runDenomUnofferedTest(t: GlobalTestState) { TalerErrorCode.MERCHANT_POST_ORDERS_ID_PAY_DENOMINATION_KEY_NOT_FOUND, ); - await wallet.client.call(WalletApiOperation.AddExchange, { + await walletClient.call(WalletApiOperation.AddExchange, { exchangeBaseUrl: exchange.baseUrl, forceUpdate: true, }); - await wallet.client.call(WalletApiOperation.DeleteTransaction, { + await walletClient.call(WalletApiOperation.DeleteTransaction, { transactionId: confirmResp.transactionId, }); // Now withdrawal should work again. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { walletClient, bank, exchange, amount: "TESTKUDOS:20" }); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); - const txs = await wallet.client.call(WalletApiOperation.GetTransactions, {}); + const txs = await walletClient.call(WalletApiOperation.GetTransactions, {}); console.log(JSON.stringify(txs, undefined, 2)); } diff --git a/packages/taler-harness/src/integrationtests/test-exchange-deposit.ts b/packages/taler-harness/src/integrationtests/test-exchange-deposit.ts index 6c0d070d0..05bbbfaa1 100644 --- a/packages/taler-harness/src/integrationtests/test-exchange-deposit.ts +++ b/packages/taler-harness/src/integrationtests/test-exchange-deposit.ts @@ -30,14 +30,15 @@ import { depositCoin, downloadExchangeInfo, findDenomOrThrow, - refreshCoin, SynchronousCryptoWorkerFactoryPlain, topupReserveWithDemobank, Wallet, withdrawCoin, } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState } from "../harness/harness.js"; -import { createSimpleTestkudosEnvironment } from "../harness/helpers.js"; +import { + createSimpleTestkudosEnvironmentV2, +} from "../harness/helpers.js"; /** * Run test for basic, bank-integrated withdrawal and payment. @@ -45,7 +46,7 @@ import { createSimpleTestkudosEnvironment } from "../harness/helpers.js"; export async function runExchangeDepositTest(t: GlobalTestState) { // Set up test environment - const { bank, exchange } = await createSimpleTestkudosEnvironment(t); + const { bank, exchange } = await createSimpleTestkudosEnvironmentV2(t); const http = createPlatformHttpLib({ allowHttp: true, diff --git a/packages/taler-harness/src/integrationtests/test-forced-selection.ts b/packages/taler-harness/src/integrationtests/test-forced-selection.ts index d0621f000..3425dadf1 100644 --- a/packages/taler-harness/src/integrationtests/test-forced-selection.ts +++ b/packages/taler-harness/src/integrationtests/test-forced-selection.ts @@ -20,7 +20,7 @@ import { j2s } from "@gnu-taler/taler-util"; import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState } from "../harness/harness.js"; -import { createSimpleTestkudosEnvironment } from "../harness/helpers.js"; +import { createSimpleTestkudosEnvironmentV2 } from "../harness/helpers.js"; /** * Run test for forced denom/coin selection. @@ -28,14 +28,14 @@ import { createSimpleTestkudosEnvironment } from "../harness/helpers.js"; export async function runForcedSelectionTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); - await wallet.client.call(WalletApiOperation.AddExchange, { + await walletClient.call(WalletApiOperation.AddExchange, { exchangeBaseUrl: exchange.baseUrl, }); - await wallet.client.call(WalletApiOperation.WithdrawTestBalance, { + await walletClient.call(WalletApiOperation.WithdrawTestBalance, { exchangeBaseUrl: exchange.baseUrl, amount: "TESTKUDOS:10", bankAccessApiBaseUrl: bank.bankAccessApiBaseUrl, @@ -49,13 +49,13 @@ export async function runForcedSelectionTest(t: GlobalTestState) { }, }); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); - const coinDump = await wallet.client.call(WalletApiOperation.DumpCoins, {}); + const coinDump = await walletClient.call(WalletApiOperation.DumpCoins, {}); console.log(coinDump); t.assertDeepEqual(coinDump.coins.length, 3); - const payResp = await wallet.client.call(WalletApiOperation.TestPay, { + const payResp = await walletClient.call(WalletApiOperation.TestPay, { amount: "TESTKUDOS:3", merchantBaseUrl: merchant.makeInstanceBaseUrl(), summary: "bla", diff --git a/packages/taler-harness/src/integrationtests/test-libeufin-api-bankaccount.ts b/packages/taler-harness/src/integrationtests/test-libeufin-api-bankaccount.ts index a5396a472..f36168301 100644 --- a/packages/taler-harness/src/integrationtests/test-libeufin-api-bankaccount.ts +++ b/packages/taler-harness/src/integrationtests/test-libeufin-api-bankaccount.ts @@ -19,7 +19,6 @@ */ import { GlobalTestState } from "../harness/harness.js"; import { - NexusUserBundle, LibeufinNexusApi, LibeufinNexusService, LibeufinSandboxService, diff --git a/packages/taler-harness/src/integrationtests/test-libeufin-nexus-balance.ts b/packages/taler-harness/src/integrationtests/test-libeufin-nexus-balance.ts index 5c10c029e..68b0174cc 100644 --- a/packages/taler-harness/src/integrationtests/test-libeufin-nexus-balance.ts +++ b/packages/taler-harness/src/integrationtests/test-libeufin-nexus-balance.ts @@ -23,7 +23,6 @@ import { NexusUserBundle, launchLibeufinServices, LibeufinNexusApi, - LibeufinCli, } from "../harness/libeufin.js"; /** diff --git a/packages/taler-harness/src/integrationtests/test-merchant-longpolling.ts b/packages/taler-harness/src/integrationtests/test-merchant-longpolling.ts index 7d2ba99b2..161e8beac 100644 --- a/packages/taler-harness/src/integrationtests/test-merchant-longpolling.ts +++ b/packages/taler-harness/src/integrationtests/test-merchant-longpolling.ts @@ -17,20 +17,20 @@ /** * Imports. */ -import { GlobalTestState, MerchantPrivateApi } from "../harness/harness.js"; -import { - createSimpleTestkudosEnvironment, - withdrawViaBank, -} from "../harness/helpers.js"; import { - PreparePayResultType, - codecForMerchantOrderStatusUnpaid, ConfirmPayResultType, + PreparePayResultType, URL, + codecForMerchantOrderStatusUnpaid, } from "@gnu-taler/taler-util"; +import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import axiosImp from "axios"; +import { GlobalTestState, MerchantPrivateApi } from "../harness/harness.js"; +import { + createSimpleTestkudosEnvironmentV2, + withdrawViaBankV2 +} from "../harness/helpers.js"; const axios = axiosImp.default; -import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; /** * Run test for basic, bank-integrated withdrawal. @@ -38,12 +38,17 @@ import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; export async function runMerchantLongpollingTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { + walletClient, + bank, + exchange, + amount: "TESTKUDOS:20", + }); /** * ========================================================================= @@ -113,7 +118,7 @@ export async function runMerchantLongpollingTest(t: GlobalTestState) { * ========================================================================= */ - let preparePayResp = await wallet.client.call( + let preparePayResp = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri: pubUnpaidStatus.taler_pay_uri, @@ -148,7 +153,7 @@ export async function runMerchantLongpollingTest(t: GlobalTestState) { publicOrderStatusResp.data, ); - const confirmPayRes = await wallet.client.call( + const confirmPayRes = await walletClient.call( WalletApiOperation.ConfirmPay, { proposalId: proposalId, diff --git a/packages/taler-harness/src/integrationtests/test-payment-abort.ts b/packages/taler-harness/src/integrationtests/test-payment-abort.ts index 0ac953240..40438c583 100644 --- a/packages/taler-harness/src/integrationtests/test-payment-abort.ts +++ b/packages/taler-harness/src/integrationtests/test-payment-abort.ts @@ -24,7 +24,6 @@ import { } from "../harness/helpers.js"; import { FaultInjectionRequestContext, - FaultInjectionResponseContext, } from "../harness/faultInjection.js"; import { codecForMerchantOrderStatusUnpaid, diff --git a/packages/taler-harness/src/integrationtests/test-payment-claim.ts b/packages/taler-harness/src/integrationtests/test-payment-claim.ts index e93d2c44c..eb219c1e7 100644 --- a/packages/taler-harness/src/integrationtests/test-payment-claim.ts +++ b/packages/taler-harness/src/integrationtests/test-payment-claim.ts @@ -17,18 +17,17 @@ /** * Imports. */ +import { PreparePayResultType, TalerErrorCode } from "@gnu-taler/taler-util"; +import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState, MerchantPrivateApi, WalletCli, } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, + createSimpleTestkudosEnvironmentV2, + withdrawViaBankV2, } from "../harness/helpers.js"; -import { PreparePayResultType } from "@gnu-taler/taler-util"; -import { TalerErrorCode } from "@gnu-taler/taler-util"; -import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; /** * Run test for basic, bank-integrated withdrawal. @@ -36,14 +35,19 @@ import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; export async function runPaymentClaimTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); const walletTwo = new WalletCli(t, "two"); // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { + walletClient, + bank, + exchange, + amount: "TESTKUDOS:20", + }); // Set up order. @@ -65,7 +69,7 @@ export async function runPaymentClaimTest(t: GlobalTestState) { // Make wallet pay for the order - const preparePayResult = await wallet.client.call( + const preparePayResult = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri, @@ -82,7 +86,7 @@ export async function runPaymentClaimTest(t: GlobalTestState) { }); }); - await wallet.client.call(WalletApiOperation.ConfirmPay, { + await walletClient.call(WalletApiOperation.ConfirmPay, { proposalId: preparePayResult.proposalId, }); diff --git a/packages/taler-harness/src/integrationtests/test-payment-forgettable.ts b/packages/taler-harness/src/integrationtests/test-payment-forgettable.ts index b66eda2f1..83f19e58e 100644 --- a/packages/taler-harness/src/integrationtests/test-payment-forgettable.ts +++ b/packages/taler-harness/src/integrationtests/test-payment-forgettable.ts @@ -17,11 +17,12 @@ /** * Imports. */ +import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, - makeTestPayment, + createSimpleTestkudosEnvironmentV2, + makeTestPaymentV2, + withdrawViaBankV2, } from "../harness/helpers.js"; /** @@ -30,12 +31,17 @@ import { export async function runPaymentForgettableTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { + walletClient, + bank, + exchange, + amount: "TESTKUDOS:20", + }); { const order = { @@ -50,7 +56,7 @@ export async function runPaymentForgettableTest(t: GlobalTestState) { }, }; - await makeTestPayment(t, { wallet, merchant, order }); + await makeTestPaymentV2(t, { walletClient, merchant, order }); } console.log("testing with forgettable field without hash"); @@ -68,10 +74,10 @@ export async function runPaymentForgettableTest(t: GlobalTestState) { }, }; - await makeTestPayment(t, { wallet, merchant, order }); + await makeTestPaymentV2(t, { walletClient, merchant, order }); } - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); } runPaymentForgettableTest.suites = ["wallet", "merchant"]; diff --git a/packages/taler-harness/src/integrationtests/test-payment-idempotency.ts b/packages/taler-harness/src/integrationtests/test-payment-idempotency.ts index 1099a8188..e16cf9dd1 100644 --- a/packages/taler-harness/src/integrationtests/test-payment-idempotency.ts +++ b/packages/taler-harness/src/integrationtests/test-payment-idempotency.ts @@ -17,13 +17,13 @@ /** * Imports. */ +import { PreparePayResultType } from "@gnu-taler/taler-util"; +import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState, MerchantPrivateApi } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, + createSimpleTestkudosEnvironmentV2, + withdrawViaBankV2, } from "../harness/helpers.js"; -import { PreparePayResultType } from "@gnu-taler/taler-util"; -import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; /** * Test the wallet-core payment API, especially that repeated operations @@ -32,12 +32,17 @@ import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; export async function runPaymentIdempotencyTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { + walletClient, + bank, + exchange, + amount: "TESTKUDOS:20", + }); // Set up order. @@ -59,14 +64,14 @@ export async function runPaymentIdempotencyTest(t: GlobalTestState) { // Make wallet pay for the order - const preparePayResult = await wallet.client.call( + const preparePayResult = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri: orderStatus.taler_pay_uri, }, ); - const preparePayResultRep = await wallet.client.call( + const preparePayResultRep = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri: orderStatus.taler_pay_uri, @@ -82,7 +87,7 @@ export async function runPaymentIdempotencyTest(t: GlobalTestState) { const proposalId = preparePayResult.proposalId; - const confirmPayResult = await wallet.client.call( + const confirmPayResult = await walletClient.call( WalletApiOperation.ConfirmPay, { proposalId: proposalId, @@ -91,7 +96,7 @@ export async function runPaymentIdempotencyTest(t: GlobalTestState) { console.log("confirm pay result", confirmPayResult); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); // Check if payment was successful. @@ -101,7 +106,7 @@ export async function runPaymentIdempotencyTest(t: GlobalTestState) { t.assertTrue(orderStatus.order_status === "paid"); - const preparePayResultAfter = await wallet.client.call( + const preparePayResultAfter = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri, diff --git a/packages/taler-harness/src/integrationtests/test-payment-share.ts b/packages/taler-harness/src/integrationtests/test-payment-share.ts index 2f853b91b..156571372 100644 --- a/packages/taler-harness/src/integrationtests/test-payment-share.ts +++ b/packages/taler-harness/src/integrationtests/test-payment-share.ts @@ -17,21 +17,17 @@ /** * Imports. */ +import { + ConfirmPayResultType, + PreparePayResultType, +} from "@gnu-taler/taler-util"; import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState, MerchantPrivateApi } from "../harness/harness.js"; import { createSimpleTestkudosEnvironmentV2, - withdrawViaBankV2, - makeTestPaymentV2, createWalletDaemonWithClient, + withdrawViaBankV2, } from "../harness/helpers.js"; -import { - ConfirmPayResultType, - PreparePayResultType, - j2s, - parsePayUri, - stringifyPayUri, -} from "@gnu-taler/taler-util"; /** * Run test for basic, bank-integrated withdrawal and payment. diff --git a/packages/taler-harness/src/integrationtests/test-payment-template.ts b/packages/taler-harness/src/integrationtests/test-payment-template.ts index 41e43e28a..172791648 100644 --- a/packages/taler-harness/src/integrationtests/test-payment-template.ts +++ b/packages/taler-harness/src/integrationtests/test-payment-template.ts @@ -17,13 +17,12 @@ /** * Imports. */ -import { ConfirmPayResultType, Duration, PreparePayResultType, TalerProtocolTimestamp } from "@gnu-taler/taler-util"; +import { ConfirmPayResultType, Duration, PreparePayResultType } from "@gnu-taler/taler-util"; import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState, MerchantPrivateApi } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, - makeTestPayment, + createSimpleTestkudosEnvironmentV2, + withdrawViaBankV2 } from "../harness/helpers.js"; /** @@ -32,8 +31,8 @@ import { export async function runPaymentTemplateTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); await MerchantPrivateApi.createTemplate(merchant, "default", { template_id: "template1", @@ -51,11 +50,11 @@ export async function runPaymentTemplateTest(t: GlobalTestState) { // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { walletClient, bank, exchange, amount: "TESTKUDOS:20" }); // Request a template payment - const preparePayResult = await wallet.client.call( + const preparePayResult = await walletClient.call( WalletApiOperation.PreparePayForTemplate, { talerPayTemplateUri: `taler+http://pay-template/localhost:${merchant.port}/template1?amount=TESTKUDOS:1`, @@ -71,7 +70,7 @@ export async function runPaymentTemplateTest(t: GlobalTestState) { // Pay for it - const r2 = await wallet.client.call(WalletApiOperation.ConfirmPay, { + const r2 = await walletClient.call(WalletApiOperation.ConfirmPay, { proposalId: preparePayResult.proposalId, }); @@ -88,8 +87,7 @@ export async function runPaymentTemplateTest(t: GlobalTestState) { ); t.assertTrue(orderStatus.order_status === "paid"); - - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); } runPaymentTemplateTest.suites = ["wallet"]; diff --git a/packages/taler-harness/src/integrationtests/test-payment-zero.ts b/packages/taler-harness/src/integrationtests/test-payment-zero.ts index 264cffd06..7423751a5 100644 --- a/packages/taler-harness/src/integrationtests/test-payment-zero.ts +++ b/packages/taler-harness/src/integrationtests/test-payment-zero.ts @@ -20,9 +20,9 @@ import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, - makeTestPayment, + createSimpleTestkudosEnvironmentV2, + withdrawViaBankV2, + makeTestPaymentV2, } from "../harness/helpers.js"; import { TransactionMajorState } from "@gnu-taler/taler-util"; @@ -33,19 +33,19 @@ import { TransactionMajorState } from "@gnu-taler/taler-util"; export async function runPaymentZeroTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); // First, make a "free" payment when we don't even have // any money in the // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { walletClient, bank, exchange, amount: "TESTKUDOS:20" }); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); - await makeTestPayment(t, { - wallet, + await makeTestPaymentV2(t, { + walletClient, merchant, order: { summary: "I am free!", @@ -54,9 +54,9 @@ export async function runPaymentZeroTest(t: GlobalTestState) { }, }); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); - const transactions = await wallet.client.call( + const transactions = await walletClient.call( WalletApiOperation.GetTransactions, {}, ); diff --git a/packages/taler-harness/src/integrationtests/test-paywall-flow.ts b/packages/taler-harness/src/integrationtests/test-paywall-flow.ts index a9601c625..c90898034 100644 --- a/packages/taler-harness/src/integrationtests/test-paywall-flow.ts +++ b/packages/taler-harness/src/integrationtests/test-paywall-flow.ts @@ -19,10 +19,6 @@ */ import { GlobalTestState, MerchantPrivateApi } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, -} from "../harness/helpers.js"; -import { PreparePayResultType, codecForMerchantOrderStatusUnpaid, ConfirmPayResultType, @@ -31,6 +27,7 @@ import { import axiosImp from "axios"; const axios = axiosImp.default; import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; +import { createSimpleTestkudosEnvironmentV2, withdrawViaBankV2 } from "../harness/helpers.js"; /** * Run test for basic, bank-integrated withdrawal. @@ -38,12 +35,12 @@ import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; export async function runPaywallFlowTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { walletClient, bank, exchange, amount: "TESTKUDOS:20" }); /** * ========================================================================= @@ -93,7 +90,7 @@ export async function runPaywallFlowTest(t: GlobalTestState) { console.log(pubUnpaidStatus); - let preparePayResp = await wallet.client.call( + let preparePayResp = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri: pubUnpaidStatus.taler_pay_uri, @@ -119,7 +116,7 @@ export async function runPaywallFlowTest(t: GlobalTestState) { publicOrderStatusResp.data, ); - const confirmPayRes = await wallet.client.call( + const confirmPayRes = await walletClient.call( WalletApiOperation.ConfirmPay, { proposalId: proposalId, @@ -158,7 +155,7 @@ export async function runPaywallFlowTest(t: GlobalTestState) { // Pay with new taler://pay URI, which should // have the new session ID! // Wallet should now automatically re-play payment. - preparePayResp = await wallet.client.call( + preparePayResp = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri: talerPayUriOne, @@ -199,7 +196,7 @@ export async function runPaywallFlowTest(t: GlobalTestState) { // Here the re-purchase detection should kick in, // and the wallet should re-pay for the old order // under the new session ID (mysession-three). - preparePayResp = await wallet.client.call( + preparePayResp = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri: orderStatus.taler_pay_uri, diff --git a/packages/taler-harness/src/integrationtests/test-refund-auto.ts b/packages/taler-harness/src/integrationtests/test-refund-auto.ts index 4c2a2f94a..607080e68 100644 --- a/packages/taler-harness/src/integrationtests/test-refund-auto.ts +++ b/packages/taler-harness/src/integrationtests/test-refund-auto.ts @@ -17,13 +17,13 @@ /** * Imports. */ +import { Duration, durationFromSpec } from "@gnu-taler/taler-util"; +import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState, MerchantPrivateApi } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, + createSimpleTestkudosEnvironmentV2, + withdrawViaBankV2, } from "../harness/helpers.js"; -import { Duration, durationFromSpec } from "@gnu-taler/taler-util"; -import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; /** * Run test for basic, bank-integrated withdrawal. @@ -31,12 +31,17 @@ import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; export async function runRefundAutoTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { + walletClient, + bank, + exchange, + amount: "TESTKUDOS:20", + }); // Set up order. const orderResp = await MerchantPrivateApi.createOrder(merchant, "default", { @@ -61,13 +66,12 @@ export async function runRefundAutoTest(t: GlobalTestState) { // Make wallet pay for the order - const r1 = await wallet.client.call(WalletApiOperation.PreparePayForUri, { + const r1 = await walletClient.call(WalletApiOperation.PreparePayForUri, { talerPayUri: orderStatus.taler_pay_uri, }); - await wallet.client.call(WalletApiOperation.ConfirmPay, { - // FIXME: should be validated, don't cast! - proposalId: r1.proposalId, + await walletClient.call(WalletApiOperation.ConfirmPay, { + transactionId: r1.transactionId, }); // Check if payment was successful. @@ -88,9 +92,9 @@ export async function runRefundAutoTest(t: GlobalTestState) { console.log(ref); // The wallet should now automatically pick up the refund. - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); - const transactions = await wallet.client.call( + const transactions = await walletClient.call( WalletApiOperation.GetTransactions, {}, ); diff --git a/packages/taler-harness/src/integrationtests/test-refund-incremental.ts b/packages/taler-harness/src/integrationtests/test-refund-incremental.ts index c8fcfc831..8e7e38b71 100644 --- a/packages/taler-harness/src/integrationtests/test-refund-incremental.ts +++ b/packages/taler-harness/src/integrationtests/test-refund-incremental.ts @@ -18,21 +18,21 @@ * Imports. */ import { + Amounts, + Duration, + TransactionType, + durationFromSpec, +} from "@gnu-taler/taler-util"; +import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; +import { GlobalTestState, - delayMs, MerchantPrivateApi, + delayMs, } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - withdrawViaBank, + createSimpleTestkudosEnvironmentV2, + withdrawViaBankV2, } from "../harness/helpers.js"; -import { - TransactionType, - Amounts, - durationFromSpec, - Duration, -} from "@gnu-taler/taler-util"; -import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; /** * Run test for basic, bank-integrated withdrawal. @@ -40,12 +40,17 @@ import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; export async function runRefundIncrementalTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant } = + await createSimpleTestkudosEnvironmentV2(t); // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { + walletClient, + bank, + exchange, + amount: "TESTKUDOS:20", + }); // Set up order. @@ -68,11 +73,11 @@ export async function runRefundIncrementalTest(t: GlobalTestState) { // Make wallet pay for the order - const r1 = await wallet.client.call(WalletApiOperation.PreparePayForUri, { + const r1 = await walletClient.call(WalletApiOperation.PreparePayForUri, { talerPayUri: orderStatus.taler_pay_uri, }); - await wallet.client.call(WalletApiOperation.ConfirmPay, { + await walletClient.call(WalletApiOperation.ConfirmPay, { proposalId: r1.proposalId, }); @@ -94,15 +99,15 @@ export async function runRefundIncrementalTest(t: GlobalTestState) { console.log("first refund increase response", ref); { - let wr = await wallet.client.call(WalletApiOperation.StartRefundQuery, { + let wr = await walletClient.call(WalletApiOperation.StartRefundQuery, { transactionId: r1.transactionId, }); - await wallet.runUntilDone(); - console.log(wr); - const txs = await wallet.client.call( - WalletApiOperation.GetTransactions, + await walletClient.call( + WalletApiOperation.TestingWaitTransactionsFinal, {}, ); + console.log(wr); + const txs = await walletClient.call(WalletApiOperation.GetTransactions, {}); console.log( "transactions after applying first refund:", JSON.stringify(txs, undefined, 2), @@ -136,10 +141,13 @@ export async function runRefundIncrementalTest(t: GlobalTestState) { console.log("third refund increase response", ref); { - let wr = await wallet.client.call(WalletApiOperation.StartRefundQuery, { + let wr = await walletClient.call(WalletApiOperation.StartRefundQuery, { transactionId: r1.transactionId, }); - await wallet.runUntilDone(); + await walletClient.call( + WalletApiOperation.TestingWaitTransactionsFinal, + {}, + ); console.log(wr); } @@ -153,25 +161,17 @@ export async function runRefundIncrementalTest(t: GlobalTestState) { console.log(JSON.stringify(orderStatus, undefined, 2)); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); - const bal = await wallet.client.call(WalletApiOperation.GetBalances, {}); + const bal = await walletClient.call(WalletApiOperation.GetBalances, {}); console.log(JSON.stringify(bal, undefined, 2)); { - const txs = await wallet.client.call( - WalletApiOperation.GetTransactions, - {}, - ); + const txs = await walletClient.call(WalletApiOperation.GetTransactions, {}); console.log(JSON.stringify(txs, undefined, 2)); const txTypes = txs.transactions.map((x) => x.type); - t.assertDeepEqual(txTypes, [ - "withdrawal", - "payment", - "refund", - "refund", - ]); + t.assertDeepEqual(txTypes, ["withdrawal", "payment", "refund", "refund"]); for (const tx of txs.transactions) { if (tx.type !== TransactionType.Refund) { diff --git a/packages/taler-harness/src/integrationtests/test-tipping.ts b/packages/taler-harness/src/integrationtests/test-tipping.ts index 332f702d7..53d7f08c8 100644 --- a/packages/taler-harness/src/integrationtests/test-tipping.ts +++ b/packages/taler-harness/src/integrationtests/test-tipping.ts @@ -18,8 +18,8 @@ * Imports. */ import { + BankAccessApiClient, WalletApiOperation, - BankApi, WireGatewayApiClient, } from "@gnu-taler/taler-wallet-core"; import { @@ -28,7 +28,7 @@ import { MerchantPrivateApi, getWireMethodForTest, } from "../harness/harness.js"; -import { createSimpleTestkudosEnvironment } from "../harness/helpers.js"; +import { createSimpleTestkudosEnvironmentV2 } from "../harness/helpers.js"; import { TransactionMajorState } from "@gnu-taler/taler-util"; /** @@ -37,10 +37,14 @@ import { TransactionMajorState } from "@gnu-taler/taler-util"; export async function runTippingTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, merchant, exchangeBankAccount } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, merchant, exchangeBankAccount } = + await createSimpleTestkudosEnvironmentV2(t); - const mbu = await BankApi.createRandomBankUser(bank); + const bankAccessApiClient = new BankAccessApiClient({ + allowHttp: true, + baseUrl: bank.bankAccessApiBaseUrl, + }); + const mbu = await bankAccessApiClient.createRandomBankUser(); const merchantClient = new MerchantApiClient( merchant.makeInstanceBaseUrl("default"), @@ -99,7 +103,7 @@ export async function runTippingTest(t: GlobalTestState) { console.log("created tip", tip); const doTip = async (): Promise<void> => { - const ptr = await wallet.client.call(WalletApiOperation.PrepareReward, { + const ptr = await walletClient.call(WalletApiOperation.PrepareReward, { talerRewardUri: tip.taler_reward_uri, }); @@ -108,19 +112,22 @@ export async function runTippingTest(t: GlobalTestState) { t.assertAmountEquals(ptr.rewardAmountRaw, "TESTKUDOS:5"); t.assertAmountEquals(ptr.rewardAmountEffective, "TESTKUDOS:4.85"); - await wallet.client.call(WalletApiOperation.AcceptReward, { + await walletClient.call(WalletApiOperation.AcceptReward, { walletRewardId: ptr.walletRewardId, }); - await wallet.runUntilDone(); + await walletClient.call( + WalletApiOperation.TestingWaitTransactionsFinal, + {}, + ); - const bal = await wallet.client.call(WalletApiOperation.GetBalances, {}); + const bal = await walletClient.call(WalletApiOperation.GetBalances, {}); console.log(bal); t.assertAmountEquals(bal.balances[0].available, "TESTKUDOS:4.85"); - const txns = await wallet.client.call( + const txns = await walletClient.call( WalletApiOperation.GetTransactions, {}, ); @@ -128,7 +135,10 @@ export async function runTippingTest(t: GlobalTestState) { console.log("Transactions:", JSON.stringify(txns, undefined, 2)); t.assertDeepEqual(txns.transactions[0].type, "reward"); - t.assertDeepEqual(txns.transactions[0].txState.major, TransactionMajorState.Done); + t.assertDeepEqual( + txns.transactions[0].txState.major, + TransactionMajorState.Done, + ); t.assertAmountEquals( txns.transactions[0].amountEffective, "TESTKUDOS:4.85", diff --git a/packages/taler-harness/src/integrationtests/test-tos-format.ts b/packages/taler-harness/src/integrationtests/test-tos-format.ts index ebe9c403a..e6087af9d 100644 --- a/packages/taler-harness/src/integrationtests/test-tos-format.ts +++ b/packages/taler-harness/src/integrationtests/test-tos-format.ts @@ -23,7 +23,6 @@ import { createSimpleTestkudosEnvironmentV2, } from "../harness/helpers.js"; import * as fs from "fs"; -import * as path from "path"; /** * Run test for basic, bank-integrated withdrawal and payment. diff --git a/packages/taler-harness/src/integrationtests/test-wallet-backup-basic.ts b/packages/taler-harness/src/integrationtests/test-wallet-backup-basic.ts index f36e2e4f1..5321cf5c7 100644 --- a/packages/taler-harness/src/integrationtests/test-wallet-backup-basic.ts +++ b/packages/taler-harness/src/integrationtests/test-wallet-backup-basic.ts @@ -22,7 +22,9 @@ import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState, WalletCli } from "../harness/harness.js"; import { createSimpleTestkudosEnvironment, + createSimpleTestkudosEnvironmentV2, withdrawViaBank, + withdrawViaBankV2, } from "../harness/helpers.js"; import { SyncService } from "../harness/sync.js"; @@ -32,8 +34,8 @@ import { SyncService } from "../harness/sync.js"; export async function runWalletBackupBasicTest(t: GlobalTestState) { // Set up test environment - const { commonDb, merchant, wallet, bank, exchange } = - await createSimpleTestkudosEnvironment(t); + const { commonDb, merchant, walletClient, bank, exchange } = + await createSimpleTestkudosEnvironmentV2(t); const sync = await SyncService.create(t, { currency: "TESTKUDOS", @@ -49,32 +51,32 @@ export async function runWalletBackupBasicTest(t: GlobalTestState) { await sync.start(); await sync.pingUntilAvailable(); - await wallet.client.call(WalletApiOperation.AddBackupProvider, { + await walletClient.call(WalletApiOperation.AddBackupProvider, { backupProviderBaseUrl: sync.baseUrl, activate: false, name: sync.baseUrl, }); { - const bi = await wallet.client.call(WalletApiOperation.GetBackupInfo, {}); + const bi = await walletClient.call(WalletApiOperation.GetBackupInfo, {}); t.assertDeepEqual(bi.providers[0].active, false); } - await wallet.client.call(WalletApiOperation.AddBackupProvider, { + await walletClient.call(WalletApiOperation.AddBackupProvider, { backupProviderBaseUrl: sync.baseUrl, activate: true, name: sync.baseUrl, }); { - const bi = await wallet.client.call(WalletApiOperation.GetBackupInfo, {}); + const bi = await walletClient.call(WalletApiOperation.GetBackupInfo, {}); t.assertDeepEqual(bi.providers[0].active, true); } - await wallet.client.call(WalletApiOperation.RunBackupCycle, {}); + await walletClient.call(WalletApiOperation.RunBackupCycle, {}); { - const bi = await wallet.client.call(WalletApiOperation.GetBackupInfo, {}); + const bi = await walletClient.call(WalletApiOperation.GetBackupInfo, {}); console.log(bi); t.assertDeepEqual( bi.providers[0].paymentStatus.type, @@ -82,32 +84,32 @@ export async function runWalletBackupBasicTest(t: GlobalTestState) { ); } - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:10" }); + await withdrawViaBankV2(t, { walletClient, bank, exchange, amount: "TESTKUDOS:10" }); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); - await wallet.client.call(WalletApiOperation.RunBackupCycle, {}); + await walletClient.call(WalletApiOperation.RunBackupCycle, {}); { - const bi = await wallet.client.call(WalletApiOperation.GetBackupInfo, {}); + const bi = await walletClient.call(WalletApiOperation.GetBackupInfo, {}); console.log(bi); } - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:5" }); + await withdrawViaBankV2(t, { walletClient, bank, exchange, amount: "TESTKUDOS:5" }); - await wallet.client.call(WalletApiOperation.RunBackupCycle, {}); + await walletClient.call(WalletApiOperation.RunBackupCycle, {}); { - const bi = await wallet.client.call(WalletApiOperation.GetBackupInfo, {}); + const bi = await walletClient.call(WalletApiOperation.GetBackupInfo, {}); console.log(bi); } - const backupRecovery = await wallet.client.call( + const backupRecovery = await walletClient.call( WalletApiOperation.ExportBackupRecovery, {}, ); - const txs = await wallet.client.call(WalletApiOperation.GetTransactions, {}); + const txs = await walletClient.call(WalletApiOperation.GetTransactions, {}); console.log(`backed up transactions ${j2s(txs)}`); const wallet2 = new WalletCli(t, "wallet2"); diff --git a/packages/taler-harness/src/integrationtests/test-wallet-backup-doublespend.ts b/packages/taler-harness/src/integrationtests/test-wallet-backup-doublespend.ts index 2aceab86e..e3e18d5a4 100644 --- a/packages/taler-harness/src/integrationtests/test-wallet-backup-doublespend.ts +++ b/packages/taler-harness/src/integrationtests/test-wallet-backup-doublespend.ts @@ -21,21 +21,22 @@ import { PreparePayResultType } from "@gnu-taler/taler-util"; import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState, - WalletCli, MerchantPrivateApi, + WalletCli, } from "../harness/harness.js"; import { - createSimpleTestkudosEnvironment, - makeTestPayment, + createSimpleTestkudosEnvironmentV2, + makeTestPaymentV2, withdrawViaBank, + withdrawViaBankV2 } from "../harness/helpers.js"; import { SyncService } from "../harness/sync.js"; export async function runWalletBackupDoublespendTest(t: GlobalTestState) { // Set up test environment - const { commonDb, merchant, wallet, bank, exchange } = - await createSimpleTestkudosEnvironment(t); + const { commonDb, merchant, walletClient, bank, exchange } = + await createSimpleTestkudosEnvironmentV2(t); const sync = await SyncService.create(t, { currency: "TESTKUDOS", @@ -51,21 +52,21 @@ export async function runWalletBackupDoublespendTest(t: GlobalTestState) { await sync.start(); await sync.pingUntilAvailable(); - await wallet.client.call(WalletApiOperation.AddBackupProvider, { + await walletClient.call(WalletApiOperation.AddBackupProvider, { backupProviderBaseUrl: sync.baseUrl, activate: true, name: sync.baseUrl, }); - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:10" }); + await withdrawViaBankV2(t, { walletClient, bank, exchange, amount: "TESTKUDOS:10" }); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); - await wallet.client.call(WalletApiOperation.RunBackupCycle, {}); - await wallet.runUntilDone(); - await wallet.client.call(WalletApiOperation.RunBackupCycle, {}); + await walletClient.call(WalletApiOperation.RunBackupCycle, {}); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); + await walletClient.call(WalletApiOperation.RunBackupCycle, {}); - const backupRecovery = await wallet.client.call( + const backupRecovery = await walletClient.call( WalletApiOperation.ExportBackupRecovery, {}, ); @@ -80,23 +81,23 @@ export async function runWalletBackupDoublespendTest(t: GlobalTestState) { console.log( "wallet1 balance before spend:", - await wallet.client.call(WalletApiOperation.GetBalances, {}), + await walletClient.call(WalletApiOperation.GetBalances, {}), ); - await makeTestPayment(t, { + await makeTestPaymentV2(t, { merchant, - wallet, + walletClient, order: { summary: "foo", amount: "TESTKUDOS:7", }, }); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); console.log( "wallet1 balance after spend:", - await wallet.client.call(WalletApiOperation.GetBalances, {}), + await walletClient.call(WalletApiOperation.GetBalances, {}), ); { diff --git a/packages/taler-harness/src/integrationtests/test-wallet-balance.ts b/packages/taler-harness/src/integrationtests/test-wallet-balance.ts index b5b1917a6..0f75bd96e 100644 --- a/packages/taler-harness/src/integrationtests/test-wallet-balance.ts +++ b/packages/taler-harness/src/integrationtests/test-wallet-balance.ts @@ -30,7 +30,11 @@ import { setupDb, WalletCli, } from "../harness/harness.js"; -import { withdrawViaBank } from "../harness/helpers.js"; +import { + createSimpleTestkudosEnvironmentV2, + withdrawViaBank, + withdrawViaBankV2, +} from "../harness/helpers.js"; /** * Test for wallet balance error messages / different types of insufficient balance. @@ -41,72 +45,17 @@ import { withdrawViaBank } from "../harness/helpers.js"; export async function runWalletBalanceTest(t: GlobalTestState) { // Set up test environment - const db = await setupDb(t); - - const bank = await FakebankService.create(t, { - allowRegistrations: true, - currency: "TESTKUDOS", - database: db.connStr, - httpPort: 8082, - }); - - const exchange = ExchangeService.create(t, { - name: "testexchange-1", - currency: "TESTKUDOS", - httpPort: 8081, - database: db.connStr, - }); - - const merchant = await MerchantService.create(t, { - name: "testmerchant-1", - currency: "TESTKUDOS", - httpPort: 8083, - database: db.connStr, - }); - - const exchangeBankAccount = await bank.createExchangeAccount( - "myexchange", - "x", - ); - exchange.addBankAccount("1", exchangeBankAccount); - - bank.setSuggestedExchange(exchange, exchangeBankAccount.accountPaytoUri); - - await bank.start(); - - await bank.pingUntilAvailable(); - - const coinConfig: CoinConfig[] = defaultCoinConfig.map((x) => x("TESTKUDOS")); - exchange.addCoinConfigList(coinConfig); - - await exchange.start(); - await exchange.pingUntilAvailable(); - - merchant.addExchange(exchange); - - await merchant.start(); - await merchant.pingUntilAvailable(); - - // Fakebank uses x-taler-bank, but merchant is configured to only accept sepa! - const label = "mymerchant"; - await merchant.addInstance({ - id: "default", - name: "Default Instance", - paytoUris: [ - `payto://iban/SANDBOXX/${getRandomIban(label)}?receiver-name=${label}`, - ], - defaultWireTransferDelay: Duration.toTalerProtocolDuration( - Duration.fromSpec({ minutes: 1 }), - ), - }); - - console.log("setup done!"); - - const wallet = new WalletCli(t); + const { merchant, walletClient, exchange, bank } = + await createSimpleTestkudosEnvironmentV2(t); // Withdraw digital cash into the wallet. - await withdrawViaBank(t, { wallet, bank, exchange, amount: "TESTKUDOS:20" }); + await withdrawViaBankV2(t, { + walletClient, + bank, + exchange, + amount: "TESTKUDOS:20", + }); const order = { summary: "Buy me!", @@ -126,7 +75,7 @@ export async function runWalletBalanceTest(t: GlobalTestState) { // Make wallet pay for the order - const preparePayResult = await wallet.client.call( + const preparePayResult = await walletClient.call( WalletApiOperation.PreparePayForUri, { talerPayUri: orderStatus.taler_pay_uri, @@ -152,7 +101,7 @@ export async function runWalletBalanceTest(t: GlobalTestState) { Amounts.isZero(preparePayResult.balanceDetails.balanceMerchantDepositable), ); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); } runWalletBalanceTest.suites = ["wallet"]; diff --git a/packages/taler-harness/src/integrationtests/test-wallet-dbless.ts b/packages/taler-harness/src/integrationtests/test-wallet-dbless.ts index c384a6e74..58f564f34 100644 --- a/packages/taler-harness/src/integrationtests/test-wallet-dbless.ts +++ b/packages/taler-harness/src/integrationtests/test-wallet-dbless.ts @@ -37,7 +37,7 @@ import { withdrawCoin, } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState } from "../harness/harness.js"; -import { createSimpleTestkudosEnvironment } from "../harness/helpers.js"; +import { createSimpleTestkudosEnvironmentV2 } from "../harness/helpers.js"; /** * Run test for basic, bank-integrated withdrawal and payment. @@ -45,7 +45,7 @@ import { createSimpleTestkudosEnvironment } from "../harness/helpers.js"; export async function runWalletDblessTest(t: GlobalTestState) { // Set up test environment - const { bank, exchange } = await createSimpleTestkudosEnvironment(t); + const { bank, exchange } = await createSimpleTestkudosEnvironmentV2(t); const http = createPlatformHttpLib({ allowHttp: true, diff --git a/packages/taler-harness/src/integrationtests/test-wallet-notifications.ts b/packages/taler-harness/src/integrationtests/test-wallet-notifications.ts index 810250f53..c70fd51d4 100644 --- a/packages/taler-harness/src/integrationtests/test-wallet-notifications.ts +++ b/packages/taler-harness/src/integrationtests/test-wallet-notifications.ts @@ -18,27 +18,24 @@ * Imports. */ import { - Amounts, Duration, NotificationType, - PreparePayResultType, TransactionMajorState, } from "@gnu-taler/taler-util"; import { - BankAccessApi, - BankApi, + BankAccessApiClient, WalletApiOperation, } from "@gnu-taler/taler-wallet-core"; import { CoinConfig, defaultCoinConfig } from "../harness/denomStructures.js"; import { ExchangeService, FakebankService, - getRandomIban, GlobalTestState, MerchantService, - setupDb, WalletClient, WalletService, + getRandomIban, + setupDb, } from "../harness/harness.js"; /** @@ -126,10 +123,14 @@ export async function runWalletNotificationsTest(t: GlobalTestState) { skipDefaults: true, }); - const user = await BankApi.createRandomBankUser(bank); - const wop = await BankAccessApi.createWithdrawalOperation( - bank, - user, + const bankAccessApiClient = new BankAccessApiClient({ + allowHttp: true, + baseUrl: bank.bankAccessApiBaseUrl, + }); + const user = await bankAccessApiClient.createRandomBankUser(); + bankAccessApiClient.setAuth(user); + const wop = await bankAccessApiClient.createWithdrawalOperation( + user.username, "TESTKUDOS:20", ); @@ -163,7 +164,7 @@ export async function runWalletNotificationsTest(t: GlobalTestState) { // Confirm it - await BankApi.confirmWithdrawalOperation(bank, user, wop); + await bankAccessApiClient.confirmWithdrawalOperation(user.username, wop); await withdrawalFinishedReceivedPromise; } diff --git a/packages/taler-harness/src/integrationtests/test-withdrawal-abort-bank.ts b/packages/taler-harness/src/integrationtests/test-withdrawal-abort-bank.ts index bf2dc0133..c3069c317 100644 --- a/packages/taler-harness/src/integrationtests/test-withdrawal-abort-bank.ts +++ b/packages/taler-harness/src/integrationtests/test-withdrawal-abort-bank.ts @@ -20,8 +20,7 @@ import { TalerErrorCode } from "@gnu-taler/taler-util"; import { WalletApiOperation, - BankApi, - BankAccessApi, + BankAccessApiClient, } from "@gnu-taler/taler-wallet-core"; import { GlobalTestState } from "../harness/harness.js"; import { createSimpleTestkudosEnvironment } from "../harness/helpers.js"; @@ -36,10 +35,14 @@ export async function runWithdrawalAbortBankTest(t: GlobalTestState) { // Create a withdrawal operation - const user = await BankApi.createRandomBankUser(bank); - const wop = await BankAccessApi.createWithdrawalOperation( - bank, - user, + const bankAccessApiClient = new BankAccessApiClient({ + allowHttp: true, + baseUrl: bank.bankAccessApiBaseUrl, + }); + const user = await bankAccessApiClient.createRandomBankUser(); + bankAccessApiClient.setAuth(user); + const wop = await bankAccessApiClient.createWithdrawalOperation( + user.username, "TESTKUDOS:10", ); @@ -53,8 +56,7 @@ export async function runWithdrawalAbortBankTest(t: GlobalTestState) { // Abort it - await BankApi.abortWithdrawalOperation(bank, user, wop); - //await BankApi.confirmWithdrawalOperation(bank, user, wop); + await bankAccessApiClient.abortWithdrawalOperation(user.username, wop); // Withdraw diff --git a/packages/taler-harness/src/integrationtests/test-withdrawal-bank-integrated.ts b/packages/taler-harness/src/integrationtests/test-withdrawal-bank-integrated.ts index 396f0f03f..61687ec02 100644 --- a/packages/taler-harness/src/integrationtests/test-withdrawal-bank-integrated.ts +++ b/packages/taler-harness/src/integrationtests/test-withdrawal-bank-integrated.ts @@ -19,11 +19,7 @@ */ import { GlobalTestState } from "../harness/harness.js"; import { createSimpleTestkudosEnvironmentV2 } from "../harness/helpers.js"; -import { - WalletApiOperation, - BankApi, - BankAccessApi, -} from "@gnu-taler/taler-wallet-core"; +import { BankAccessApiClient, WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { j2s, NotificationType, @@ -44,10 +40,14 @@ export async function runWithdrawalBankIntegratedTest(t: GlobalTestState) { // Create a withdrawal operation - const user = await BankApi.createRandomBankUser(bank); - const wop = await BankAccessApi.createWithdrawalOperation( - bank, - user, + const bankAccessApiClient = new BankAccessApiClient({ + allowHttp: true, + baseUrl: bank.bankAccessApiBaseUrl, + }); + const user = await bankAccessApiClient.createRandomBankUser(); + bankAccessApiClient.setAuth(user); + const wop = await bankAccessApiClient.createWithdrawalOperation( + user.username, "TESTKUDOS:10", ); @@ -129,7 +129,7 @@ export async function runWithdrawalBankIntegratedTest(t: GlobalTestState) { // Confirm it - await BankApi.confirmWithdrawalOperation(bank, user, wop); + await bankAccessApiClient.confirmWithdrawalOperation(user.username, wop); await withdrawalBankConfirmedCond; diff --git a/packages/taler-harness/src/integrationtests/test-withdrawal-fees.ts b/packages/taler-harness/src/integrationtests/test-withdrawal-fees.ts index 065b134c4..06355b964 100644 --- a/packages/taler-harness/src/integrationtests/test-withdrawal-fees.ts +++ b/packages/taler-harness/src/integrationtests/test-withdrawal-fees.ts @@ -26,6 +26,7 @@ import { } from "../harness/harness.js"; import { BankAccessApi, + BankAccessApiClient, BankApi, WalletApiOperation, } from "@gnu-taler/taler-wallet-core"; @@ -112,8 +113,13 @@ export async function runWithdrawalFeesTest(t: GlobalTestState) { const amount = "TESTKUDOS:7.5"; - const user = await BankApi.createRandomBankUser(bank); - const wop = await BankAccessApi.createWithdrawalOperation(bank, user, amount); + const bankAccessApiClient = new BankAccessApiClient({ + allowHttp: true, + baseUrl: bank.bankAccessApiBaseUrl, + }); + const user = await bankAccessApiClient.createRandomBankUser(); + bankAccessApiClient.setAuth(user); + const wop = await bankAccessApiClient.createWithdrawalOperation(user.username, amount); // Hand it to the wallet @@ -150,10 +156,7 @@ export async function runWithdrawalFeesTest(t: GlobalTestState) { // Confirm it - await BankApi.confirmWithdrawalOperation(bank, user, wop); - - await exchange.runWirewatchOnce(); - + await bankAccessApiClient.confirmWithdrawalOperation(user.username, wop); await wallet.runUntilDone(); // Check balance diff --git a/packages/taler-harness/src/integrationtests/test-withdrawal-huge.ts b/packages/taler-harness/src/integrationtests/test-withdrawal-huge.ts index f56e4d24d..a9d544ee0 100644 --- a/packages/taler-harness/src/integrationtests/test-withdrawal-huge.ts +++ b/packages/taler-harness/src/integrationtests/test-withdrawal-huge.ts @@ -27,7 +27,11 @@ import { } from "../harness/harness.js"; import { WalletApiOperation } from "@gnu-taler/taler-wallet-core"; import { CoinConfig, defaultCoinConfig } from "../harness/denomStructures.js"; -import { NotificationType, TransactionMajorState, URL } from "@gnu-taler/taler-util"; +import { + NotificationType, + TransactionMajorState, + URL, +} from "@gnu-taler/taler-util"; /** * Withdraw a high amount. Mostly intended as a perf test. @@ -84,7 +88,8 @@ export async function runWithdrawalHugeTest(t: GlobalTestState) { await wallet.connect(); const withdrawalFinishedCond = wallet.waitForNotificationCond( - (wn) => wn.type === NotificationType.TransactionStateTransition && + (wn) => + wn.type === NotificationType.TransactionStateTransition && wn.transactionId.startsWith("txn:withdrawal:") && wn.newTxState.major === TransactionMajorState.Done, ); diff --git a/packages/taler-harness/src/integrationtests/test-withdrawal-manual.ts b/packages/taler-harness/src/integrationtests/test-withdrawal-manual.ts index a356a5c1a..d49235f89 100644 --- a/packages/taler-harness/src/integrationtests/test-withdrawal-manual.ts +++ b/packages/taler-harness/src/integrationtests/test-withdrawal-manual.ts @@ -17,14 +17,14 @@ /** * Imports. */ -import { GlobalTestState } from "../harness/harness.js"; -import { createSimpleTestkudosEnvironment } from "../harness/helpers.js"; +import { AbsoluteTime, Logger, j2s } from "@gnu-taler/taler-util"; import { + BankAccessApiClient, WalletApiOperation, - BankApi, WireGatewayApiClient, } from "@gnu-taler/taler-wallet-core"; -import { AbsoluteTime, j2s, Logger } from "@gnu-taler/taler-util"; +import { GlobalTestState } from "../harness/harness.js"; +import { createSimpleTestkudosEnvironmentV2 } from "../harness/helpers.js"; const logger = new Logger("test-withdrawal-manual.ts"); @@ -34,14 +34,19 @@ const logger = new Logger("test-withdrawal-manual.ts"); export async function runWithdrawalManualTest(t: GlobalTestState) { // Set up test environment - const { wallet, bank, exchange, exchangeBankAccount } = - await createSimpleTestkudosEnvironment(t); + const { walletClient, bank, exchange, exchangeBankAccount } = + await createSimpleTestkudosEnvironmentV2(t); // Create a withdrawal operation - const user = await BankApi.createRandomBankUser(bank); + const bankAccessApiClient = new BankAccessApiClient({ + baseUrl: bank.bankAccessApiBaseUrl, + allowHttp: true, + }); + + const user = await bankAccessApiClient.createRandomBankUser(); - await wallet.client.call(WalletApiOperation.AddExchange, { + await walletClient.call(WalletApiOperation.AddExchange, { exchangeBaseUrl: exchange.baseUrl, }); @@ -50,7 +55,7 @@ export async function runWithdrawalManualTest(t: GlobalTestState) { logger.info("starting AcceptManualWithdrawal request"); // We expect this to return immediately. - const wres = await wallet.client.call( + const wres = await walletClient.call( WalletApiOperation.AcceptManualWithdrawal, { exchangeBaseUrl: exchange.baseUrl, @@ -84,11 +89,11 @@ export async function runWithdrawalManualTest(t: GlobalTestState) { await exchange.runWirewatchOnce(); - await wallet.runUntilDone(); + await walletClient.call(WalletApiOperation.TestingWaitTransactionsFinal, {}); // Check balance - const balResp = await wallet.client.call(WalletApiOperation.GetBalances, {}); + const balResp = await walletClient.call(WalletApiOperation.GetBalances, {}); t.assertAmountEquals("TESTKUDOS:9.72", balResp.balances[0].available); await t.shutdown(); diff --git a/packages/taler-harness/src/integrationtests/testrunner.ts b/packages/taler-harness/src/integrationtests/testrunner.ts index c1b06f21e..cbdca04b9 100644 --- a/packages/taler-harness/src/integrationtests/testrunner.ts +++ b/packages/taler-harness/src/integrationtests/testrunner.ts @@ -494,8 +494,6 @@ if (runTestInstrStr && process.argv.includes("__TWCLI_TESTWORKER")) { runTestInstrStr, ) as RunTestChildInstruction; - setGlobalLogLevelFromString("TRACE"); - process.on("disconnect", () => { logger.trace("got disconnect from parent"); process.exit(3); diff --git a/packages/taler-util/src/talerconfig.ts b/packages/taler-util/src/talerconfig.ts index 59c789cae..948ccb9c4 100644 --- a/packages/taler-util/src/talerconfig.ts +++ b/packages/taler-util/src/talerconfig.ts @@ -39,10 +39,20 @@ export class ConfigError extends Error { } } +enum EntryOrigin { + // From a default file + Default = 1, + // Loaded from file or string + Loaded = 2, + // Changed after loading + Changed = 3, +} + interface Entry { value: string; sourceLine: number; sourceFile: string; + origin: EntryOrigin; } interface Section { @@ -195,6 +205,7 @@ export interface LoadOptions { export interface StringifyOptions { diagnostics?: boolean; + excludeDefaults?: boolean; } export interface LoadedFile { @@ -282,7 +293,11 @@ export class Configuration { private nestLevel = 0; - private loadFromFilename(filename: string, opts: LoadOptions = {}): void { + private loadFromFilename( + filename: string, + isDefaultSource: boolean, + opts: LoadOptions = {}, + ): void { filename = expandPath(filename); const checkCycle = () => { @@ -309,7 +324,7 @@ export class Configuration { const oldNestLevel = this.nestLevel; this.nestLevel += 1; try { - this.loadFromString(s, { + this.internalLoadFromString(s, isDefaultSource, { ...opts, filename: filename, }); @@ -318,7 +333,11 @@ export class Configuration { } } - private loadGlob(parentFilename: string, fileglob: string): void { + private loadGlob( + parentFilename: string, + isDefaultSource: boolean, + fileglob: string, + ): void { const resolvedParent = nodejs_fs.realpathSync(parentFilename); const parentDir = nodejs_path.dirname(resolvedParent); @@ -339,12 +358,16 @@ export class Configuration { for (const f of files) { if (globMatch(tail, f)) { const fullPath = nodejs_path.join(head, f); - this.loadFromFilename(fullPath); + this.loadFromFilename(fullPath, isDefaultSource); } } } - private loadSecret(sectionName: string, filename: string): void { + private loadSecret( + sectionName: string, + filename: string, + isDefaultSource: boolean, + ): void { const sec = this.provideSection(sectionName); sec.secretFilename = filename; const otherCfg = new Configuration(); @@ -354,7 +377,7 @@ export class Configuration { sec.inaccessible = true; return; } - otherCfg.loadFromFilename(filename, { + otherCfg.loadFromFilename(filename, isDefaultSource, { banDirectives: true, }); const otherSec = otherCfg.provideSection(sectionName); @@ -363,7 +386,11 @@ export class Configuration { } } - loadFromString(s: string, opts: LoadOptions = {}): void { + private internalLoadFromString( + s: string, + isDefaultSource: boolean, + opts: LoadOptions = {}, + ): void { let lineNo = 0; const fn = opts.filename ?? "<input>"; const reComment = /^\s*#.*$/; @@ -399,7 +426,10 @@ export class Configuration { ); } const arg = directiveMatch[2].trim(); - this.loadFromFilename(normalizeInlineFilename(opts.filename, arg)); + this.loadFromFilename( + normalizeInlineFilename(opts.filename, arg), + isDefaultSource, + ); break; } case "inline-secret": { @@ -419,7 +449,7 @@ export class Configuration { opts.filename, sp[1], ); - this.loadSecret(sp[0], secretFilename); + this.loadSecret(sp[0], secretFilename, isDefaultSource); break; } case "inline-matching": { @@ -429,7 +459,7 @@ export class Configuration { `invalid configuration, @inline-matching@ directive in ${fn}:${lineNo} can only be used from a file`, ); } - this.loadGlob(opts.filename, arg); + this.loadGlob(opts.filename, isDefaultSource, arg); break; } default: @@ -462,6 +492,7 @@ export class Configuration { value: val, sourceFile: opts.filename ?? "<unknown>", sourceLine: lineNo, + origin: isDefaultSource ? EntryOrigin.Default : EntryOrigin.Loaded, }; continue; } @@ -471,6 +502,10 @@ export class Configuration { } } + loadFromString(s: string, opts: LoadOptions = {}): void { + return this.internalLoadFromString(s, false, opts); + } + private provideSection(section: string): Section { const secNorm = section.toUpperCase(); if (this.sectionMap[secNorm]) { @@ -496,6 +531,7 @@ export class Configuration { value, sourceLine: 0, sourceFile: "<unknown>", + origin: EntryOrigin.Changed, }; } @@ -578,11 +614,11 @@ export class Configuration { ); } - loadFrom(dirname: string): void { + loadDefaultsFromDir(dirname: string): void { const files = nodejs_fs.readdirSync(dirname); for (const f of files) { const fn = nodejs_path.join(dirname, f); - this.loadFromFilename(fn); + this.loadFromFilename(fn, true); } } @@ -601,7 +637,7 @@ export class Configuration { if (!bc) { bc = "/usr/share/taler/config.d"; } - this.loadFrom(bc); + this.loadDefaultsFromDir(bc); } getDefaultConfigFilename(): string | undefined { @@ -631,11 +667,13 @@ export class Configuration { const cfg = new Configuration(); cfg.loadDefaults(); if (filename) { - cfg.loadFromFilename(filename); + cfg.loadFromFilename(filename, false); } else { const fn = cfg.getDefaultConfigFilename(); if (fn) { - cfg.loadFromFilename(fn); + // It's the default filename for the main config file, + // but we don't consider the values default values. + cfg.loadFromFilename(fn, false); } } cfg.hintEntrypoint = filename; @@ -657,13 +695,20 @@ export class Configuration { } for (const sectionName of Object.keys(this.sectionMap)) { const sec = this.sectionMap[sectionName]; - if (opts.diagnostics && sec.secretFilename) { - s += `# Secret section from ${sec.secretFilename}\n`; - s += `# Secret accessible: ${!sec.inaccessible}\n`; - } - s += `[${sectionName}]\n`; + let headerWritten = false; for (const optionName of Object.keys(sec.entries)) { const entry = this.sectionMap[sectionName].entries[optionName]; + if (opts.excludeDefaults && entry.origin === EntryOrigin.Default) { + continue; + } + if (!headerWritten) { + if (opts.diagnostics && sec.secretFilename) { + s += `# Secret section from ${sec.secretFilename}\n`; + s += `# Secret accessible: ${!sec.inaccessible}\n`; + } + s += `[${sectionName}]\n`; + headerWritten = true; + } if (entry !== undefined) { if (opts.diagnostics) { s += `# ${entry.sourceFile}:${entry.sourceLine}\n`; @@ -671,12 +716,17 @@ export class Configuration { s += `${optionName} = ${entry.value}\n`; } } - s += "\n"; + if (headerWritten) { + s += "\n"; + } } return s; } - write(filename: string): void { - nodejs_fs.writeFileSync(filename, this.stringify()); + write(filename: string, opts: { excludeDefaults?: boolean } = {}): void { + nodejs_fs.writeFileSync( + filename, + this.stringify({ excludeDefaults: opts.excludeDefaults }), + ); } } diff --git a/packages/taler-wallet-core/src/bank-api-client.ts b/packages/taler-wallet-core/src/bank-api-client.ts index 01c28e8e8..8e351cb48 100644 --- a/packages/taler-wallet-core/src/bank-api-client.ts +++ b/packages/taler-wallet-core/src/bank-api-client.ts @@ -267,8 +267,7 @@ export namespace BankAccessApi { export interface BankAccessApiClientArgs { baseUrl: string; - username: string; - password: string; + auth?: { username: string; password: string }; enableThrottling?: boolean; allowHttp?: boolean; } @@ -339,19 +338,33 @@ export class BankAccessApiClient { }); } - async getTransactions(): Promise<void> { + setAuth(auth: { username: string; password: string }) { + this.args.auth = auth; + } + + private makeAuthHeader(): Record<string, string> { + if (!this.args.auth) { + return {}; + } + const authHeaderValue = makeBasicAuthHeader( + this.args.auth.username, + this.args.auth.password, + ); + return { + Authorization: authHeaderValue, + }; + } + + async getTransactions(username: string): Promise<void> { + const auth = this.args.auth; const reqUrl = new URL( - `accounts/${this.args.username}/transactions`, + `accounts/${username}/transactions`, this.args.baseUrl, ); - const authHeaderValue = makeBasicAuthHeader( - this.args.username, - this.args.password, - ); const resp = await this.httpLib.fetch(reqUrl.href, { method: "GET", headers: { - Authorization: authHeaderValue, + ...this.makeAuthHeader(), }, }); @@ -360,24 +373,128 @@ export class BankAccessApiClient { } async createTransaction( + username: string, req: BankAccessApiCreateTransactionRequest, ): Promise<any> { const reqUrl = new URL( - `accounts/${this.args.username}/transactions`, + `accounts/${username}/transactions`, this.args.baseUrl, ); - const authHeaderValue = makeBasicAuthHeader( - this.args.username, - this.args.password, - ); + const resp = await this.httpLib.fetch(reqUrl.href, { method: "POST", body: req, - headers: { - Authorization: authHeaderValue, - }, + headers: this.makeAuthHeader(), }); return await readSuccessResponseJsonOrThrow(resp, codecForAny()); } + + async registerAccount( + username: string, + password: string, + options: { + iban?: string; + }, + ): Promise<BankUser> { + const url = new URL("testing/register", this.args.baseUrl); + const resp = await this.httpLib.fetch(url.href, { + method: "POST", + body: { + username, + password, + iban: options?.iban, + }, + }); + let paytoUri = `payto://x-taler-bank/localhost/${username}`; + if (resp.status !== 200 && resp.status !== 202 && resp.status !== 204) { + logger.error(`${j2s(await resp.json())}`); + throw TalerError.fromDetail( + TalerErrorCode.GENERIC_UNEXPECTED_REQUEST_ERROR, + { + httpStatusCode: resp.status, + }, + ); + } + try { + // Pybank has no body, thus this might throw. + const respJson = await resp.json(); + // LibEuFin demobank returns payto URI in response + if (respJson.paytoUri) { + paytoUri = respJson.paytoUri; + } + } catch (e) { + // Do nothing + } + return { + password, + username, + accountPaytoUri: paytoUri, + }; + } + + async createRandomBankUser(): Promise<BankUser> { + const username = "user-" + encodeCrock(getRandomBytes(10)).toLowerCase(); + const password = "pw-" + encodeCrock(getRandomBytes(10)).toLowerCase(); + // FIXME: This is just a temporary workaround, because demobank is running out of short IBANs + const iban = generateIban("DE", 15); + return await this.registerAccount(username, password, { + iban, + }); + } + + async createWithdrawalOperation( + user: string, + amount: string, + ): Promise<WithdrawalOperationInfo> { + const url = new URL(`accounts/${user}/withdrawals`, this.args.baseUrl); + const resp = await this.httpLib.fetch(url.href, { + method: "POST", + body: { + amount, + }, + headers: this.makeAuthHeader(), + }); + return readSuccessResponseJsonOrThrow( + resp, + codecForWithdrawalOperationInfo(), + ); + } + + async confirmWithdrawalOperation( + username: string, + wopi: WithdrawalOperationInfo, + ): Promise<void> { + const url = new URL( + `accounts/${username}/withdrawals/${wopi.withdrawal_id}/confirm`, + this.args.baseUrl, + ); + logger.info(`confirming withdrawal operation via ${url.href}`); + const resp = await this.httpLib.fetch(url.href, { + method: "POST", + body: {}, + headers: this.makeAuthHeader(), + }); + + logger.info(`response status ${resp.status}`); + const respJson = await readSuccessResponseJsonOrThrow(resp, codecForAny()); + + // FIXME: We don't check the status here! + } + + async abortWithdrawalOperation( + accountName: string, + wopi: WithdrawalOperationInfo, + ): Promise<void> { + const url = new URL( + `accounts/${accountName}/withdrawals/${wopi.withdrawal_id}/abort`, + this.args.baseUrl, + ); + const resp = await this.httpLib.fetch(url.href, { + method: "POST", + body: {}, + headers: this.makeAuthHeader(), + }); + await readSuccessResponseJsonOrThrow(resp, codecForAny()); + } } |