gnunet-svn
[Top][All Lists]
Advanced

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

[taler-wallet-core] 01/02: address first batch of transaction list issue


From: gnunet
Subject: [taler-wallet-core] 01/02: address first batch of transaction list issues
Date: Fri, 15 May 2020 13:09:47 +0200

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

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

commit 3eb88574bcf327672c34120becfb511eac4e06cd
Author: Florian Dold <address@hidden>
AuthorDate: Fri May 15 16:03:52 2020 +0530

    address first batch of transaction list issues
---
 src/db.ts                      |   2 +-
 src/operations/pay.ts          |  10 ++--
 src/operations/reserves.ts     |  51 ++++++++--------
 src/operations/tip.ts          |  16 ++----
 src/operations/transactions.ts |  55 ++++--------------
 src/operations/withdraw.ts     |  20 ++++++-
 src/types/dbTypes.ts           |  22 ++++---
 src/types/talerTypes.ts        |  94 +++++++++++++++++++++++++++---
 src/types/transactions.ts      | 128 +++++++++++++++++++++++++++++------------
 9 files changed, 257 insertions(+), 141 deletions(-)

diff --git a/src/db.ts b/src/db.ts
index 098767b5..19737202 100644
--- a/src/db.ts
+++ b/src/db.ts
@@ -7,7 +7,7 @@ import { openDatabase, Database, Store, Index } from 
"./util/query";
  * with each major change.  When incrementing the major version,
  * the wallet should import data from the previous version.
  */
-const TALER_DB_NAME = "taler-walletdb-v3";
+const TALER_DB_NAME = "taler-walletdb-v4";
 
 /**
  * Current database minor version, should be incremented
diff --git a/src/operations/pay.ts b/src/operations/pay.ts
index 45caa958..20d62dea 100644
--- a/src/operations/pay.ts
+++ b/src/operations/pay.ts
@@ -137,11 +137,7 @@ export async function getTotalPaymentCost(
   ws: InternalWalletState,
   pcs: PayCoinSelection,
 ): Promise<PayCostInfo> {
-  const costs = [
-    pcs.paymentAmount,
-    pcs.customerDepositFees,
-    pcs.customerWireFees,
-  ];
+  const costs = [];
   for (let i = 0; i < pcs.coinPubs.length; i++) {
     const coin = await ws.db.get(Stores.coins, pcs.coinPubs[i]);
     if (!coin) {
@@ -165,6 +161,7 @@ export async function getTotalPaymentCost(
     const amountLeft = Amounts.sub(denom.value, pcs.coinContributions[i])
       .amount;
     const refreshCost = getTotalRefreshCost(allDenoms, denom, amountLeft);
+    costs.push(pcs.coinContributions[i]);
     costs.push(refreshCost);
   }
   return {
@@ -670,6 +667,9 @@ async function processDownloadProposalImpl(
           wireMethod: parsedContractTerms.wire_method,
           wireInfoHash: parsedContractTerms.h_wire,
           maxDepositFee: Amounts.parseOrThrow(parsedContractTerms.max_fee),
+          merchant: parsedContractTerms.merchant,
+          products: parsedContractTerms.products,
+          summaryI18n: parsedContractTerms.summary_i18n,
         },
         contractTermsRaw: JSON.stringify(proposalResp.contract_terms),
       };
diff --git a/src/operations/reserves.ts b/src/operations/reserves.ts
index 347f6e89..3d45d8d5 100644
--- a/src/operations/reserves.ts
+++ b/src/operations/reserves.ts
@@ -35,6 +35,7 @@ import {
   WalletReserveHistoryItemType,
   WithdrawalSourceType,
   ReserveHistoryRecord,
+  ReserveBankInfo,
 } from "../types/dbTypes";
 import { Logger } from "../util/logging";
 import { Amounts } from "../util/amounts";
@@ -48,9 +49,11 @@ import { assertUnreachable } from 
"../util/assertUnreachable";
 import { encodeCrock, getRandomBytes } from "../crypto/talerCrypto";
 import { randomBytes } from "../crypto/primitives/nacl-fast";
 import {
-  getVerifiedWithdrawDenomList,
+  selectWithdrawalDenoms,
   processWithdrawGroup,
   getBankWithdrawalInfo,
+  denomSelectionInfoToState,
+  getWithdrawDenomList,
 } from "./withdraw";
 import {
   guardOperationException,
@@ -100,6 +103,20 @@ export async function createReserve(
     reserveStatus = ReserveRecordStatus.UNCONFIRMED;
   }
 
+  let bankInfo: ReserveBankInfo | undefined;
+
+  if (req.bankWithdrawStatusUrl) {
+    const denomSelInfo = await selectWithdrawalDenoms(ws, canonExchange, 
req.amount);
+    const denomSel = denomSelectionInfoToState(denomSelInfo);
+    bankInfo = {
+      statusUrl: req.bankWithdrawStatusUrl,
+      amount: req.amount,
+      bankWithdrawalGroupId: encodeCrock(getRandomBytes(32)),
+      withdrawalStarted: false,
+      denomSel,
+    };
+  }
+
   const reserveRecord: ReserveRecord = {
     timestampCreated: now,
     exchangeBaseUrl: canonExchange,
@@ -108,14 +125,7 @@ export async function createReserve(
     senderWire: req.senderWire,
     timestampConfirmed: undefined,
     timestampReserveInfoPosted: undefined,
-    bankInfo: req.bankWithdrawStatusUrl
-      ? {
-          statusUrl: req.bankWithdrawStatusUrl,
-          amount: req.amount,
-          bankWithdrawalGroupId: encodeCrock(getRandomBytes(32)),
-          withdrawalStarted: false,
-        }
-      : undefined,
+    bankInfo,
     exchangeWire: req.exchangeWire,
     reserveStatus,
     lastSuccessfulStatusQuery: undefined,
@@ -286,10 +296,11 @@ async function registerReserveWithBank(
     default:
       return;
   }
-  const bankStatusUrl = reserve.bankInfo?.statusUrl;
-  if (!bankStatusUrl) {
+  const bankInfo = reserve.bankInfo;
+  if (!bankInfo) {
     return;
   }
+  const bankStatusUrl = bankInfo.statusUrl;
   console.log("making selection");
   if (reserve.timestampReserveInfoPosted) {
     throw Error("bank claims that reserve info selection is not done");
@@ -309,6 +320,9 @@ async function registerReserveWithBank(
     }
     r.timestampReserveInfoPosted = getTimestampNow();
     r.reserveStatus = ReserveRecordStatus.WAIT_CONFIRM_BANK;
+    if (!r.bankInfo) {
+      throw Error("invariant failed");
+    }
     r.retryInfo = initRetryInfo();
     return r;
   });
@@ -657,7 +671,7 @@ async function depleteReserve(
 
   logger.trace(`getting denom list`);
 
-  const denomsForWithdraw = await getVerifiedWithdrawDenomList(
+  const denomsForWithdraw = await selectWithdrawalDenoms(
     ws,
     reserve.exchangeBaseUrl,
     withdrawAmount,
@@ -752,17 +766,8 @@ async function depleteReserve(
         retryInfo: initRetryInfo(),
         lastErrorPerCoin: {},
         lastError: undefined,
-        denomsSel: {
-          totalCoinValue: denomsForWithdraw.totalCoinValue,
-          totalWithdrawCost: denomsForWithdraw.totalWithdrawCost,
-          selectedDenoms: denomsForWithdraw.selectedDenoms.map((x) => {
-            return {
-              count: x.count,
-              denomPubHash: x.denom.denomPubHash,
-            };
-          }),
-        },
-      };    
+        denomsSel: denomSelectionInfoToState(denomsForWithdraw),
+      };
 
       await tx.put(Stores.reserves, newReserve);
       await tx.put(Stores.reserveHistory, newHist);
diff --git a/src/operations/tip.ts b/src/operations/tip.ts
index f584fc50..15d2339b 100644
--- a/src/operations/tip.ts
+++ b/src/operations/tip.ts
@@ -34,8 +34,9 @@ import {
 } from "../types/dbTypes";
 import {
   getExchangeWithdrawalInfo,
-  getVerifiedWithdrawDenomList,
+  selectWithdrawalDenoms,
   processWithdrawGroup,
+  denomSelectionInfoToState,
 } from "./withdraw";
 import { updateExchangeFromUrl } from "./exchanges";
 import { getRandomBytes, encodeCrock } from "../crypto/talerCrypto";
@@ -81,7 +82,7 @@ export async function getTipStatus(
     );
 
     const tipId = encodeCrock(getRandomBytes(32));
-    const selectedDenoms = await getVerifiedWithdrawDenomList(
+    const selectedDenoms = await selectWithdrawalDenoms(
       ws,
       tipPickupStatus.exchange_url,
       amount,
@@ -107,16 +108,7 @@ export async function getTipStatus(
       ).amount,
       retryInfo: initRetryInfo(),
       lastError: undefined,
-      denomsSel: {
-        totalCoinValue: selectedDenoms.totalCoinValue,
-        totalWithdrawCost: selectedDenoms.totalWithdrawCost,
-        selectedDenoms: selectedDenoms.selectedDenoms.map((x) => {
-          return {
-            count: x.count,
-            denomPubHash: x.denom.denomPubHash,
-          };
-        }),
-      },
+      denomsSel: denomSelectionInfoToState(selectedDenoms),
     };
     await ws.db.put(Stores.tips, tipRecord);
   }
diff --git a/src/operations/transactions.ts b/src/operations/transactions.ts
index 4cc6154b..fd767962 100644
--- a/src/operations/transactions.ts
+++ b/src/operations/transactions.ts
@@ -18,7 +18,7 @@
  * Imports.
  */
 import { InternalWalletState } from "./state";
-import { Stores, ReserveRecordStatus, PurchaseRecord, ProposalStatus } from 
"../types/dbTypes";
+import { Stores, ReserveRecordStatus, PurchaseRecord } from "../types/dbTypes";
 import { Amounts, AmountJson } from "../util/amounts";
 import { timestampCmp } from "../util/time";
 import {
@@ -131,10 +131,8 @@ export async function getTransactions(
           if (wsr.timestampFinish) {
             transactions.push({
               type: TransactionType.Withdrawal,
-              amountEffective: Amounts.stringify(
-                wsr.denomsSel.totalWithdrawCost,
-              ),
-              amountRaw: Amounts.stringify(wsr.denomsSel.totalCoinValue),
+              amountEffective: Amounts.stringify(wsr.denomsSel.totalCoinValue),
+              amountRaw: Amounts.stringify(wsr.denomsSel.totalWithdrawCost),
               confirmed: true,
               exchangeBaseUrl: wsr.exchangeBaseUrl,
               pending: !wsr.timestampFinish,
@@ -163,9 +161,9 @@ export async function getTransactions(
         transactions.push({
           type: TransactionType.Withdrawal,
           confirmed: false,
-          amountRaw: Amounts.stringify(r.bankInfo.amount),
-          amountEffective: undefined,
-          exchangeBaseUrl: undefined,
+          amountRaw: Amounts.stringify(r.bankInfo.denomSel.totalWithdrawCost),
+          amountEffective: 
Amounts.stringify(r.bankInfo.denomSel.totalCoinValue),
+          exchangeBaseUrl: r.exchangeBaseUrl,
           pending: true,
           timestamp: r.timestampCreated,
           bankConfirmationUrl: r.bankInfo.confirmUrl,
@@ -176,38 +174,6 @@ export async function getTransactions(
         });
       });
 
-      tx.iter(Stores.proposals).forEachAsync(async (proposal) => {
-        if (!proposal.download) {
-          return;
-        }
-        if (proposal.proposalStatus !== ProposalStatus.PROPOSED) {
-          return;
-        }
-        const dl = proposal.download;
-        const purchase = await tx.get(Stores.purchases, proposal.proposalId);
-        if (purchase) {
-          return;
-        }
-
-        transactions.push({
-          type: TransactionType.Payment,
-          amountRaw: Amounts.stringify(dl.contractData.amount),
-          amountEffective: undefined,
-          status: PaymentStatus.Offered,
-          pending: true,
-          timestamp: proposal.timestamp,
-          transactionId: makeEventId(TransactionType.Payment, 
proposal.proposalId),
-          info: {
-            fulfillmentUrl: dl.contractData.fulfillmentUrl,
-            merchant: {},
-            orderId: dl.contractData.orderId,
-            products: [],
-            summary: dl.contractData.summary,
-            summary_i18n: {},
-          },
-        });
-      });
-
       tx.iter(Stores.purchases).forEachAsync(async (pr) => {
         if (
           transactionsRequest?.currency &&
@@ -231,11 +197,11 @@ export async function getTransactions(
           transactionId: makeEventId(TransactionType.Payment, pr.proposalId),
           info: {
             fulfillmentUrl: pr.contractData.fulfillmentUrl,
-            merchant: {},
+            merchant: pr.contractData.merchant,
             orderId: pr.contractData.orderId,
-            products: [],
+            products: pr.contractData.products,
             summary: pr.contractData.summary,
-            summary_i18n: {},
+            summary_i18n: pr.contractData.summaryI18n,
           },
         });
 
@@ -258,7 +224,8 @@ export async function getTransactions(
             timestamp: rg.timestampQueried,
             transactionId: makeEventId(
               TransactionType.Refund,
-              `{rg.timestampQueried.t_ms}`,
+              pr.proposalId,
+              `${rg.timestampQueried.t_ms}`,
             ),
             refundedTransactionId: makeEventId(
               TransactionType.Payment,
diff --git a/src/operations/withdraw.ts b/src/operations/withdraw.ts
index 21c30d7a..14071be7 100644
--- a/src/operations/withdraw.ts
+++ b/src/operations/withdraw.ts
@@ -1,6 +1,6 @@
 /*
  This file is part of GNU Taler
- (C) 2019-2029 Taler Systems SA
+ (C) 2019-2020 Taler Systems SA
 
  GNU Taler is free software; you can redistribute it and/or modify it under the
  terms of the GNU General Public License as published by the Free Software
@@ -27,6 +27,7 @@ import {
   DenominationSelectionInfo,
   PlanchetRecord,
   WithdrawalSourceType,
+  DenomSelectionState,
 } from "../types/dbTypes";
 import {
   BankWithdrawDetails,
@@ -419,6 +420,19 @@ async function processPlanchet(
   }
 }
 
+export function denomSelectionInfoToState(dsi: DenominationSelectionInfo): 
DenomSelectionState {
+  return {
+    selectedDenoms: dsi.selectedDenoms.map((x) => {
+      return {
+        count: x.count,
+        denomPubHash: x.denom.denomPubHash
+      };
+    }),
+    totalCoinValue: dsi.totalCoinValue,
+    totalWithdrawCost: dsi.totalWithdrawCost,
+  }
+}
+
 /**
  * Get a list of denominations to withdraw from the given exchange for the
  * given amount, making sure that all denominations' signatures are verified.
@@ -426,7 +440,7 @@ async function processPlanchet(
  * Writes to the DB in order to record the result from verifying
  * denominations.
  */
-export async function getVerifiedWithdrawDenomList(
+export async function selectWithdrawalDenoms(
   ws: InternalWalletState,
   exchangeBaseUrl: string,
   amount: AmountJson,
@@ -603,7 +617,7 @@ export async function getExchangeWithdrawalInfo(
     throw Error(`exchange ${exchangeInfo.baseUrl} wire details not available`);
   }
 
-  const selectedDenoms = await getVerifiedWithdrawDenomList(
+  const selectedDenoms = await selectWithdrawalDenoms(
     ws,
     baseUrl,
     amount,
diff --git a/src/types/dbTypes.ts b/src/types/dbTypes.ts
index 37a66251..79966eb3 100644
--- a/src/types/dbTypes.ts
+++ b/src/types/dbTypes.ts
@@ -31,6 +31,8 @@ import {
   PayReq,
   TipResponse,
   ExchangeSignKeyJson,
+  MerchantInfo,
+  Product,
 } from "./talerTypes";
 
 import { Index, Store } from "../util/query";
@@ -216,6 +218,15 @@ export interface ReserveHistoryRecord {
   reserveTransactions: WalletReserveHistoryItem[];
 }
 
+export interface ReserveBankInfo {
+  statusUrl: string;
+  confirmUrl?: string;
+  amount: AmountJson;
+  bankWithdrawalGroupId: string;
+  withdrawalStarted: boolean;
+  denomSel: DenomSelectionState;
+}
+
 /**
  * A reserve record as stored in the wallet's database.
  */
@@ -278,13 +289,7 @@ export interface ReserveRecord {
    * Extra state for when this is a withdrawal involving
    * a Taler-integrated bank.
    */
-  bankInfo?: {
-    statusUrl: string;
-    confirmUrl?: string;
-    amount: AmountJson;
-    bankWithdrawalGroupId: string;
-    withdrawalStarted: boolean;
-  };
+  bankInfo?: ReserveBankInfo;
 
   reserveStatus: ReserveRecordStatus;
 
@@ -1179,10 +1184,13 @@ export interface AllowedExchangeInfo {
  * processing in the wallet.
  */
 export interface WalletContractData {
+  products?: Product[];
+  summaryI18n: { [lang_tag: string]: string } | undefined;
   fulfillmentUrl: string;
   contractTermsHash: string;
   merchantSig: string;
   merchantPub: string;
+  merchant: MerchantInfo;
   amount: AmountJson;
   orderId: string;
   merchantBaseUrl: string;
diff --git a/src/types/talerTypes.ts b/src/types/talerTypes.ts
index 17d11eea..eb10d6e1 100644
--- a/src/types/talerTypes.ts
+++ b/src/types/talerTypes.ts
@@ -260,6 +260,55 @@ export class AuditorHandle {
   url: string;
 }
 
+export interface MerchantInfo {
+  name: string;
+  jurisdiction: string | undefined;
+  address: string | undefined;
+}
+
+export interface Tax {
+  // the name of the tax
+  name: string;
+
+  // amount paid in tax
+  tax: AmountString;
+}
+
+export interface Product {
+  // merchant-internal identifier for the product.
+  product_id?: string;
+
+  // Human-readable product description.
+  description: string;
+
+  // Map from IETF BCP 47 language tags to localized descriptions
+  description_i18n?: { [lang_tag: string]: string };
+
+  // The number of units of the product to deliver to the customer.
+  quantity?: number;
+
+  // The unit in which the product is measured (liters, kilograms, packages, 
etc.)
+  unit?: string;
+
+  // The price of the product; this is the total price for quantity times unit 
of this product.
+  price?: AmountString;
+
+  // An optional base64-encoded product image
+  image?: string;
+
+  // a list of taxes paid by the merchant for this product. Can be empty.
+  taxes?: Tax[];
+
+  // time indicating when this product should be delivered
+  delivery_date?: Timestamp;
+
+  // where to deliver this product. This may be an URL for online delivery
+  // (i.e. 'http://example.com/download' or 'mailto:address@hidden'),
+  // or a location label defined inside the proposition's 'locations'.
+  // The presence of a colon (':') indicates the use of an URL.
+  delivery_location?: string;
+}
+
 /**
  * Contract terms from a merchant.
  */
@@ -284,6 +333,8 @@ export class ContractTerms {
    */
   summary: string;
 
+  summary_i18n?: { [lang_tag: string]: string };
+
   /**
    * Nonce used to ensure freshness.
    */
@@ -317,7 +368,7 @@ export class ContractTerms {
   /**
    * Information about the merchant.
    */
-  merchant: any;
+  merchant: MerchantInfo;
 
   /**
    * Public key of the merchant.
@@ -332,7 +383,7 @@ export class ContractTerms {
   /**
    * Products that are sold in this contract.
    */
-  products?: any[];
+  products?: Product[];
 
   /**
    * Deadline for refunds.
@@ -805,6 +856,35 @@ export const codecForAuditorHandle = (): 
Codec<AuditorHandle> =>
     .property("url", codecForString)
     .build("AuditorHandle");
 
+export const codecForMerchantInfo = (): Codec<MerchantInfo> =>
+  makeCodecForObject<MerchantInfo>()
+    .property("name", codecForString)
+    .property("address", makeCodecOptional(codecForString))
+    .property("jurisdiction", makeCodecOptional(codecForString))
+    .build("MerchantInfo");
+
+export const codecForTax = (): Codec<Tax> =>
+  makeCodecForObject<Tax>()
+    .property("name", codecForString)
+    .property("tax", codecForString)
+    .build("Tax");
+
+
+export const codecForI18n = (): Codec<{ [lang_tag: string]: string }> =>
+  makeCodecForMap(codecForString)
+
+export const codecForProduct = (): Codec<Product> =>
+  makeCodecForObject<Product>()
+    .property("product_id", makeCodecOptional(codecForString))
+    .property("description", codecForString)
+    .property("description_i18n", makeCodecOptional(codecForI18n()))
+    .property("quantity", makeCodecOptional(codecForNumber))
+    .property("unit", makeCodecOptional(codecForString))
+    .property("price", makeCodecOptional(codecForString))
+    .property("delivery_date", makeCodecOptional(codecForTimestamp))
+    .property("delivery_location", makeCodecOptional(codecForString))
+    .build("Tax");
+
 export const codecForContractTerms = (): Codec<ContractTerms> =>
   makeCodecForObject<ContractTerms>()
     .property("order_id", codecForString)
@@ -814,6 +894,7 @@ export const codecForContractTerms = (): 
Codec<ContractTerms> =>
     .property("auto_refund", makeCodecOptional(codecForDuration))
     .property("wire_method", codecForString)
     .property("summary", codecForString)
+    .property("summary_i18n", makeCodecOptional(codecForI18n()))
     .property("nonce", codecForString)
     .property("amount", codecForString)
     .property("auditors", makeCodecForList(codecForAuditorHandle()))
@@ -824,10 +905,10 @@ export const codecForContractTerms = (): 
Codec<ContractTerms> =>
     .property("locations", codecForAny)
     .property("max_fee", codecForString)
     .property("max_wire_fee", makeCodecOptional(codecForString))
-    .property("merchant", codecForAny)
+    .property("merchant", codecForMerchantInfo())
     .property("merchant_pub", codecForString)
     .property("exchanges", makeCodecForList(codecForExchangeHandle()))
-    .property("products", makeCodecOptional(makeCodecForList(codecForAny)))
+    .property("products", 
makeCodecOptional(makeCodecForList(codecForProduct())))
     .property("extra", codecForAny)
     .build("ContractTerms");
 
@@ -852,10 +933,7 @@ export const codecForMerchantRefundResponse = (): Codec<
   makeCodecForObject<MerchantRefundResponse>()
     .property("merchant_pub", codecForString)
     .property("h_contract_terms", codecForString)
-    .property(
-      "refunds",
-      makeCodecForList(codecForMerchantRefundPermission()),
-    )
+    .property("refunds", makeCodecForList(codecForMerchantRefundPermission()))
     .build("MerchantRefundResponse");
 
 export const codecForReserveSigSingleton = (): Codec<ReserveSigSingleton> =>
diff --git a/src/types/transactions.ts b/src/types/transactions.ts
index 263e08a4..b1d033c0 100644
--- a/src/types/transactions.ts
+++ b/src/types/transactions.ts
@@ -16,13 +16,16 @@
 
 /**
  * Type and schema definitions for the wallet's transaction list.
+ * 
+ * @author Florian Dold
+ * @author Torsten Grote
  */
 
 /**
  * Imports.
  */
 import { Timestamp } from "../util/time";
-import { AmountString } from "./talerTypes";
+import { AmountString, Product } from "./talerTypes";
 
 export interface TransactionsRequest {
   /**
@@ -44,6 +47,24 @@ export interface TransactionsResponse {
   transactions: Transaction[];
 }
 
+interface TransactionError {
+  /**
+   * TALER_EC_* unique error code.
+   * The action(s) offered and message displayed on the transaction item 
depend on this code.
+   */
+  ec: number;
+
+  /**
+   * English-only error hint, if available.
+   */
+  hint?: string;
+
+  /**
+   * Error details specific to "ec", if applicable/available
+   */
+  details?: any;
+}
+
 export interface TransactionCommon {
   // opaque unique ID for the transaction, used as a starting point for 
paginating queries
   // and for invoking actions on the transaction (e.g. deleting/hiding it from 
the history)
@@ -64,16 +85,17 @@ export interface TransactionCommon {
   amountRaw: AmountString;
 
   // Amount added or removed from the wallet's balance (including all fees and 
other costs)
-  amountEffective?: AmountString;
+  amountEffective: AmountString;
+
+  error?: TransactionError;
 }
 
-export type Transaction = (
-  TransactionWithdrawal |
-  TransactionPayment |
-  TransactionRefund |
-  TransactionTip |
-  TransactionRefresh
-)
+export type Transaction =
+  | TransactionWithdrawal
+  | TransactionPayment
+  | TransactionRefund
+  | TransactionTip
+  | TransactionRefresh;
 
 export const enum TransactionType {
   Withdrawal = "withdrawal",
@@ -93,79 +115,109 @@ interface TransactionWithdrawal extends TransactionCommon 
{
    */
   exchangeBaseUrl?: string;
 
-  // true if the bank has confirmed the withdrawal, false if not.
-  // An unconfirmed withdrawal usually requires user-input and should be 
highlighted in the UI.
-  // See also bankConfirmationUrl below.
+  /**
+   * true if the bank has confirmed the withdrawal, false if not.
+   * An unconfirmed withdrawal usually requires user-input and should be 
highlighted in the UI.
+   * See also bankConfirmationUrl below.
+   */
   confirmed: boolean;
 
-  // If the withdrawal is unconfirmed, this can include a URL for user 
initiated confirmation.
+  /**
+   * If the withdrawal is unconfirmed, this can include a URL for user
+   * initiated confirmation.
+   */
   bankConfirmationUrl?: string;
 
-  // Amount that has been subtracted from the reserve's balance for this 
withdrawal.
+  /**
+   * Amount that got subtracted from the reserve balance.
+   */
   amountRaw: AmountString;
 
   /**
    * Amount that actually was (or will be) added to the wallet's balance.
-   * Only present if an exchange has already been selected.
    */
-  amountEffective?: AmountString;
+  amountEffective: AmountString;
 }
 
 export const enum PaymentStatus {
-  // Explicitly aborted after timeout / failure
+  /**
+   * Explicitly aborted after timeout / failure
+   */
   Aborted = "aborted",
 
-  // Payment failed, wallet will auto-retry.
-  // User should be given the option to retry now / abort.
+  /**
+   * Payment failed, wallet will auto-retry.
+   * User should be given the option to retry now / abort.
+   */
   Failed = "failed",
 
-  // Paid successfully
+  /**
+   * Paid successfully
+   */
   Paid = "paid",
 
-  // Only offered, user must accept / decline
-  Offered = "offered",
-
-  // User accepted, payment is processing.
+  /**
+   * User accepted, payment is processing.
+   */
   Accepted = "accepted",
 }
 
 export interface TransactionPayment extends TransactionCommon {
   type: TransactionType.Payment;
 
-  // Additional information about the payment.
+  /**
+   * Additional information about the payment.
+   */
   info: PaymentShortInfo;
 
+  /**
+   * How far did the wallet get with processing the payment?
+   */
   status: PaymentStatus;
 
-  // Amount that must be paid for the contract
+  /**
+   * Amount that must be paid for the contract
+   */
   amountRaw: AmountString;
 
-  // Amount that was paid, including deposit, wire and refresh fees.
-  amountEffective?: AmountString;
+  /**
+   * Amount that was paid, including deposit, wire and refresh fees.
+   */
+  amountEffective: AmountString;
 }
 
-
 interface PaymentShortInfo {
-  // Order ID, uniquely identifies the order within a merchant instance
+  /**
+   * Order ID, uniquely identifies the order within a merchant instance
+   */
   orderId: string;
 
-  // More information about the merchant
+  /**
+   * More information about the merchant
+   */
   merchant: any;
 
-  // Summary of the order, given by the merchant
+  /**
+   * Summary of the order, given by the merchant
+   */
   summary: string;
 
-  // Map from IETF BCP 47 language tags to localized summaries
+  /**
+   * Map from IETF BCP 47 language tags to localized summaries
+   */
   summary_i18n?: { [lang_tag: string]: string };
 
-  // List of products that are part of the order
-  products: any[];
+  /**
+   * List of products that are part of the order
+   */
+  products: Product[] | undefined;
 
-  // URL of the fulfillment, given by the merchant
+  /**
+   * URL of the fulfillment, given by the merchant
+   */
   fulfillmentUrl: string;
 }
 
-
 interface TransactionRefund extends TransactionCommon {
   type: TransactionType.Refund;
 
@@ -221,4 +273,4 @@ interface TransactionRefresh extends TransactionCommon {
 
   // Amount that will be paid as fees for the refresh
   amountEffective: AmountString;
-}
\ No newline at end of file
+}

-- 
To stop receiving notification emails like this one, please contact
address@hidden.



reply via email to

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