parent
557dcec30d
commit
cd8f76db61
@ -1473,7 +1473,7 @@ async function updateUploadFees(
|
|||||||
x,
|
x,
|
||||||
).amount;
|
).amount;
|
||||||
};
|
};
|
||||||
const expirationTime = AbsoluteTime.fromTimestamp(expiration);
|
const expirationTime = AbsoluteTime.fromProtocolTimestamp(expiration);
|
||||||
const years = Duration.toIntegerYears(Duration.getRemaining(expirationTime));
|
const years = Duration.toIntegerYears(Duration.getRemaining(expirationTime));
|
||||||
logger.info(`computing fees for ${years} years`);
|
logger.info(`computing fees for ${years} years`);
|
||||||
// For now, we compute fees for *all* available providers.
|
// For now, we compute fees for *all* available providers.
|
||||||
|
@ -59,7 +59,7 @@ export async function runAgeRestrictionsPeerTest(t: GlobalTestState) {
|
|||||||
restrictAge: 13,
|
restrictAge: 13,
|
||||||
});
|
});
|
||||||
|
|
||||||
const purse_expiration = AbsoluteTime.toTimestamp(
|
const purse_expiration = AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(
|
AbsoluteTime.addDuration(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
Duration.fromSpec({ days: 2 }),
|
Duration.fromSpec({ days: 2 }),
|
||||||
|
@ -177,7 +177,7 @@ export async function runExchangeTimetravelTest(t: GlobalTestState) {
|
|||||||
return {
|
return {
|
||||||
denomPub: x.denom_pub,
|
denomPub: x.denom_pub,
|
||||||
expireDeposit: AbsoluteTime.stringify(
|
expireDeposit: AbsoluteTime.stringify(
|
||||||
AbsoluteTime.fromTimestamp(x.stamp_expire_deposit),
|
AbsoluteTime.fromProtocolTimestamp(x.stamp_expire_deposit),
|
||||||
),
|
),
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
@ -186,7 +186,7 @@ export async function runExchangeTimetravelTest(t: GlobalTestState) {
|
|||||||
return {
|
return {
|
||||||
denomPub: x.denom_pub,
|
denomPub: x.denom_pub,
|
||||||
expireDeposit: AbsoluteTime.stringify(
|
expireDeposit: AbsoluteTime.stringify(
|
||||||
AbsoluteTime.fromTimestamp(x.stamp_expire_deposit),
|
AbsoluteTime.fromProtocolTimestamp(x.stamp_expire_deposit),
|
||||||
),
|
),
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
@ -196,7 +196,7 @@ export async function runExchangeTimetravelTest(t: GlobalTestState) {
|
|||||||
|
|
||||||
console.log(
|
console.log(
|
||||||
"list issue date",
|
"list issue date",
|
||||||
AbsoluteTime.stringify(AbsoluteTime.fromTimestamp(keys1.list_issue_date)),
|
AbsoluteTime.stringify(AbsoluteTime.fromProtocolTimestamp(keys1.list_issue_date)),
|
||||||
);
|
);
|
||||||
console.log("num denoms", keys1.denoms.length);
|
console.log("num denoms", keys1.denoms.length);
|
||||||
console.log("denoms", JSON.stringify(denomPubs1, undefined, 2));
|
console.log("denoms", JSON.stringify(denomPubs1, undefined, 2));
|
||||||
@ -205,7 +205,7 @@ export async function runExchangeTimetravelTest(t: GlobalTestState) {
|
|||||||
|
|
||||||
console.log(
|
console.log(
|
||||||
"list issue date",
|
"list issue date",
|
||||||
AbsoluteTime.stringify(AbsoluteTime.fromTimestamp(keys2.list_issue_date)),
|
AbsoluteTime.stringify(AbsoluteTime.fromProtocolTimestamp(keys2.list_issue_date)),
|
||||||
);
|
);
|
||||||
console.log("num denoms", keys2.denoms.length);
|
console.log("num denoms", keys2.denoms.length);
|
||||||
console.log("denoms", JSON.stringify(denomPubs2, undefined, 2));
|
console.log("denoms", JSON.stringify(denomPubs2, undefined, 2));
|
||||||
@ -227,7 +227,7 @@ export async function runExchangeTimetravelTest(t: GlobalTestState) {
|
|||||||
);
|
);
|
||||||
console.log(
|
console.log(
|
||||||
`the new /keys response was issued ${AbsoluteTime.stringify(
|
`the new /keys response was issued ${AbsoluteTime.stringify(
|
||||||
AbsoluteTime.fromTimestamp(keys2.list_issue_date),
|
AbsoluteTime.fromProtocolTimestamp(keys2.list_issue_date),
|
||||||
)}`,
|
)}`,
|
||||||
);
|
);
|
||||||
console.log(
|
console.log(
|
||||||
|
@ -275,7 +275,7 @@ export async function runLibeufinBasicTest(t: GlobalTestState) {
|
|||||||
summary: "Buy me!",
|
summary: "Buy me!",
|
||||||
amount: "EUR:5",
|
amount: "EUR:5",
|
||||||
fulfillment_url: "taler://fulfillment-success/thx",
|
fulfillment_url: "taler://fulfillment-success/thx",
|
||||||
wire_transfer_deadline: AbsoluteTime.toTimestamp(AbsoluteTime.now()),
|
wire_transfer_deadline: AbsoluteTime.toProtocolTimestamp(AbsoluteTime.now()),
|
||||||
};
|
};
|
||||||
|
|
||||||
await makeTestPayment(t, { wallet, merchant, order });
|
await makeTestPayment(t, { wallet, merchant, order });
|
||||||
|
@ -75,7 +75,7 @@ export async function runPeerToPeerPullTest(t: GlobalTestState) {
|
|||||||
|
|
||||||
await withdrawalDoneCond;
|
await withdrawalDoneCond;
|
||||||
|
|
||||||
const purse_expiration = AbsoluteTime.toTimestamp(
|
const purse_expiration = AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(
|
AbsoluteTime.addDuration(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
Duration.fromSpec({ days: 2 }),
|
Duration.fromSpec({ days: 2 }),
|
||||||
|
@ -47,7 +47,7 @@ export async function runPeerToPeerPushTest(t: GlobalTestState) {
|
|||||||
|
|
||||||
await wallet1.runUntilDone();
|
await wallet1.runUntilDone();
|
||||||
|
|
||||||
const purse_expiration = AbsoluteTime.toTimestamp(
|
const purse_expiration = AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(
|
AbsoluteTime.addDuration(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
Duration.fromSpec({ days: 2 }),
|
Duration.fromSpec({ days: 2 }),
|
||||||
|
@ -50,7 +50,7 @@ export async function runRefundGoneTest(t: GlobalTestState) {
|
|||||||
summary: "Buy me!",
|
summary: "Buy me!",
|
||||||
amount: "TESTKUDOS:5",
|
amount: "TESTKUDOS:5",
|
||||||
fulfillment_url: "taler://fulfillment-success/thx",
|
fulfillment_url: "taler://fulfillment-success/thx",
|
||||||
pay_deadline: AbsoluteTime.toTimestamp(
|
pay_deadline: AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(
|
AbsoluteTime.addDuration(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
durationFromSpec({
|
durationFromSpec({
|
||||||
|
@ -63,7 +63,7 @@
|
|||||||
* Imports.
|
* Imports.
|
||||||
*/
|
*/
|
||||||
import { DenominationPubKey, UnblindedSignature } from "./taler-types.js";
|
import { DenominationPubKey, UnblindedSignature } from "./taler-types.js";
|
||||||
import { TalerProtocolDuration, TalerProtocolTimestamp } from "./time.js";
|
import { TalerProtocolDuration, TalerProtocolTimestamp, TalerPreciseTimestamp } from "./time.js";
|
||||||
|
|
||||||
export const BACKUP_TAG = "gnu-taler-wallet-backup-content" as const;
|
export const BACKUP_TAG = "gnu-taler-wallet-backup-content" as const;
|
||||||
/**
|
/**
|
||||||
@ -148,7 +148,7 @@ export interface WalletBackupContentV1 {
|
|||||||
* This timestamp should only be advanced if the content
|
* This timestamp should only be advanced if the content
|
||||||
* of the backup changes.
|
* of the backup changes.
|
||||||
*/
|
*/
|
||||||
timestamp: TalerProtocolTimestamp;
|
timestamp: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Per-exchange data sorted by exchange master public key.
|
* Per-exchange data sorted by exchange master public key.
|
||||||
@ -274,14 +274,14 @@ export type BackupWgInfo =
|
|||||||
*
|
*
|
||||||
* Set to undefined if that hasn't happened yet.
|
* Set to undefined if that hasn't happened yet.
|
||||||
*/
|
*/
|
||||||
timestamp_reserve_info_posted?: TalerProtocolTimestamp;
|
timestamp_reserve_info_posted?: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Time when the reserve was confirmed by the bank.
|
* Time when the reserve was confirmed by the bank.
|
||||||
*
|
*
|
||||||
* Set to undefined if not confirmed yet.
|
* Set to undefined if not confirmed yet.
|
||||||
*/
|
*/
|
||||||
timestamp_bank_confirmed?: TalerProtocolTimestamp;
|
timestamp_bank_confirmed?: TalerPreciseTimestamp;
|
||||||
}
|
}
|
||||||
| {
|
| {
|
||||||
type: BackupWgType.PeerPullCredit;
|
type: BackupWgType.PeerPullCredit;
|
||||||
@ -315,9 +315,9 @@ export interface BackupWithdrawalGroup {
|
|||||||
|
|
||||||
exchange_base_url: string;
|
exchange_base_url: string;
|
||||||
|
|
||||||
timestamp_created: TalerProtocolTimestamp;
|
timestamp_created: TalerPreciseTimestamp;
|
||||||
|
|
||||||
timestamp_finish?: TalerProtocolTimestamp;
|
timestamp_finish?: TalerPreciseTimestamp;
|
||||||
|
|
||||||
operation_status: BackupOperationStatus;
|
operation_status: BackupOperationStatus;
|
||||||
|
|
||||||
@ -473,9 +473,9 @@ export interface BackupRecoupGroup {
|
|||||||
/**
|
/**
|
||||||
* Timestamp when the recoup was started.
|
* Timestamp when the recoup was started.
|
||||||
*/
|
*/
|
||||||
timestamp_created: TalerProtocolTimestamp;
|
timestamp_created: TalerPreciseTimestamp;
|
||||||
|
|
||||||
timestamp_finish?: TalerProtocolTimestamp;
|
timestamp_finish?: TalerPreciseTimestamp;
|
||||||
finish_clock?: TalerProtocolTimestamp;
|
finish_clock?: TalerProtocolTimestamp;
|
||||||
// FIXME: Use some enum here!
|
// FIXME: Use some enum here!
|
||||||
finish_is_failure?: boolean;
|
finish_is_failure?: boolean;
|
||||||
@ -633,14 +633,14 @@ export interface BackupTip {
|
|||||||
* Has the user accepted the tip? Only after the tip has been accepted coins
|
* Has the user accepted the tip? Only after the tip has been accepted coins
|
||||||
* withdrawn from the tip may be used.
|
* withdrawn from the tip may be used.
|
||||||
*/
|
*/
|
||||||
timestamp_accepted: TalerProtocolTimestamp | undefined;
|
timestamp_accepted: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* When was the tip first scanned by the wallet?
|
* When was the tip first scanned by the wallet?
|
||||||
*/
|
*/
|
||||||
timestamp_created: TalerProtocolTimestamp;
|
timestamp_created: TalerPreciseTimestamp;
|
||||||
|
|
||||||
timestamp_finished?: TalerProtocolTimestamp;
|
timestamp_finished?: TalerPreciseTimestamp;
|
||||||
finish_is_failure?: boolean;
|
finish_is_failure?: boolean;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -765,9 +765,9 @@ export interface BackupRefreshGroup {
|
|||||||
*/
|
*/
|
||||||
old_coins: BackupRefreshOldCoin[];
|
old_coins: BackupRefreshOldCoin[];
|
||||||
|
|
||||||
timestamp_created: TalerProtocolTimestamp;
|
timestamp_created: TalerPreciseTimestamp;
|
||||||
|
|
||||||
timestamp_finish?: TalerProtocolTimestamp;
|
timestamp_finish?: TalerPreciseTimestamp;
|
||||||
finish_is_failure?: boolean;
|
finish_is_failure?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -940,7 +940,7 @@ export interface BackupPurchase {
|
|||||||
* Timestamp of the first time that sending a payment to the merchant
|
* Timestamp of the first time that sending a payment to the merchant
|
||||||
* for this purchase was successful.
|
* for this purchase was successful.
|
||||||
*/
|
*/
|
||||||
timestamp_first_successful_pay: TalerProtocolTimestamp | undefined;
|
timestamp_first_successful_pay: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Signature by the merchant confirming the payment.
|
* Signature by the merchant confirming the payment.
|
||||||
@ -952,13 +952,13 @@ export interface BackupPurchase {
|
|||||||
*/
|
*/
|
||||||
pos_confirmation: string | undefined;
|
pos_confirmation: string | undefined;
|
||||||
|
|
||||||
timestamp_proposed: TalerProtocolTimestamp;
|
timestamp_proposed: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* When was the purchase made?
|
* When was the purchase made?
|
||||||
* Refers to the time that the user accepted.
|
* Refers to the time that the user accepted.
|
||||||
*/
|
*/
|
||||||
timestamp_accepted: TalerProtocolTimestamp | undefined;
|
timestamp_accepted: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Pending refunds for the purchase. A refund is pending
|
* Pending refunds for the purchase. A refund is pending
|
||||||
@ -1186,7 +1186,7 @@ export interface BackupExchange {
|
|||||||
*
|
*
|
||||||
* Used to facilitate automatic merging.
|
* Used to facilitate automatic merging.
|
||||||
*/
|
*/
|
||||||
update_clock: TalerProtocolTimestamp;
|
update_clock: TalerPreciseTimestamp;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -1258,7 +1258,7 @@ export interface BackupExchangeDetails {
|
|||||||
/**
|
/**
|
||||||
* Timestamp when the ToS has been accepted.
|
* Timestamp when the ToS has been accepted.
|
||||||
*/
|
*/
|
||||||
tos_accepted_timestamp: TalerProtocolTimestamp | undefined;
|
tos_accepted_timestamp: TalerPreciseTimestamp | undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum BackupProposalStatus {
|
export enum BackupProposalStatus {
|
||||||
|
@ -25,8 +25,9 @@ import { Codec, renderContext, Context } from "./codec.js";
|
|||||||
|
|
||||||
declare const flavor_AbsoluteTime: unique symbol;
|
declare const flavor_AbsoluteTime: unique symbol;
|
||||||
declare const flavor_TalerProtocolTimestamp: unique symbol;
|
declare const flavor_TalerProtocolTimestamp: unique symbol;
|
||||||
declare const flavor_TalerWalletDbTimestamp: unique symbol;
|
declare const flavor_TalerPreciseTimestamp: unique symbol;
|
||||||
|
|
||||||
|
// FIXME: Make this opaque!
|
||||||
export interface AbsoluteTime {
|
export interface AbsoluteTime {
|
||||||
/**
|
/**
|
||||||
* Timestamp in milliseconds.
|
* Timestamp in milliseconds.
|
||||||
@ -45,7 +46,7 @@ export interface TalerProtocolTimestamp {
|
|||||||
readonly _flavor?: typeof flavor_TalerProtocolTimestamp;
|
readonly _flavor?: typeof flavor_TalerProtocolTimestamp;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface TalerWalletDbTimestamp {
|
export interface TalerPreciseTimestamp {
|
||||||
/**
|
/**
|
||||||
* Seconds (as integer) since epoch.
|
* Seconds (as integer) since epoch.
|
||||||
*/
|
*/
|
||||||
@ -56,12 +57,32 @@ export interface TalerWalletDbTimestamp {
|
|||||||
*/
|
*/
|
||||||
readonly off_us?: number;
|
readonly off_us?: number;
|
||||||
|
|
||||||
readonly _flavor?: typeof flavor_TalerWalletDbTimestamp;
|
readonly _flavor?: typeof flavor_TalerPreciseTimestamp;
|
||||||
|
}
|
||||||
|
|
||||||
|
export namespace TalerPreciseTimestamp {
|
||||||
|
export function now(): TalerPreciseTimestamp {
|
||||||
|
const absNow = AbsoluteTime.now();
|
||||||
|
return AbsoluteTime.toPreciseTimestamp(absNow);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function round(t: TalerPreciseTimestamp): TalerProtocolTimestamp {
|
||||||
|
return {
|
||||||
|
t_s: t.t_s,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export function fromSeconds(s: number): TalerPreciseTimestamp {
|
||||||
|
return {
|
||||||
|
t_s: Math.floor(s),
|
||||||
|
off_us: (s - Math.floor(s)) / 1000 / 1000,
|
||||||
|
};
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export namespace TalerProtocolTimestamp {
|
export namespace TalerProtocolTimestamp {
|
||||||
export function now(): TalerProtocolTimestamp {
|
export function now(): TalerProtocolTimestamp {
|
||||||
return AbsoluteTime.toTimestamp(AbsoluteTime.now());
|
return AbsoluteTime.toProtocolTimestamp(AbsoluteTime.now());
|
||||||
}
|
}
|
||||||
|
|
||||||
export function zero(): TalerProtocolTimestamp {
|
export function zero(): TalerProtocolTimestamp {
|
||||||
@ -81,6 +102,7 @@ export namespace TalerProtocolTimestamp {
|
|||||||
t_s: s,
|
t_s: s,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export function min(
|
export function min(
|
||||||
t1: TalerProtocolTimestamp,
|
t1: TalerProtocolTimestamp,
|
||||||
t2: TalerProtocolTimestamp,
|
t2: TalerProtocolTimestamp,
|
||||||
@ -309,7 +331,7 @@ export namespace AbsoluteTime {
|
|||||||
return cmp(t, now()) <= 0;
|
return cmp(t, now()) <= 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function fromTimestamp(t: TalerProtocolTimestamp): AbsoluteTime {
|
export function fromProtocolTimestamp(t: TalerProtocolTimestamp): AbsoluteTime {
|
||||||
if (t.t_s === "never") {
|
if (t.t_s === "never") {
|
||||||
return { t_ms: "never" };
|
return { t_ms: "never" };
|
||||||
}
|
}
|
||||||
@ -318,7 +340,31 @@ export namespace AbsoluteTime {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export function toTimestamp(at: AbsoluteTime): TalerProtocolTimestamp {
|
export function fromPreciseTimestamp(t: TalerPreciseTimestamp): AbsoluteTime {
|
||||||
|
if (t.t_s === "never") {
|
||||||
|
return { t_ms: "never" };
|
||||||
|
}
|
||||||
|
const offsetUs = t.off_us ?? 0;
|
||||||
|
return {
|
||||||
|
t_ms: t.t_s * 1000 + offsetUs / 1000,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export function toPreciseTimestamp(at: AbsoluteTime): TalerPreciseTimestamp {
|
||||||
|
if (at.t_ms == "never") {
|
||||||
|
return {
|
||||||
|
t_s: "never",
|
||||||
|
};
|
||||||
|
}
|
||||||
|
const t_s = Math.floor(at.t_ms / 1000);
|
||||||
|
const off_us = Math.floor(1000 * (at.t_ms - t_s * 1000));
|
||||||
|
return {
|
||||||
|
t_s,
|
||||||
|
off_us,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export function toProtocolTimestamp(at: AbsoluteTime): TalerProtocolTimestamp {
|
||||||
if (at.t_ms === "never") {
|
if (at.t_ms === "never") {
|
||||||
return { t_s: "never" };
|
return { t_s: "never" };
|
||||||
}
|
}
|
||||||
|
@ -24,7 +24,7 @@
|
|||||||
/**
|
/**
|
||||||
* Imports.
|
* Imports.
|
||||||
*/
|
*/
|
||||||
import { TalerProtocolTimestamp } from "./time.js";
|
import { TalerPreciseTimestamp, TalerProtocolTimestamp } from "./time.js";
|
||||||
import {
|
import {
|
||||||
AmountString,
|
AmountString,
|
||||||
Product,
|
Product,
|
||||||
@ -141,7 +141,7 @@ export interface TransactionCommon {
|
|||||||
type: TransactionType;
|
type: TransactionType;
|
||||||
|
|
||||||
// main timestamp of the transaction
|
// main timestamp of the transaction
|
||||||
timestamp: TalerProtocolTimestamp;
|
timestamp: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Transaction state, as per DD37.
|
* Transaction state, as per DD37.
|
||||||
|
@ -1112,7 +1112,7 @@ peerCli
|
|||||||
partialContractTerms: {
|
partialContractTerms: {
|
||||||
amount: args.initiatePayPull.amount,
|
amount: args.initiatePayPull.amount,
|
||||||
summary: args.initiatePayPull.summary ?? "Invoice",
|
summary: args.initiatePayPull.summary ?? "Invoice",
|
||||||
purse_expiration: AbsoluteTime.toTimestamp(purseExpiration),
|
purse_expiration: AbsoluteTime.toProtocolTimestamp(purseExpiration),
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
@ -1168,7 +1168,7 @@ peerCli
|
|||||||
partialContractTerms: {
|
partialContractTerms: {
|
||||||
amount: args.payPush.amount,
|
amount: args.payPush.amount,
|
||||||
summary: args.payPush.summary ?? "Payment",
|
summary: args.payPush.summary ?? "Payment",
|
||||||
purse_expiration: AbsoluteTime.toTimestamp(purseExpiration),
|
purse_expiration: AbsoluteTime.toProtocolTimestamp(purseExpiration),
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
@ -14,7 +14,7 @@
|
|||||||
GNU Taler; see the file COPYING. If not, see <http://www.gnu.org/licenses/>
|
GNU Taler; see the file COPYING. If not, see <http://www.gnu.org/licenses/>
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { AbsoluteTime } from "@gnu-taler/taler-util";
|
import { AbsoluteTime, TalerErrorCode } from "@gnu-taler/taler-util";
|
||||||
import test from "ava";
|
import test from "ava";
|
||||||
import { CryptoDispatcher, CryptoWorkerFactory } from "./crypto-dispatcher.js";
|
import { CryptoDispatcher, CryptoWorkerFactory } from "./crypto-dispatcher.js";
|
||||||
import {
|
import {
|
||||||
@ -72,7 +72,7 @@ export class MyCryptoWorker implements CryptoWorker {
|
|||||||
id: msg.id,
|
id: msg.id,
|
||||||
type: "error",
|
type: "error",
|
||||||
error: {
|
error: {
|
||||||
code: 42,
|
code: TalerErrorCode.ANASTASIS_EMAIL_INVALID,
|
||||||
when: AbsoluteTime.now(),
|
when: AbsoluteTime.now(),
|
||||||
hint: "bla",
|
hint: "bla",
|
||||||
},
|
},
|
||||||
|
@ -57,6 +57,7 @@ import {
|
|||||||
AttentionInfo,
|
AttentionInfo,
|
||||||
Logger,
|
Logger,
|
||||||
CoinPublicKeyString,
|
CoinPublicKeyString,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
} from "@gnu-taler/taler-util";
|
} from "@gnu-taler/taler-util";
|
||||||
import {
|
import {
|
||||||
DbAccess,
|
DbAccess,
|
||||||
@ -236,14 +237,14 @@ export interface ReserveBankInfo {
|
|||||||
*
|
*
|
||||||
* Set to undefined if that hasn't happened yet.
|
* Set to undefined if that hasn't happened yet.
|
||||||
*/
|
*/
|
||||||
timestampReserveInfoPosted: TalerProtocolTimestamp | undefined;
|
timestampReserveInfoPosted: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Time when the reserve was confirmed by the bank.
|
* Time when the reserve was confirmed by the bank.
|
||||||
*
|
*
|
||||||
* Set to undefined if not confirmed yet.
|
* Set to undefined if not confirmed yet.
|
||||||
*/
|
*/
|
||||||
timestampBankConfirmed: TalerProtocolTimestamp | undefined;
|
timestampBankConfirmed: TalerPreciseTimestamp | undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -516,7 +517,7 @@ export interface ExchangeDetailsRecord {
|
|||||||
tosAccepted:
|
tosAccepted:
|
||||||
| {
|
| {
|
||||||
etag: string;
|
etag: string;
|
||||||
timestamp: TalerProtocolTimestamp;
|
timestamp: TalerPreciseTimestamp;
|
||||||
}
|
}
|
||||||
| undefined;
|
| undefined;
|
||||||
|
|
||||||
@ -556,7 +557,7 @@ export interface ExchangeDetailsPointer {
|
|||||||
* Timestamp when the (masterPublicKey, currency) pointer
|
* Timestamp when the (masterPublicKey, currency) pointer
|
||||||
* has been updated.
|
* has been updated.
|
||||||
*/
|
*/
|
||||||
updateClock: TalerProtocolTimestamp;
|
updateClock: TalerPreciseTimestamp;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -573,7 +574,7 @@ export interface ExchangeRecord {
|
|||||||
*
|
*
|
||||||
* Used mostly in the UI to suggest exchanges.
|
* Used mostly in the UI to suggest exchanges.
|
||||||
*/
|
*/
|
||||||
lastWithdrawal?: TalerProtocolTimestamp;
|
lastWithdrawal?: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Pointer to the current exchange details.
|
* Pointer to the current exchange details.
|
||||||
@ -595,14 +596,14 @@ export interface ExchangeRecord {
|
|||||||
/**
|
/**
|
||||||
* Last time when the exchange was updated (both /keys and /wire).
|
* Last time when the exchange was updated (both /keys and /wire).
|
||||||
*/
|
*/
|
||||||
lastUpdate: TalerProtocolTimestamp | undefined;
|
lastUpdate: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Next scheduled update for the exchange.
|
* Next scheduled update for the exchange.
|
||||||
*
|
*
|
||||||
* (This field must always be present, so we can index on the timestamp.)
|
* (This field must always be present, so we can index on the timestamp.)
|
||||||
*/
|
*/
|
||||||
nextUpdate: TalerProtocolTimestamp;
|
nextUpdate: TalerPreciseTimestamp;
|
||||||
|
|
||||||
lastKeysEtag: string | undefined;
|
lastKeysEtag: string | undefined;
|
||||||
|
|
||||||
@ -614,7 +615,7 @@ export interface ExchangeRecord {
|
|||||||
* Updated whenever the exchange's denominations are updated or when
|
* Updated whenever the exchange's denominations are updated or when
|
||||||
* the refresh check has been done.
|
* the refresh check has been done.
|
||||||
*/
|
*/
|
||||||
nextRefreshCheck: TalerProtocolTimestamp;
|
nextRefreshCheck: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Public key of the reserve that we're currently using for
|
* Public key of the reserve that we're currently using for
|
||||||
@ -803,7 +804,7 @@ export interface TipRecord {
|
|||||||
* Has the user accepted the tip? Only after the tip has been accepted coins
|
* Has the user accepted the tip? Only after the tip has been accepted coins
|
||||||
* withdrawn from the tip may be used.
|
* withdrawn from the tip may be used.
|
||||||
*/
|
*/
|
||||||
acceptedTimestamp: TalerProtocolTimestamp | undefined;
|
acceptedTimestamp: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The tipped amount.
|
* The tipped amount.
|
||||||
@ -856,7 +857,7 @@ export interface TipRecord {
|
|||||||
*/
|
*/
|
||||||
merchantTipId: string;
|
merchantTipId: string;
|
||||||
|
|
||||||
createdTimestamp: TalerProtocolTimestamp;
|
createdTimestamp: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The url to be redirected after the tip is accepted.
|
* The url to be redirected after the tip is accepted.
|
||||||
@ -866,7 +867,7 @@ export interface TipRecord {
|
|||||||
* Timestamp for when the wallet finished picking up the tip
|
* Timestamp for when the wallet finished picking up the tip
|
||||||
* from the merchant.
|
* from the merchant.
|
||||||
*/
|
*/
|
||||||
pickedUpTimestamp: TalerProtocolTimestamp | undefined;
|
pickedUpTimestamp: TalerPreciseTimestamp | undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum RefreshCoinStatus {
|
export enum RefreshCoinStatus {
|
||||||
@ -974,12 +975,12 @@ export interface RefreshGroupRecord {
|
|||||||
*/
|
*/
|
||||||
statusPerCoin: RefreshCoinStatus[];
|
statusPerCoin: RefreshCoinStatus[];
|
||||||
|
|
||||||
timestampCreated: TalerProtocolTimestamp;
|
timestampCreated: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Timestamp when the refresh session finished.
|
* Timestamp when the refresh session finished.
|
||||||
*/
|
*/
|
||||||
timestampFinished: TalerProtocolTimestamp | undefined;
|
timestampFinished: TalerPreciseTimestamp | undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -1233,7 +1234,7 @@ export interface PurchaseRecord {
|
|||||||
* Timestamp of the first time that sending a payment to the merchant
|
* Timestamp of the first time that sending a payment to the merchant
|
||||||
* for this purchase was successful.
|
* for this purchase was successful.
|
||||||
*/
|
*/
|
||||||
timestampFirstSuccessfulPay: TalerProtocolTimestamp | undefined;
|
timestampFirstSuccessfulPay: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
merchantPaySig: string | undefined;
|
merchantPaySig: string | undefined;
|
||||||
|
|
||||||
@ -1242,13 +1243,13 @@ export interface PurchaseRecord {
|
|||||||
/**
|
/**
|
||||||
* When was the purchase record created?
|
* When was the purchase record created?
|
||||||
*/
|
*/
|
||||||
timestamp: TalerProtocolTimestamp;
|
timestamp: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* When was the purchase made?
|
* When was the purchase made?
|
||||||
* Refers to the time that the user accepted.
|
* Refers to the time that the user accepted.
|
||||||
*/
|
*/
|
||||||
timestampAccept: TalerProtocolTimestamp | undefined;
|
timestampAccept: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Pending refunds for the purchase. A refund is pending
|
* Pending refunds for the purchase. A refund is pending
|
||||||
@ -1262,7 +1263,7 @@ export interface PurchaseRecord {
|
|||||||
* When was the last refund made?
|
* When was the last refund made?
|
||||||
* Set to 0 if no refund was made on the purchase.
|
* Set to 0 if no refund was made on the purchase.
|
||||||
*/
|
*/
|
||||||
timestampLastRefundStatus: TalerProtocolTimestamp | undefined;
|
timestampLastRefundStatus: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Last session signature that we submitted to /pay (if any).
|
* Last session signature that we submitted to /pay (if any).
|
||||||
@ -1312,12 +1313,12 @@ export interface WalletBackupConfState {
|
|||||||
/**
|
/**
|
||||||
* Timestamp stored in the last backup.
|
* Timestamp stored in the last backup.
|
||||||
*/
|
*/
|
||||||
lastBackupTimestamp?: TalerProtocolTimestamp;
|
lastBackupTimestamp?: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Last time we tried to do a backup.
|
* Last time we tried to do a backup.
|
||||||
*/
|
*/
|
||||||
lastBackupCheckTimestamp?: TalerProtocolTimestamp;
|
lastBackupCheckTimestamp?: TalerPreciseTimestamp;
|
||||||
lastBackupNonce?: string;
|
lastBackupNonce?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1421,12 +1422,12 @@ export interface WithdrawalGroupRecord {
|
|||||||
* When was the withdrawal operation started started?
|
* When was the withdrawal operation started started?
|
||||||
* Timestamp in milliseconds.
|
* Timestamp in milliseconds.
|
||||||
*/
|
*/
|
||||||
timestampStart: TalerProtocolTimestamp;
|
timestampStart: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* When was the withdrawal operation completed?
|
* When was the withdrawal operation completed?
|
||||||
*/
|
*/
|
||||||
timestampFinish?: TalerProtocolTimestamp;
|
timestampFinish?: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Current status of the reserve.
|
* Current status of the reserve.
|
||||||
@ -1517,9 +1518,9 @@ export interface RecoupGroupRecord {
|
|||||||
|
|
||||||
exchangeBaseUrl: string;
|
exchangeBaseUrl: string;
|
||||||
|
|
||||||
timestampStarted: TalerProtocolTimestamp;
|
timestampStarted: TalerPreciseTimestamp;
|
||||||
|
|
||||||
timestampFinished: TalerProtocolTimestamp | undefined;
|
timestampFinished: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Public keys that identify the coins being recouped
|
* Public keys that identify the coins being recouped
|
||||||
@ -1553,7 +1554,7 @@ export type BackupProviderState =
|
|||||||
}
|
}
|
||||||
| {
|
| {
|
||||||
tag: BackupProviderStateTag.Ready;
|
tag: BackupProviderStateTag.Ready;
|
||||||
nextBackupTimestamp: TalerProtocolTimestamp;
|
nextBackupTimestamp: TalerPreciseTimestamp;
|
||||||
}
|
}
|
||||||
| {
|
| {
|
||||||
tag: BackupProviderStateTag.Retrying;
|
tag: BackupProviderStateTag.Retrying;
|
||||||
@ -1598,7 +1599,7 @@ export interface BackupProviderRecord {
|
|||||||
* Does NOT correspond to the timestamp of the backup,
|
* Does NOT correspond to the timestamp of the backup,
|
||||||
* which only changes when the backup content changes.
|
* which only changes when the backup content changes.
|
||||||
*/
|
*/
|
||||||
lastBackupCycleTimestamp?: TalerProtocolTimestamp;
|
lastBackupCycleTimestamp?: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Proposal that we're currently trying to pay for.
|
* Proposal that we're currently trying to pay for.
|
||||||
@ -1693,9 +1694,9 @@ export interface DepositGroupRecord {
|
|||||||
*/
|
*/
|
||||||
effectiveDepositAmount: AmountString;
|
effectiveDepositAmount: AmountString;
|
||||||
|
|
||||||
timestampCreated: TalerProtocolTimestamp;
|
timestampCreated: TalerPreciseTimestamp;
|
||||||
|
|
||||||
timestampFinished: TalerProtocolTimestamp | undefined;
|
timestampFinished: TalerPreciseTimestamp | undefined;
|
||||||
|
|
||||||
operationStatus: DepositOperationStatus;
|
operationStatus: DepositOperationStatus;
|
||||||
|
|
||||||
@ -1728,7 +1729,7 @@ export interface GhostDepositGroupRecord {
|
|||||||
* When multiple deposits for the same contract terms hash
|
* When multiple deposits for the same contract terms hash
|
||||||
* have a different timestamp, we choose the earliest one.
|
* have a different timestamp, we choose the earliest one.
|
||||||
*/
|
*/
|
||||||
timestamp: TalerProtocolTimestamp;
|
timestamp: TalerPreciseTimestamp;
|
||||||
|
|
||||||
contractTermsHash: string;
|
contractTermsHash: string;
|
||||||
|
|
||||||
@ -1821,7 +1822,7 @@ export interface PeerPushPaymentInitiationRecord {
|
|||||||
|
|
||||||
purseExpiration: TalerProtocolTimestamp;
|
purseExpiration: TalerProtocolTimestamp;
|
||||||
|
|
||||||
timestampCreated: TalerProtocolTimestamp;
|
timestampCreated: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Status of the peer push payment initiation.
|
* Status of the peer push payment initiation.
|
||||||
@ -1882,7 +1883,7 @@ export interface PeerPullPaymentInitiationRecord {
|
|||||||
|
|
||||||
contractTerms: PeerContractTerms;
|
contractTerms: PeerContractTerms;
|
||||||
|
|
||||||
mergeTimestamp: TalerProtocolTimestamp;
|
mergeTimestamp: TalerPreciseTimestamp;
|
||||||
|
|
||||||
mergeReserveRowId: number;
|
mergeReserveRowId: number;
|
||||||
|
|
||||||
@ -1924,7 +1925,7 @@ export interface PeerPushPaymentIncomingRecord {
|
|||||||
|
|
||||||
contractPriv: string;
|
contractPriv: string;
|
||||||
|
|
||||||
timestamp: TalerProtocolTimestamp;
|
timestamp: TalerPreciseTimestamp;
|
||||||
|
|
||||||
estimatedAmountEffective: AmountString;
|
estimatedAmountEffective: AmountString;
|
||||||
|
|
||||||
@ -1984,7 +1985,7 @@ export interface PeerPullPaymentIncomingRecord {
|
|||||||
|
|
||||||
contractTerms: PeerContractTerms;
|
contractTerms: PeerContractTerms;
|
||||||
|
|
||||||
timestampCreated: TalerProtocolTimestamp;
|
timestampCreated: TalerPreciseTimestamp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Contract priv that we got from the other party.
|
* Contract priv that we got from the other party.
|
||||||
@ -2081,7 +2082,7 @@ export interface UserAttentionRecord {
|
|||||||
/**
|
/**
|
||||||
* When the user mark this notification as read.
|
* When the user mark this notification as read.
|
||||||
*/
|
*/
|
||||||
read: TalerProtocolTimestamp | undefined;
|
read: TalerPreciseTimestamp | undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface DbExchangeHandle {
|
export interface DbExchangeHandle {
|
||||||
@ -2125,7 +2126,7 @@ export interface RefundGroupRecord {
|
|||||||
/**
|
/**
|
||||||
* Timestamp when the refund group was created.
|
* Timestamp when the refund group was created.
|
||||||
*/
|
*/
|
||||||
timestampCreated: TalerProtocolTimestamp;
|
timestampCreated: TalerPreciseTimestamp;
|
||||||
|
|
||||||
proposalId: string;
|
proposalId: string;
|
||||||
|
|
||||||
@ -2180,7 +2181,7 @@ export interface RefundItemRecord {
|
|||||||
/**
|
/**
|
||||||
* Time when the wallet became aware of the refund.
|
* Time when the wallet became aware of the refund.
|
||||||
*/
|
*/
|
||||||
obtainedTime: TalerProtocolTimestamp;
|
obtainedTime: TalerPreciseTimestamp;
|
||||||
|
|
||||||
refundAmount: AmountString;
|
refundAmount: AmountString;
|
||||||
|
|
||||||
|
@ -256,7 +256,7 @@ export async function depositCoin(args: {
|
|||||||
const depositPayto =
|
const depositPayto =
|
||||||
args.depositPayto ?? "payto://x-taler-bank/localhost/foo";
|
args.depositPayto ?? "payto://x-taler-bank/localhost/foo";
|
||||||
const wireSalt = args.wireSalt ?? encodeCrock(getRandomBytes(16));
|
const wireSalt = args.wireSalt ?? encodeCrock(getRandomBytes(16));
|
||||||
const timestampNow = AbsoluteTime.toTimestamp(AbsoluteTime.now());
|
const timestampNow = AbsoluteTime.toProtocolTimestamp(AbsoluteTime.now());
|
||||||
const contractTermsHash =
|
const contractTermsHash =
|
||||||
args.contractTermsHash ?? encodeCrock(getRandomBytes(64));
|
args.contractTermsHash ?? encodeCrock(getRandomBytes(64));
|
||||||
const depositTimestamp = timestampNow;
|
const depositTimestamp = timestampNow;
|
||||||
|
@ -22,6 +22,7 @@ import {
|
|||||||
AttentionInfo,
|
AttentionInfo,
|
||||||
Logger,
|
Logger,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
UserAttentionByIdRequest,
|
UserAttentionByIdRequest,
|
||||||
UserAttentionPriority,
|
UserAttentionPriority,
|
||||||
UserAttentionsCountResponse,
|
UserAttentionsCountResponse,
|
||||||
@ -95,7 +96,7 @@ export async function markAttentionRequestAsRead(
|
|||||||
if (!ua) throw Error("attention request not found");
|
if (!ua) throw Error("attention request not found");
|
||||||
tx.userAttention.put({
|
tx.userAttention.put({
|
||||||
...ua,
|
...ua,
|
||||||
read: TalerProtocolTimestamp.now(),
|
read: TalerPreciseTimestamp.now(),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -62,6 +62,7 @@ import {
|
|||||||
Logger,
|
Logger,
|
||||||
stringToBytes,
|
stringToBytes,
|
||||||
WalletBackupContentV1,
|
WalletBackupContentV1,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
} from "@gnu-taler/taler-util";
|
} from "@gnu-taler/taler-util";
|
||||||
import {
|
import {
|
||||||
CoinSourceType,
|
CoinSourceType,
|
||||||
@ -521,7 +522,7 @@ export async function exportBackup(
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
const ts = AbsoluteTime.toTimestamp(AbsoluteTime.now());
|
const ts = TalerPreciseTimestamp.now();
|
||||||
|
|
||||||
if (!bs.lastBackupTimestamp) {
|
if (!bs.lastBackupTimestamp) {
|
||||||
bs.lastBackupTimestamp = ts;
|
bs.lastBackupTimestamp = ts;
|
||||||
@ -565,7 +566,7 @@ export async function exportBackup(
|
|||||||
bs.lastBackupNonce = encodeCrock(getRandomBytes(32));
|
bs.lastBackupNonce = encodeCrock(getRandomBytes(32));
|
||||||
logger.trace(
|
logger.trace(
|
||||||
`setting timestamp to ${AbsoluteTime.toIsoString(
|
`setting timestamp to ${AbsoluteTime.toIsoString(
|
||||||
AbsoluteTime.fromTimestamp(ts),
|
AbsoluteTime.fromPreciseTimestamp(ts),
|
||||||
)} and nonce to ${bs.lastBackupNonce}`,
|
)} and nonce to ${bs.lastBackupNonce}`,
|
||||||
);
|
);
|
||||||
await tx.config.put({
|
await tx.config.put({
|
||||||
|
@ -35,6 +35,7 @@ import {
|
|||||||
PayCoinSelection,
|
PayCoinSelection,
|
||||||
RefreshReason,
|
RefreshReason,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
WalletBackupContentV1,
|
WalletBackupContentV1,
|
||||||
WireInfo,
|
WireInfo,
|
||||||
} from "@gnu-taler/taler-util";
|
} from "@gnu-taler/taler-util";
|
||||||
@ -349,8 +350,8 @@ export async function importBackup(
|
|||||||
},
|
},
|
||||||
permanent: true,
|
permanent: true,
|
||||||
lastUpdate: undefined,
|
lastUpdate: undefined,
|
||||||
nextUpdate: TalerProtocolTimestamp.now(),
|
nextUpdate: TalerPreciseTimestamp.now(),
|
||||||
nextRefreshCheck: TalerProtocolTimestamp.now(),
|
nextRefreshCheck: TalerPreciseTimestamp.now(),
|
||||||
lastKeysEtag: undefined,
|
lastKeysEtag: undefined,
|
||||||
lastWireEtag: undefined,
|
lastWireEtag: undefined,
|
||||||
});
|
});
|
||||||
|
@ -71,6 +71,7 @@ import {
|
|||||||
TalerErrorCode,
|
TalerErrorCode,
|
||||||
TalerErrorDetail,
|
TalerErrorDetail,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
URL,
|
URL,
|
||||||
WalletBackupContentV1,
|
WalletBackupContentV1,
|
||||||
} from "@gnu-taler/taler-util";
|
} from "@gnu-taler/taler-util";
|
||||||
@ -246,9 +247,9 @@ interface BackupForProviderArgs {
|
|||||||
backupProviderBaseUrl: string;
|
backupProviderBaseUrl: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
function getNextBackupTimestamp(): TalerProtocolTimestamp {
|
function getNextBackupTimestamp(): TalerPreciseTimestamp {
|
||||||
// FIXME: Randomize!
|
// FIXME: Randomize!
|
||||||
return AbsoluteTime.toTimestamp(
|
return AbsoluteTime.toPreciseTimestamp(
|
||||||
AbsoluteTime.addDuration(
|
AbsoluteTime.addDuration(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
durationFromSpec({ minutes: 5 }),
|
durationFromSpec({ minutes: 5 }),
|
||||||
@ -329,7 +330,7 @@ async function runBackupCycleForProvider(
|
|||||||
if (!prov) {
|
if (!prov) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
prov.lastBackupCycleTimestamp = TalerProtocolTimestamp.now();
|
prov.lastBackupCycleTimestamp = TalerPreciseTimestamp.now();
|
||||||
prov.state = {
|
prov.state = {
|
||||||
tag: BackupProviderStateTag.Ready,
|
tag: BackupProviderStateTag.Ready,
|
||||||
nextBackupTimestamp: getNextBackupTimestamp(),
|
nextBackupTimestamp: getNextBackupTimestamp(),
|
||||||
@ -442,7 +443,7 @@ async function runBackupCycleForProvider(
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
prov.lastBackupHash = encodeCrock(currentBackupHash);
|
prov.lastBackupHash = encodeCrock(currentBackupHash);
|
||||||
prov.lastBackupCycleTimestamp = TalerProtocolTimestamp.now();
|
prov.lastBackupCycleTimestamp = TalerPreciseTimestamp.now();
|
||||||
prov.state = {
|
prov.state = {
|
||||||
tag: BackupProviderStateTag.Ready,
|
tag: BackupProviderStateTag.Ready,
|
||||||
nextBackupTimestamp: getNextBackupTimestamp(),
|
nextBackupTimestamp: getNextBackupTimestamp(),
|
||||||
@ -676,7 +677,7 @@ export async function addBackupProvider(
|
|||||||
if (req.activate) {
|
if (req.activate) {
|
||||||
oldProv.state = {
|
oldProv.state = {
|
||||||
tag: BackupProviderStateTag.Ready,
|
tag: BackupProviderStateTag.Ready,
|
||||||
nextBackupTimestamp: TalerProtocolTimestamp.now(),
|
nextBackupTimestamp: TalerPreciseTimestamp.now(),
|
||||||
};
|
};
|
||||||
logger.info("setting existing backup provider to active");
|
logger.info("setting existing backup provider to active");
|
||||||
await tx.backupProviders.put(oldProv);
|
await tx.backupProviders.put(oldProv);
|
||||||
@ -698,7 +699,7 @@ export async function addBackupProvider(
|
|||||||
if (req.activate) {
|
if (req.activate) {
|
||||||
state = {
|
state = {
|
||||||
tag: BackupProviderStateTag.Ready,
|
tag: BackupProviderStateTag.Ready,
|
||||||
nextBackupTimestamp: TalerProtocolTimestamp.now(),
|
nextBackupTimestamp: TalerPreciseTimestamp.now(),
|
||||||
};
|
};
|
||||||
} else {
|
} else {
|
||||||
state = {
|
state = {
|
||||||
@ -773,8 +774,8 @@ export interface ProviderInfo {
|
|||||||
* Last communication issue with the provider.
|
* Last communication issue with the provider.
|
||||||
*/
|
*/
|
||||||
lastError?: TalerErrorDetail;
|
lastError?: TalerErrorDetail;
|
||||||
lastSuccessfulBackupTimestamp?: TalerProtocolTimestamp;
|
lastSuccessfulBackupTimestamp?: TalerPreciseTimestamp;
|
||||||
lastAttemptedBackupTimestamp?: TalerProtocolTimestamp;
|
lastAttemptedBackupTimestamp?: TalerPreciseTimestamp;
|
||||||
paymentProposalIds: string[];
|
paymentProposalIds: string[];
|
||||||
backupProblem?: BackupProblem;
|
backupProblem?: BackupProblem;
|
||||||
paymentStatus: ProviderPaymentStatus;
|
paymentStatus: ProviderPaymentStatus;
|
||||||
@ -894,7 +895,7 @@ async function getProviderPaymentInfo(
|
|||||||
return {
|
return {
|
||||||
type: ProviderPaymentType.Paid,
|
type: ProviderPaymentType.Paid,
|
||||||
paidUntil: AbsoluteTime.addDuration(
|
paidUntil: AbsoluteTime.addDuration(
|
||||||
AbsoluteTime.fromTimestamp(status.contractTerms.timestamp),
|
AbsoluteTime.fromProtocolTimestamp(status.contractTerms.timestamp),
|
||||||
durationFromSpec({ years: 1 }), //FIXME: take this from the contract term
|
durationFromSpec({ years: 1 }), //FIXME: take this from the contract term
|
||||||
),
|
),
|
||||||
};
|
};
|
||||||
@ -1010,7 +1011,7 @@ async function backupRecoveryTheirs(
|
|||||||
shouldRetryFreshProposal: false,
|
shouldRetryFreshProposal: false,
|
||||||
state: {
|
state: {
|
||||||
tag: BackupProviderStateTag.Ready,
|
tag: BackupProviderStateTag.Ready,
|
||||||
nextBackupTimestamp: TalerProtocolTimestamp.now(),
|
nextBackupTimestamp: TalerPreciseTimestamp.now(),
|
||||||
},
|
},
|
||||||
uids: [encodeCrock(getRandomBytes(32))],
|
uids: [encodeCrock(getRandomBytes(32))],
|
||||||
});
|
});
|
||||||
|
@ -51,6 +51,7 @@ import {
|
|||||||
stringToBytes,
|
stringToBytes,
|
||||||
TalerErrorCode,
|
TalerErrorCode,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
TrackTransaction,
|
TrackTransaction,
|
||||||
TransactionMajorState,
|
TransactionMajorState,
|
||||||
TransactionMinorState,
|
TransactionMinorState,
|
||||||
@ -779,7 +780,7 @@ export async function processDepositGroup(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (allDepositedAndWired) {
|
if (allDepositedAndWired) {
|
||||||
dg.timestampFinished = TalerProtocolTimestamp.now();
|
dg.timestampFinished = TalerPreciseTimestamp.now();
|
||||||
dg.operationStatus = DepositOperationStatus.Finished;
|
dg.operationStatus = DepositOperationStatus.Finished;
|
||||||
await tx.depositGroups.put(dg);
|
await tx.depositGroups.put(dg);
|
||||||
}
|
}
|
||||||
@ -858,9 +859,9 @@ async function getExchangeWireFee(
|
|||||||
}
|
}
|
||||||
const fee = fees.find((x) => {
|
const fee = fees.find((x) => {
|
||||||
return AbsoluteTime.isBetween(
|
return AbsoluteTime.isBetween(
|
||||||
AbsoluteTime.fromTimestamp(time),
|
AbsoluteTime.fromProtocolTimestamp(time),
|
||||||
AbsoluteTime.fromTimestamp(x.startStamp),
|
AbsoluteTime.fromProtocolTimestamp(x.startStamp),
|
||||||
AbsoluteTime.fromTimestamp(x.endStamp),
|
AbsoluteTime.fromProtocolTimestamp(x.endStamp),
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
if (!fee) {
|
if (!fee) {
|
||||||
@ -952,7 +953,7 @@ export async function prepareDepositGroup(
|
|||||||
});
|
});
|
||||||
|
|
||||||
const now = AbsoluteTime.now();
|
const now = AbsoluteTime.now();
|
||||||
const nowRounded = AbsoluteTime.toTimestamp(now);
|
const nowRounded = AbsoluteTime.toProtocolTimestamp(now);
|
||||||
const contractTerms: MerchantContractTerms = {
|
const contractTerms: MerchantContractTerms = {
|
||||||
exchanges: exchangeInfos,
|
exchanges: exchangeInfos,
|
||||||
amount: req.amount,
|
amount: req.amount,
|
||||||
@ -966,7 +967,7 @@ export async function prepareDepositGroup(
|
|||||||
wire_transfer_deadline: nowRounded,
|
wire_transfer_deadline: nowRounded,
|
||||||
order_id: "",
|
order_id: "",
|
||||||
h_wire: "",
|
h_wire: "",
|
||||||
pay_deadline: AbsoluteTime.toTimestamp(
|
pay_deadline: AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(now, durationFromSpec({ hours: 1 })),
|
AbsoluteTime.addDuration(now, durationFromSpec({ hours: 1 })),
|
||||||
),
|
),
|
||||||
merchant: {
|
merchant: {
|
||||||
@ -1066,7 +1067,7 @@ export async function createDepositGroup(
|
|||||||
});
|
});
|
||||||
|
|
||||||
const now = AbsoluteTime.now();
|
const now = AbsoluteTime.now();
|
||||||
const nowRounded = AbsoluteTime.toTimestamp(now);
|
const nowRounded = AbsoluteTime.toProtocolTimestamp(now);
|
||||||
const noncePair = await ws.cryptoApi.createEddsaKeypair({});
|
const noncePair = await ws.cryptoApi.createEddsaKeypair({});
|
||||||
const merchantPair = await ws.cryptoApi.createEddsaKeypair({});
|
const merchantPair = await ws.cryptoApi.createEddsaKeypair({});
|
||||||
const wireSalt = encodeCrock(getRandomBytes(16));
|
const wireSalt = encodeCrock(getRandomBytes(16));
|
||||||
@ -1084,7 +1085,7 @@ export async function createDepositGroup(
|
|||||||
wire_transfer_deadline: nowRounded,
|
wire_transfer_deadline: nowRounded,
|
||||||
order_id: "",
|
order_id: "",
|
||||||
h_wire: wireHash,
|
h_wire: wireHash,
|
||||||
pay_deadline: AbsoluteTime.toTimestamp(
|
pay_deadline: AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(now, durationFromSpec({ hours: 1 })),
|
AbsoluteTime.addDuration(now, durationFromSpec({ hours: 1 })),
|
||||||
),
|
),
|
||||||
merchant: {
|
merchant: {
|
||||||
@ -1150,7 +1151,7 @@ export async function createDepositGroup(
|
|||||||
depositGroupId,
|
depositGroupId,
|
||||||
noncePriv: noncePair.priv,
|
noncePriv: noncePair.priv,
|
||||||
noncePub: noncePair.pub,
|
noncePub: noncePair.pub,
|
||||||
timestampCreated: AbsoluteTime.toTimestamp(now),
|
timestampCreated: AbsoluteTime.toPreciseTimestamp(now),
|
||||||
timestampFinished: undefined,
|
timestampFinished: undefined,
|
||||||
transactionPerCoin: payCoinSel.coinSel.coinPubs.map(
|
transactionPerCoin: payCoinSel.coinSel.coinPubs.map(
|
||||||
() => DepositElementStatus.Unknown,
|
() => DepositElementStatus.Unknown,
|
||||||
@ -1260,8 +1261,8 @@ export async function getCounterpartyEffectiveDepositAmount(
|
|||||||
const fee = exchangeDetails.wireInfo.feesForType[wireType].find((x) => {
|
const fee = exchangeDetails.wireInfo.feesForType[wireType].find((x) => {
|
||||||
return AbsoluteTime.isBetween(
|
return AbsoluteTime.isBetween(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
AbsoluteTime.fromTimestamp(x.startStamp),
|
AbsoluteTime.fromProtocolTimestamp(x.startStamp),
|
||||||
AbsoluteTime.fromTimestamp(x.endStamp),
|
AbsoluteTime.fromProtocolTimestamp(x.endStamp),
|
||||||
);
|
);
|
||||||
})?.wireFee;
|
})?.wireFee;
|
||||||
if (fee) {
|
if (fee) {
|
||||||
@ -1337,8 +1338,8 @@ export async function getTotalFeesForDepositAmount(
|
|||||||
(x) => {
|
(x) => {
|
||||||
return AbsoluteTime.isBetween(
|
return AbsoluteTime.isBetween(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
AbsoluteTime.fromTimestamp(x.startStamp),
|
AbsoluteTime.fromProtocolTimestamp(x.startStamp),
|
||||||
AbsoluteTime.fromTimestamp(x.endStamp),
|
AbsoluteTime.fromProtocolTimestamp(x.endStamp),
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
)?.wireFee;
|
)?.wireFee;
|
||||||
|
@ -43,6 +43,7 @@ import {
|
|||||||
Recoup,
|
Recoup,
|
||||||
TalerError,
|
TalerError,
|
||||||
TalerErrorCode,
|
TalerErrorCode,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
TalerProtocolDuration,
|
TalerProtocolDuration,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
URL,
|
URL,
|
||||||
@ -229,7 +230,7 @@ export async function acceptExchangeTermsOfService(
|
|||||||
if (d) {
|
if (d) {
|
||||||
d.tosAccepted = {
|
d.tosAccepted = {
|
||||||
etag: etag || d.tosCurrentEtag,
|
etag: etag || d.tosCurrentEtag,
|
||||||
timestamp: TalerProtocolTimestamp.now(),
|
timestamp: TalerPreciseTimestamp.now(),
|
||||||
};
|
};
|
||||||
await tx.exchangeDetails.put(d);
|
await tx.exchangeDetails.put(d);
|
||||||
}
|
}
|
||||||
@ -407,8 +408,8 @@ export async function provideExchangeRecordInTx(
|
|||||||
baseUrl: baseUrl,
|
baseUrl: baseUrl,
|
||||||
detailsPointer: undefined,
|
detailsPointer: undefined,
|
||||||
lastUpdate: undefined,
|
lastUpdate: undefined,
|
||||||
nextUpdate: AbsoluteTime.toTimestamp(now),
|
nextUpdate: AbsoluteTime.toPreciseTimestamp(now),
|
||||||
nextRefreshCheck: AbsoluteTime.toTimestamp(now),
|
nextRefreshCheck: AbsoluteTime.toPreciseTimestamp(now),
|
||||||
lastKeysEtag: undefined,
|
lastKeysEtag: undefined,
|
||||||
lastWireEtag: undefined,
|
lastWireEtag: undefined,
|
||||||
};
|
};
|
||||||
@ -497,7 +498,7 @@ async function downloadExchangeKeysInfo(
|
|||||||
protocolVersion: exchangeKeysJsonUnchecked.version,
|
protocolVersion: exchangeKeysJsonUnchecked.version,
|
||||||
signingKeys: exchangeKeysJsonUnchecked.signkeys,
|
signingKeys: exchangeKeysJsonUnchecked.signkeys,
|
||||||
reserveClosingDelay: exchangeKeysJsonUnchecked.reserve_closing_delay,
|
reserveClosingDelay: exchangeKeysJsonUnchecked.reserve_closing_delay,
|
||||||
expiry: AbsoluteTime.toTimestamp(
|
expiry: AbsoluteTime.toProtocolTimestamp(
|
||||||
getExpiry(resp, {
|
getExpiry(resp, {
|
||||||
minDuration: durationFromSpec({ hours: 1 }),
|
minDuration: durationFromSpec({ hours: 1 }),
|
||||||
}),
|
}),
|
||||||
@ -601,7 +602,9 @@ export async function updateExchangeFromUrlHandler(
|
|||||||
if (
|
if (
|
||||||
!forceNow &&
|
!forceNow &&
|
||||||
exchangeDetails !== undefined &&
|
exchangeDetails !== undefined &&
|
||||||
!AbsoluteTime.isExpired(AbsoluteTime.fromTimestamp(exchange.nextUpdate))
|
!AbsoluteTime.isExpired(
|
||||||
|
AbsoluteTime.fromPreciseTimestamp(exchange.nextUpdate),
|
||||||
|
)
|
||||||
) {
|
) {
|
||||||
logger.info("using existing exchange info");
|
logger.info("using existing exchange info");
|
||||||
return {
|
return {
|
||||||
@ -724,15 +727,17 @@ export async function updateExchangeFromUrlHandler(
|
|||||||
if (existingDetails?.rowId) {
|
if (existingDetails?.rowId) {
|
||||||
newDetails.rowId = existingDetails.rowId;
|
newDetails.rowId = existingDetails.rowId;
|
||||||
}
|
}
|
||||||
r.lastUpdate = TalerProtocolTimestamp.now();
|
r.lastUpdate = TalerPreciseTimestamp.now();
|
||||||
r.nextUpdate = keysInfo.expiry;
|
r.nextUpdate = AbsoluteTime.toPreciseTimestamp(
|
||||||
|
AbsoluteTime.fromProtocolTimestamp(keysInfo.expiry),
|
||||||
|
);
|
||||||
// New denominations might be available.
|
// New denominations might be available.
|
||||||
r.nextRefreshCheck = TalerProtocolTimestamp.now();
|
r.nextRefreshCheck = TalerPreciseTimestamp.now();
|
||||||
if (detailsPointerChanged) {
|
if (detailsPointerChanged) {
|
||||||
r.detailsPointer = {
|
r.detailsPointer = {
|
||||||
currency: newDetails.currency,
|
currency: newDetails.currency,
|
||||||
masterPublicKey: newDetails.masterPublicKey,
|
masterPublicKey: newDetails.masterPublicKey,
|
||||||
updateClock: TalerProtocolTimestamp.now(),
|
updateClock: TalerPreciseTimestamp.now(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
await tx.exchanges.put(r);
|
await tx.exchanges.put(r);
|
||||||
|
@ -66,6 +66,7 @@ import {
|
|||||||
TalerError,
|
TalerError,
|
||||||
TalerErrorCode,
|
TalerErrorCode,
|
||||||
TalerErrorDetail,
|
TalerErrorDetail,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
TalerProtocolViolationError,
|
TalerProtocolViolationError,
|
||||||
TalerUriAction,
|
TalerUriAction,
|
||||||
@ -621,7 +622,7 @@ async function createPurchase(
|
|||||||
noncePriv: priv,
|
noncePriv: priv,
|
||||||
noncePub: pub,
|
noncePub: pub,
|
||||||
claimToken,
|
claimToken,
|
||||||
timestamp: AbsoluteTime.toTimestamp(AbsoluteTime.now()),
|
timestamp: TalerPreciseTimestamp.now(),
|
||||||
merchantBaseUrl,
|
merchantBaseUrl,
|
||||||
orderId,
|
orderId,
|
||||||
proposalId: proposalId,
|
proposalId: proposalId,
|
||||||
@ -682,7 +683,7 @@ async function storeFirstPaySuccess(
|
|||||||
tag: TransactionType.Payment,
|
tag: TransactionType.Payment,
|
||||||
proposalId,
|
proposalId,
|
||||||
});
|
});
|
||||||
const now = AbsoluteTime.toTimestamp(AbsoluteTime.now());
|
const now = AbsoluteTime.toPreciseTimestamp(AbsoluteTime.now());
|
||||||
const transitionInfo = await ws.db
|
const transitionInfo = await ws.db
|
||||||
.mktx((x) => [x.purchases, x.contractTerms])
|
.mktx((x) => [x.purchases, x.contractTerms])
|
||||||
.runReadWrite(async (tx) => {
|
.runReadWrite(async (tx) => {
|
||||||
@ -721,7 +722,7 @@ async function storeFirstPaySuccess(
|
|||||||
const ar = Duration.fromTalerProtocolDuration(protoAr);
|
const ar = Duration.fromTalerProtocolDuration(protoAr);
|
||||||
logger.info("auto_refund present");
|
logger.info("auto_refund present");
|
||||||
purchase.purchaseStatus = PurchaseStatus.QueryingAutoRefund;
|
purchase.purchaseStatus = PurchaseStatus.QueryingAutoRefund;
|
||||||
purchase.autoRefundDeadline = AbsoluteTime.toTimestamp(
|
purchase.autoRefundDeadline = AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(AbsoluteTime.now(), ar),
|
AbsoluteTime.addDuration(AbsoluteTime.now(), ar),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -923,7 +924,7 @@ async function unblockBackup(
|
|||||||
.forEachAsync(async (bp) => {
|
.forEachAsync(async (bp) => {
|
||||||
bp.state = {
|
bp.state = {
|
||||||
tag: BackupProviderStateTag.Ready,
|
tag: BackupProviderStateTag.Ready,
|
||||||
nextBackupTimestamp: TalerProtocolTimestamp.now(),
|
nextBackupTimestamp: TalerPreciseTimestamp.now(),
|
||||||
};
|
};
|
||||||
tx.backupProviders.put(bp);
|
tx.backupProviders.put(bp);
|
||||||
});
|
});
|
||||||
@ -1422,7 +1423,7 @@ export async function confirmPay(
|
|||||||
totalPayCost: Amounts.stringify(payCostInfo),
|
totalPayCost: Amounts.stringify(payCostInfo),
|
||||||
};
|
};
|
||||||
p.lastSessionId = sessionId;
|
p.lastSessionId = sessionId;
|
||||||
p.timestampAccept = TalerProtocolTimestamp.now();
|
p.timestampAccept = TalerPreciseTimestamp.now();
|
||||||
p.purchaseStatus = PurchaseStatus.Paying;
|
p.purchaseStatus = PurchaseStatus.Paying;
|
||||||
await tx.purchases.put(p);
|
await tx.purchases.put(p);
|
||||||
await spendCoins(ws, tx, {
|
await spendCoins(ws, tx, {
|
||||||
@ -1925,7 +1926,7 @@ async function processPurchaseAutoRefund(
|
|||||||
if (
|
if (
|
||||||
!purchase.autoRefundDeadline ||
|
!purchase.autoRefundDeadline ||
|
||||||
AbsoluteTime.isExpired(
|
AbsoluteTime.isExpired(
|
||||||
AbsoluteTime.fromTimestamp(purchase.autoRefundDeadline),
|
AbsoluteTime.fromProtocolTimestamp(purchase.autoRefundDeadline),
|
||||||
)
|
)
|
||||||
) {
|
) {
|
||||||
const transitionInfo = await ws.db
|
const transitionInfo = await ws.db
|
||||||
@ -2068,9 +2069,9 @@ async function processPurchaseAbortingRefund(
|
|||||||
coin_pub: payCoinSelection.coinPubs[i],
|
coin_pub: payCoinSelection.coinPubs[i],
|
||||||
refund_amount: Amounts.stringify(payCoinSelection.coinContributions[i]),
|
refund_amount: Amounts.stringify(payCoinSelection.coinContributions[i]),
|
||||||
rtransaction_id: 0,
|
rtransaction_id: 0,
|
||||||
execution_time: AbsoluteTime.toTimestamp(
|
execution_time: AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(
|
AbsoluteTime.addDuration(
|
||||||
AbsoluteTime.fromTimestamp(download.contractData.timestamp),
|
AbsoluteTime.fromProtocolTimestamp(download.contractData.timestamp),
|
||||||
Duration.fromSpec({ seconds: 1 }),
|
Duration.fromSpec({ seconds: 1 }),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
@ -2267,7 +2268,7 @@ async function storeRefunds(
|
|||||||
});
|
});
|
||||||
|
|
||||||
const newRefundGroupId = encodeCrock(randomBytes(32));
|
const newRefundGroupId = encodeCrock(randomBytes(32));
|
||||||
const now = TalerProtocolTimestamp.now();
|
const now = TalerPreciseTimestamp.now();
|
||||||
|
|
||||||
const download = await expectProposalDownload(ws, purchase);
|
const download = await expectProposalDownload(ws, purchase);
|
||||||
const currency = Amounts.currencyOf(download.contractData.amount);
|
const currency = Amounts.currencyOf(download.contractData.amount);
|
||||||
|
@ -78,6 +78,7 @@ import {
|
|||||||
TransactionState,
|
TransactionState,
|
||||||
TransactionMajorState,
|
TransactionMajorState,
|
||||||
TransactionMinorState,
|
TransactionMinorState,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
} from "@gnu-taler/taler-util";
|
} from "@gnu-taler/taler-util";
|
||||||
import { SpendCoinDetails } from "../crypto/cryptoImplementation.js";
|
import { SpendCoinDetails } from "../crypto/cryptoImplementation.js";
|
||||||
import {
|
import {
|
||||||
@ -728,7 +729,7 @@ export async function initiatePeerPushDebit(
|
|||||||
purseExpiration: purseExpiration,
|
purseExpiration: purseExpiration,
|
||||||
pursePriv: pursePair.priv,
|
pursePriv: pursePair.priv,
|
||||||
pursePub: pursePair.pub,
|
pursePub: pursePair.pub,
|
||||||
timestampCreated: TalerProtocolTimestamp.now(),
|
timestampCreated: TalerPreciseTimestamp.now(),
|
||||||
status: PeerPushPaymentInitiationStatus.PendingCreatePurse,
|
status: PeerPushPaymentInitiationStatus.PendingCreatePurse,
|
||||||
contractTerms: contractTerms,
|
contractTerms: contractTerms,
|
||||||
coinSel: {
|
coinSel: {
|
||||||
@ -889,7 +890,7 @@ export async function preparePeerPushCredit(
|
|||||||
exchangeBaseUrl: exchangeBaseUrl,
|
exchangeBaseUrl: exchangeBaseUrl,
|
||||||
mergePriv: dec.mergePriv,
|
mergePriv: dec.mergePriv,
|
||||||
pursePub: pursePub,
|
pursePub: pursePub,
|
||||||
timestamp: TalerProtocolTimestamp.now(),
|
timestamp: TalerPreciseTimestamp.now(),
|
||||||
contractTermsHash,
|
contractTermsHash,
|
||||||
status: PeerPushPaymentIncomingStatus.Proposed,
|
status: PeerPushPaymentIncomingStatus.Proposed,
|
||||||
withdrawalGroupId,
|
withdrawalGroupId,
|
||||||
@ -1450,7 +1451,7 @@ export async function preparePeerPullDebit(
|
|||||||
contractPriv: contractPriv,
|
contractPriv: contractPriv,
|
||||||
exchangeBaseUrl: exchangeBaseUrl,
|
exchangeBaseUrl: exchangeBaseUrl,
|
||||||
pursePub: pursePub,
|
pursePub: pursePub,
|
||||||
timestampCreated: TalerProtocolTimestamp.now(),
|
timestampCreated: TalerPreciseTimestamp.now(),
|
||||||
contractTerms,
|
contractTerms,
|
||||||
status: PeerPullPaymentIncomingStatus.Proposed,
|
status: PeerPullPaymentIncomingStatus.Proposed,
|
||||||
totalCostEstimated: Amounts.stringify(totalAmount),
|
totalCostEstimated: Amounts.stringify(totalAmount),
|
||||||
@ -1668,7 +1669,7 @@ export async function processPeerPullCredit(
|
|||||||
contractTermsHash: pullIni.contractTermsHash,
|
contractTermsHash: pullIni.contractTermsHash,
|
||||||
flags: WalletAccountMergeFlags.CreateWithPurseFee,
|
flags: WalletAccountMergeFlags.CreateWithPurseFee,
|
||||||
mergePriv: pullIni.mergePriv,
|
mergePriv: pullIni.mergePriv,
|
||||||
mergeTimestamp: pullIni.mergeTimestamp,
|
mergeTimestamp: TalerPreciseTimestamp.round(pullIni.mergeTimestamp),
|
||||||
purseAmount: pullIni.contractTerms.amount,
|
purseAmount: pullIni.contractTerms.amount,
|
||||||
purseExpiration: purseExpiration,
|
purseExpiration: purseExpiration,
|
||||||
purseFee: purseFee,
|
purseFee: purseFee,
|
||||||
@ -1680,7 +1681,7 @@ export async function processPeerPullCredit(
|
|||||||
|
|
||||||
const reservePurseReqBody: ExchangeReservePurseRequest = {
|
const reservePurseReqBody: ExchangeReservePurseRequest = {
|
||||||
merge_sig: sigRes.mergeSig,
|
merge_sig: sigRes.mergeSig,
|
||||||
merge_timestamp: pullIni.mergeTimestamp,
|
merge_timestamp: TalerPreciseTimestamp.round(pullIni.mergeTimestamp),
|
||||||
h_contract_terms: pullIni.contractTermsHash,
|
h_contract_terms: pullIni.contractTermsHash,
|
||||||
merge_pub: pullIni.mergePub,
|
merge_pub: pullIni.mergePub,
|
||||||
min_age: 0,
|
min_age: 0,
|
||||||
@ -1788,8 +1789,8 @@ async function getPreferredExchangeForCurrency(
|
|||||||
if (candidate.lastWithdrawal && e.lastWithdrawal) {
|
if (candidate.lastWithdrawal && e.lastWithdrawal) {
|
||||||
if (
|
if (
|
||||||
AbsoluteTime.cmp(
|
AbsoluteTime.cmp(
|
||||||
AbsoluteTime.fromTimestamp(e.lastWithdrawal),
|
AbsoluteTime.fromPreciseTimestamp(e.lastWithdrawal),
|
||||||
AbsoluteTime.fromTimestamp(candidate.lastWithdrawal),
|
AbsoluteTime.fromPreciseTimestamp(candidate.lastWithdrawal),
|
||||||
) > 0
|
) > 0
|
||||||
) {
|
) {
|
||||||
candidate = e;
|
candidate = e;
|
||||||
@ -1874,7 +1875,7 @@ export async function initiatePeerPullPayment(
|
|||||||
exchangeBaseUrl: exchangeBaseUrl,
|
exchangeBaseUrl: exchangeBaseUrl,
|
||||||
});
|
});
|
||||||
|
|
||||||
const mergeTimestamp = TalerProtocolTimestamp.now();
|
const mergeTimestamp = TalerPreciseTimestamp.now();
|
||||||
|
|
||||||
const pursePair = await ws.cryptoApi.createEddsaKeypair({});
|
const pursePair = await ws.cryptoApi.createEddsaKeypair({});
|
||||||
const mergePair = await ws.cryptoApi.createEddsaKeypair({});
|
const mergePair = await ws.cryptoApi.createEddsaKeypair({});
|
||||||
|
@ -79,7 +79,7 @@ async function gatherExchangePending(
|
|||||||
const opTag = TaskIdentifiers.forExchangeUpdate(exch);
|
const opTag = TaskIdentifiers.forExchangeUpdate(exch);
|
||||||
let opr = await tx.operationRetries.get(opTag);
|
let opr = await tx.operationRetries.get(opTag);
|
||||||
const timestampDue =
|
const timestampDue =
|
||||||
opr?.retryInfo.nextRetry ?? AbsoluteTime.fromTimestamp(exch.nextUpdate);
|
opr?.retryInfo.nextRetry ?? AbsoluteTime.fromPreciseTimestamp(exch.nextUpdate);
|
||||||
resp.pendingOperations.push({
|
resp.pendingOperations.push({
|
||||||
type: PendingTaskType.ExchangeUpdate,
|
type: PendingTaskType.ExchangeUpdate,
|
||||||
...getPendingCommon(ws, opTag, timestampDue),
|
...getPendingCommon(ws, opTag, timestampDue),
|
||||||
@ -94,7 +94,7 @@ async function gatherExchangePending(
|
|||||||
resp.pendingOperations.push({
|
resp.pendingOperations.push({
|
||||||
type: PendingTaskType.ExchangeCheckRefresh,
|
type: PendingTaskType.ExchangeCheckRefresh,
|
||||||
...getPendingCommon(ws, opTag, timestampDue),
|
...getPendingCommon(ws, opTag, timestampDue),
|
||||||
timestampDue: AbsoluteTime.fromTimestamp(exch.nextRefreshCheck),
|
timestampDue: AbsoluteTime.fromPreciseTimestamp(exch.nextRefreshCheck),
|
||||||
givesLifeness: false,
|
givesLifeness: false,
|
||||||
exchangeBaseUrl: exch.baseUrl,
|
exchangeBaseUrl: exch.baseUrl,
|
||||||
});
|
});
|
||||||
@ -333,7 +333,7 @@ async function gatherBackupPending(
|
|||||||
const opId = TaskIdentifiers.forBackup(bp);
|
const opId = TaskIdentifiers.forBackup(bp);
|
||||||
const retryRecord = await tx.operationRetries.get(opId);
|
const retryRecord = await tx.operationRetries.get(opId);
|
||||||
if (bp.state.tag === BackupProviderStateTag.Ready) {
|
if (bp.state.tag === BackupProviderStateTag.Ready) {
|
||||||
const timestampDue = AbsoluteTime.fromTimestamp(
|
const timestampDue = AbsoluteTime.fromPreciseTimestamp(
|
||||||
bp.state.nextBackupTimestamp,
|
bp.state.nextBackupTimestamp,
|
||||||
);
|
);
|
||||||
resp.pendingOperations.push({
|
resp.pendingOperations.push({
|
||||||
|
@ -36,6 +36,7 @@ import {
|
|||||||
NotificationType,
|
NotificationType,
|
||||||
RefreshReason,
|
RefreshReason,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
URL,
|
URL,
|
||||||
} from "@gnu-taler/taler-util";
|
} from "@gnu-taler/taler-util";
|
||||||
import {
|
import {
|
||||||
@ -424,7 +425,7 @@ export async function processRecoupGroupHandler(
|
|||||||
if (!rg2) {
|
if (!rg2) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
rg2.timestampFinished = TalerProtocolTimestamp.now();
|
rg2.timestampFinished = TalerPreciseTimestamp.now();
|
||||||
if (rg2.scheduleRefreshCoins.length > 0) {
|
if (rg2.scheduleRefreshCoins.length > 0) {
|
||||||
const refreshGroupId = await createRefreshGroup(
|
const refreshGroupId = await createRefreshGroup(
|
||||||
ws,
|
ws,
|
||||||
@ -460,7 +461,7 @@ export async function createRecoupGroup(
|
|||||||
exchangeBaseUrl: exchangeBaseUrl,
|
exchangeBaseUrl: exchangeBaseUrl,
|
||||||
coinPubs: coinPubs,
|
coinPubs: coinPubs,
|
||||||
timestampFinished: undefined,
|
timestampFinished: undefined,
|
||||||
timestampStarted: TalerProtocolTimestamp.now(),
|
timestampStarted: TalerPreciseTimestamp.now(),
|
||||||
recoupFinishedPerCoin: coinPubs.map(() => false),
|
recoupFinishedPerCoin: coinPubs.map(() => false),
|
||||||
scheduleRefreshCoins: [],
|
scheduleRefreshCoins: [],
|
||||||
};
|
};
|
||||||
|
@ -48,6 +48,7 @@ import {
|
|||||||
RefreshReason,
|
RefreshReason,
|
||||||
TalerErrorCode,
|
TalerErrorCode,
|
||||||
TalerErrorDetail,
|
TalerErrorDetail,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
TransactionMajorState,
|
TransactionMajorState,
|
||||||
TransactionState,
|
TransactionState,
|
||||||
@ -156,10 +157,10 @@ function updateGroupStatus(rg: RefreshGroupRecord): void {
|
|||||||
);
|
);
|
||||||
if (allDone) {
|
if (allDone) {
|
||||||
if (anyFrozen) {
|
if (anyFrozen) {
|
||||||
rg.timestampFinished = AbsoluteTime.toTimestamp(AbsoluteTime.now());
|
rg.timestampFinished = TalerPreciseTimestamp.now();
|
||||||
rg.operationStatus = RefreshOperationStatus.FinishedWithError;
|
rg.operationStatus = RefreshOperationStatus.FinishedWithError;
|
||||||
} else {
|
} else {
|
||||||
rg.timestampFinished = AbsoluteTime.toTimestamp(AbsoluteTime.now());
|
rg.timestampFinished = TalerPreciseTimestamp.now();
|
||||||
rg.operationStatus = RefreshOperationStatus.Finished;
|
rg.operationStatus = RefreshOperationStatus.Finished;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1046,12 +1047,12 @@ export async function createRefreshGroup(
|
|||||||
estimatedOutputPerCoin: estimatedOutputPerCoin.map((x) =>
|
estimatedOutputPerCoin: estimatedOutputPerCoin.map((x) =>
|
||||||
Amounts.stringify(x),
|
Amounts.stringify(x),
|
||||||
),
|
),
|
||||||
timestampCreated: TalerProtocolTimestamp.now(),
|
timestampCreated: TalerPreciseTimestamp.now(),
|
||||||
};
|
};
|
||||||
|
|
||||||
if (oldCoinPubs.length == 0) {
|
if (oldCoinPubs.length == 0) {
|
||||||
logger.warn("created refresh group with zero coins");
|
logger.warn("created refresh group with zero coins");
|
||||||
refreshGroup.timestampFinished = TalerProtocolTimestamp.now();
|
refreshGroup.timestampFinished = TalerPreciseTimestamp.now();
|
||||||
refreshGroup.operationStatus = RefreshOperationStatus.Finished;
|
refreshGroup.operationStatus = RefreshOperationStatus.Finished;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1075,8 +1076,8 @@ export async function createRefreshGroup(
|
|||||||
* Timestamp after which the wallet would do the next check for an auto-refresh.
|
* Timestamp after which the wallet would do the next check for an auto-refresh.
|
||||||
*/
|
*/
|
||||||
function getAutoRefreshCheckThreshold(d: DenominationRecord): AbsoluteTime {
|
function getAutoRefreshCheckThreshold(d: DenominationRecord): AbsoluteTime {
|
||||||
const expireWithdraw = AbsoluteTime.fromTimestamp(d.stampExpireWithdraw);
|
const expireWithdraw = AbsoluteTime.fromProtocolTimestamp(d.stampExpireWithdraw);
|
||||||
const expireDeposit = AbsoluteTime.fromTimestamp(d.stampExpireDeposit);
|
const expireDeposit = AbsoluteTime.fromProtocolTimestamp(d.stampExpireDeposit);
|
||||||
const delta = AbsoluteTime.difference(expireWithdraw, expireDeposit);
|
const delta = AbsoluteTime.difference(expireWithdraw, expireDeposit);
|
||||||
const deltaDiv = durationMul(delta, 0.75);
|
const deltaDiv = durationMul(delta, 0.75);
|
||||||
return AbsoluteTime.addDuration(expireWithdraw, deltaDiv);
|
return AbsoluteTime.addDuration(expireWithdraw, deltaDiv);
|
||||||
@ -1086,8 +1087,8 @@ function getAutoRefreshCheckThreshold(d: DenominationRecord): AbsoluteTime {
|
|||||||
* Timestamp after which the wallet would do an auto-refresh.
|
* Timestamp after which the wallet would do an auto-refresh.
|
||||||
*/
|
*/
|
||||||
function getAutoRefreshExecuteThreshold(d: DenominationRecord): AbsoluteTime {
|
function getAutoRefreshExecuteThreshold(d: DenominationRecord): AbsoluteTime {
|
||||||
const expireWithdraw = AbsoluteTime.fromTimestamp(d.stampExpireWithdraw);
|
const expireWithdraw = AbsoluteTime.fromProtocolTimestamp(d.stampExpireWithdraw);
|
||||||
const expireDeposit = AbsoluteTime.fromTimestamp(d.stampExpireDeposit);
|
const expireDeposit = AbsoluteTime.fromProtocolTimestamp(d.stampExpireDeposit);
|
||||||
const delta = AbsoluteTime.difference(expireWithdraw, expireDeposit);
|
const delta = AbsoluteTime.difference(expireWithdraw, expireDeposit);
|
||||||
const deltaDiv = durationMul(delta, 0.5);
|
const deltaDiv = durationMul(delta, 0.5);
|
||||||
return AbsoluteTime.addDuration(expireWithdraw, deltaDiv);
|
return AbsoluteTime.addDuration(expireWithdraw, deltaDiv);
|
||||||
@ -1174,7 +1175,7 @@ export async function autoRefresh(
|
|||||||
logger.info(
|
logger.info(
|
||||||
`next refresh check at ${AbsoluteTime.toIsoString(minCheckThreshold)}`,
|
`next refresh check at ${AbsoluteTime.toIsoString(minCheckThreshold)}`,
|
||||||
);
|
);
|
||||||
exchange.nextRefreshCheck = AbsoluteTime.toTimestamp(minCheckThreshold);
|
exchange.nextRefreshCheck = AbsoluteTime.toPreciseTimestamp(minCheckThreshold);
|
||||||
await tx.exchanges.put(exchange);
|
await tx.exchanges.put(exchange);
|
||||||
});
|
});
|
||||||
return OperationAttemptResult.finishedEmpty();
|
return OperationAttemptResult.finishedEmpty();
|
||||||
|
@ -536,7 +536,7 @@ export async function runIntegrationTest2(
|
|||||||
partialContractTerms: {
|
partialContractTerms: {
|
||||||
amount: `${currency}:1`,
|
amount: `${currency}:1`,
|
||||||
summary: "Payment Peer Push Test",
|
summary: "Payment Peer Push Test",
|
||||||
purse_expiration: AbsoluteTime.toTimestamp(
|
purse_expiration: AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(
|
AbsoluteTime.addDuration(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
Duration.fromSpec({ hours: 1 }),
|
Duration.fromSpec({ hours: 1 }),
|
||||||
@ -557,7 +557,7 @@ export async function runIntegrationTest2(
|
|||||||
partialContractTerms: {
|
partialContractTerms: {
|
||||||
amount: `${currency}:1`,
|
amount: `${currency}:1`,
|
||||||
summary: "Payment Peer Pull Test",
|
summary: "Payment Peer Pull Test",
|
||||||
purse_expiration: AbsoluteTime.toTimestamp(
|
purse_expiration: AbsoluteTime.toProtocolTimestamp(
|
||||||
AbsoluteTime.addDuration(
|
AbsoluteTime.addDuration(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
Duration.fromSpec({ hours: 1 }),
|
Duration.fromSpec({ hours: 1 }),
|
||||||
|
@ -33,6 +33,7 @@ import {
|
|||||||
parseTipUri,
|
parseTipUri,
|
||||||
PrepareTipResult,
|
PrepareTipResult,
|
||||||
TalerErrorCode,
|
TalerErrorCode,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
TipPlanchetDetail,
|
TipPlanchetDetail,
|
||||||
TransactionMajorState,
|
TransactionMajorState,
|
||||||
@ -160,7 +161,7 @@ export async function prepareTip(
|
|||||||
exchangeBaseUrl: tipPickupStatus.exchange_url,
|
exchangeBaseUrl: tipPickupStatus.exchange_url,
|
||||||
next_url: tipPickupStatus.next_url,
|
next_url: tipPickupStatus.next_url,
|
||||||
merchantBaseUrl: res.merchantBaseUrl,
|
merchantBaseUrl: res.merchantBaseUrl,
|
||||||
createdTimestamp: TalerProtocolTimestamp.now(),
|
createdTimestamp: TalerPreciseTimestamp.now(),
|
||||||
merchantTipId: res.merchantTipId,
|
merchantTipId: res.merchantTipId,
|
||||||
tipAmountEffective: Amounts.stringify(selectedDenoms.totalCoinValue),
|
tipAmountEffective: Amounts.stringify(selectedDenoms.totalCoinValue),
|
||||||
denomsSel: selectedDenoms,
|
denomsSel: selectedDenoms,
|
||||||
@ -365,7 +366,7 @@ export async function processTip(
|
|||||||
if (tr.pickedUpTimestamp) {
|
if (tr.pickedUpTimestamp) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
tr.pickedUpTimestamp = TalerProtocolTimestamp.now();
|
tr.pickedUpTimestamp = TalerPreciseTimestamp.now();
|
||||||
await tx.tips.put(tr);
|
await tx.tips.put(tr);
|
||||||
for (const cr of newCoinRecords) {
|
for (const cr of newCoinRecords) {
|
||||||
await makeCoinAvailable(ws, tx, cr);
|
await makeCoinAvailable(ws, tx, cr);
|
||||||
@ -390,7 +391,7 @@ export async function acceptTip(
|
|||||||
logger.error("tip not found");
|
logger.error("tip not found");
|
||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
tipRecord.acceptedTimestamp = TalerProtocolTimestamp.now();
|
tipRecord.acceptedTimestamp = TalerPreciseTimestamp.now();
|
||||||
await tx.tips.put(tipRecord);
|
await tx.tips.put(tipRecord);
|
||||||
|
|
||||||
return tipRecord;
|
return tipRecord;
|
||||||
|
@ -30,6 +30,7 @@ import {
|
|||||||
stringifyPayPullUri,
|
stringifyPayPullUri,
|
||||||
stringifyPayPushUri,
|
stringifyPayPushUri,
|
||||||
TalerErrorCode,
|
TalerErrorCode,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
Transaction,
|
Transaction,
|
||||||
TransactionByIdRequest,
|
TransactionByIdRequest,
|
||||||
@ -472,7 +473,7 @@ function buildTransactionForPeerPullCredit(
|
|||||||
amountRaw: Amounts.stringify(wsr.instructedAmount),
|
amountRaw: Amounts.stringify(wsr.instructedAmount),
|
||||||
exchangeBaseUrl: wsr.exchangeBaseUrl,
|
exchangeBaseUrl: wsr.exchangeBaseUrl,
|
||||||
// Old transactions don't have it!
|
// Old transactions don't have it!
|
||||||
timestamp: pullCredit.mergeTimestamp ?? TalerProtocolTimestamp.now(),
|
timestamp: pullCredit.mergeTimestamp ?? TalerPreciseTimestamp.now(),
|
||||||
info: {
|
info: {
|
||||||
expiration: wsr.wgInfo.contractTerms.purse_expiration,
|
expiration: wsr.wgInfo.contractTerms.purse_expiration,
|
||||||
summary: wsr.wgInfo.contractTerms.summary,
|
summary: wsr.wgInfo.contractTerms.summary,
|
||||||
@ -1171,8 +1172,8 @@ export async function getTransactions(
|
|||||||
|
|
||||||
const txCmp = (h1: Transaction, h2: Transaction) => {
|
const txCmp = (h1: Transaction, h2: Transaction) => {
|
||||||
const tsCmp = AbsoluteTime.cmp(
|
const tsCmp = AbsoluteTime.cmp(
|
||||||
AbsoluteTime.fromTimestamp(h1.timestamp),
|
AbsoluteTime.fromPreciseTimestamp(h1.timestamp),
|
||||||
AbsoluteTime.fromTimestamp(h2.timestamp),
|
AbsoluteTime.fromPreciseTimestamp(h2.timestamp),
|
||||||
);
|
);
|
||||||
if (tsCmp === 0) {
|
if (tsCmp === 0) {
|
||||||
return Math.sign(txOrder[h1.type] - txOrder[h2.type]);
|
return Math.sign(txOrder[h1.type] - txOrder[h2.type]);
|
||||||
|
@ -66,6 +66,7 @@ import {
|
|||||||
TransactionState,
|
TransactionState,
|
||||||
TransactionMajorState,
|
TransactionMajorState,
|
||||||
TransactionMinorState,
|
TransactionMinorState,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
} from "@gnu-taler/taler-util";
|
} from "@gnu-taler/taler-util";
|
||||||
import { EddsaKeypair } from "../crypto/cryptoImplementation.js";
|
import { EddsaKeypair } from "../crypto/cryptoImplementation.js";
|
||||||
import {
|
import {
|
||||||
@ -1327,7 +1328,7 @@ export async function processWithdrawalGroup(
|
|||||||
}
|
}
|
||||||
const txStatusOld = computeWithdrawalTransactionStatus(wg);
|
const txStatusOld = computeWithdrawalTransactionStatus(wg);
|
||||||
wg.status = WithdrawalGroupStatus.Finished;
|
wg.status = WithdrawalGroupStatus.Finished;
|
||||||
wg.timestampFinish = TalerProtocolTimestamp.now();
|
wg.timestampFinish = TalerPreciseTimestamp.now();
|
||||||
const txStatusNew = computeWithdrawalTransactionStatus(wg);
|
const txStatusNew = computeWithdrawalTransactionStatus(wg);
|
||||||
await tx.withdrawalGroups.put(wg);
|
await tx.withdrawalGroups.put(wg);
|
||||||
return {
|
return {
|
||||||
@ -1428,7 +1429,7 @@ export async function processWithdrawalGroup(
|
|||||||
logger.info(`now withdrawn ${numFinished} of ${numTotalCoins} coins`);
|
logger.info(`now withdrawn ${numFinished} of ${numTotalCoins} coins`);
|
||||||
if (wg.timestampFinish === undefined && numFinished === numTotalCoins) {
|
if (wg.timestampFinish === undefined && numFinished === numTotalCoins) {
|
||||||
finishedForFirstTime = true;
|
finishedForFirstTime = true;
|
||||||
wg.timestampFinish = TalerProtocolTimestamp.now();
|
wg.timestampFinish = TalerPreciseTimestamp.now();
|
||||||
wg.status = WithdrawalGroupStatus.Finished;
|
wg.status = WithdrawalGroupStatus.Finished;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1613,8 +1614,8 @@ export async function getExchangeWithdrawalInfo(
|
|||||||
}
|
}
|
||||||
if (
|
if (
|
||||||
AbsoluteTime.cmp(
|
AbsoluteTime.cmp(
|
||||||
AbsoluteTime.fromTimestamp(expireDeposit),
|
AbsoluteTime.fromProtocolTimestamp(expireDeposit),
|
||||||
AbsoluteTime.fromTimestamp(earliestDepositExpiration),
|
AbsoluteTime.fromProtocolTimestamp(earliestDepositExpiration),
|
||||||
) < 0
|
) < 0
|
||||||
) {
|
) {
|
||||||
earliestDepositExpiration = expireDeposit;
|
earliestDepositExpiration = expireDeposit;
|
||||||
@ -1910,7 +1911,7 @@ async function registerReserveWithBank(
|
|||||||
if (r.wgInfo.withdrawalType !== WithdrawalRecordType.BankIntegrated) {
|
if (r.wgInfo.withdrawalType !== WithdrawalRecordType.BankIntegrated) {
|
||||||
throw Error("invariant failed");
|
throw Error("invariant failed");
|
||||||
}
|
}
|
||||||
r.wgInfo.bankInfo.timestampReserveInfoPosted = AbsoluteTime.toTimestamp(
|
r.wgInfo.bankInfo.timestampReserveInfoPosted = AbsoluteTime.toPreciseTimestamp(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
);
|
);
|
||||||
const oldTxState = computeWithdrawalTransactionStatus(r);
|
const oldTxState = computeWithdrawalTransactionStatus(r);
|
||||||
@ -1994,7 +1995,7 @@ async function processReserveBankStatus(
|
|||||||
if (r.wgInfo.withdrawalType !== WithdrawalRecordType.BankIntegrated) {
|
if (r.wgInfo.withdrawalType !== WithdrawalRecordType.BankIntegrated) {
|
||||||
throw Error("invariant failed");
|
throw Error("invariant failed");
|
||||||
}
|
}
|
||||||
const now = AbsoluteTime.toTimestamp(AbsoluteTime.now());
|
const now = AbsoluteTime.toPreciseTimestamp(AbsoluteTime.now());
|
||||||
const oldTxState = computeWithdrawalTransactionStatus(r);
|
const oldTxState = computeWithdrawalTransactionStatus(r);
|
||||||
r.wgInfo.bankInfo.timestampBankConfirmed = now;
|
r.wgInfo.bankInfo.timestampBankConfirmed = now;
|
||||||
r.status = WithdrawalGroupStatus.FailedBankAborted;
|
r.status = WithdrawalGroupStatus.FailedBankAborted;
|
||||||
@ -2044,7 +2045,7 @@ async function processReserveBankStatus(
|
|||||||
const oldTxState = computeWithdrawalTransactionStatus(r);
|
const oldTxState = computeWithdrawalTransactionStatus(r);
|
||||||
if (status.transfer_done) {
|
if (status.transfer_done) {
|
||||||
logger.info("withdrawal: transfer confirmed by bank.");
|
logger.info("withdrawal: transfer confirmed by bank.");
|
||||||
const now = AbsoluteTime.toTimestamp(AbsoluteTime.now());
|
const now = AbsoluteTime.toPreciseTimestamp(AbsoluteTime.now());
|
||||||
r.wgInfo.bankInfo.timestampBankConfirmed = now;
|
r.wgInfo.bankInfo.timestampBankConfirmed = now;
|
||||||
r.status = WithdrawalGroupStatus.PendingQueryingStatus;
|
r.status = WithdrawalGroupStatus.PendingQueryingStatus;
|
||||||
// FIXME: Notification is deprecated with DD37.
|
// FIXME: Notification is deprecated with DD37.
|
||||||
@ -2105,7 +2106,7 @@ export async function internalCreateWithdrawalGroup(
|
|||||||
): Promise<WithdrawalGroupRecord> {
|
): Promise<WithdrawalGroupRecord> {
|
||||||
const reserveKeyPair =
|
const reserveKeyPair =
|
||||||
args.reserveKeyPair ?? (await ws.cryptoApi.createEddsaKeypair({}));
|
args.reserveKeyPair ?? (await ws.cryptoApi.createEddsaKeypair({}));
|
||||||
const now = AbsoluteTime.toTimestamp(AbsoluteTime.now());
|
const now = AbsoluteTime.toPreciseTimestamp(AbsoluteTime.now());
|
||||||
const secretSeed = encodeCrock(getRandomBytes(32));
|
const secretSeed = encodeCrock(getRandomBytes(32));
|
||||||
const canonExchange = canonicalizeBaseUrl(args.exchangeBaseUrl);
|
const canonExchange = canonicalizeBaseUrl(args.exchangeBaseUrl);
|
||||||
const amount = args.amount;
|
const amount = args.amount;
|
||||||
@ -2200,7 +2201,7 @@ export async function internalCreateWithdrawalGroup(
|
|||||||
|
|
||||||
const exchange = await tx.exchanges.get(withdrawalGroup.exchangeBaseUrl);
|
const exchange = await tx.exchanges.get(withdrawalGroup.exchangeBaseUrl);
|
||||||
if (exchange) {
|
if (exchange) {
|
||||||
exchange.lastWithdrawal = TalerProtocolTimestamp.now();
|
exchange.lastWithdrawal = TalerPreciseTimestamp.now();
|
||||||
await tx.exchanges.put(exchange);
|
await tx.exchanges.put(exchange);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -577,8 +577,8 @@ export async function selectCandidates(
|
|||||||
]?.find((x) => {
|
]?.find((x) => {
|
||||||
return AbsoluteTime.isBetween(
|
return AbsoluteTime.isBetween(
|
||||||
AbsoluteTime.now(),
|
AbsoluteTime.now(),
|
||||||
AbsoluteTime.fromTimestamp(x.startStamp),
|
AbsoluteTime.fromProtocolTimestamp(x.startStamp),
|
||||||
AbsoluteTime.fromTimestamp(x.endStamp),
|
AbsoluteTime.fromProtocolTimestamp(x.endStamp),
|
||||||
);
|
);
|
||||||
})?.wireFee;
|
})?.wireFee;
|
||||||
if (wireFeeStr) {
|
if (wireFeeStr) {
|
||||||
|
@ -42,7 +42,7 @@ const VALUES: AmountString[] = Array.from({ length: 10 }).map(
|
|||||||
(undef, t) => `USD:${t}`,
|
(undef, t) => `USD:${t}`,
|
||||||
);
|
);
|
||||||
const TIMESTAMPS = Array.from({ length: 20 }).map((undef, t_s) => ({ t_s }));
|
const TIMESTAMPS = Array.from({ length: 20 }).map((undef, t_s) => ({ t_s }));
|
||||||
const ABS_TIME = TIMESTAMPS.map((m) => AbsoluteTime.fromTimestamp(m));
|
const ABS_TIME = TIMESTAMPS.map((m) => AbsoluteTime.fromProtocolTimestamp(m));
|
||||||
|
|
||||||
function normalize(
|
function normalize(
|
||||||
list: DenominationInfo[],
|
list: DenominationInfo[],
|
||||||
|
@ -326,7 +326,7 @@ export function createTimeline<Type extends object>(
|
|||||||
fee: Amounts.stringify(fee),
|
fee: Amounts.stringify(fee),
|
||||||
group,
|
group,
|
||||||
id,
|
id,
|
||||||
moment: AbsoluteTime.fromTimestamp(stampStart),
|
moment: AbsoluteTime.fromProtocolTimestamp(stampStart),
|
||||||
denom,
|
denom,
|
||||||
});
|
});
|
||||||
ps.push({
|
ps.push({
|
||||||
@ -334,7 +334,7 @@ export function createTimeline<Type extends object>(
|
|||||||
fee: Amounts.stringify(fee),
|
fee: Amounts.stringify(fee),
|
||||||
group,
|
group,
|
||||||
id,
|
id,
|
||||||
moment: AbsoluteTime.fromTimestamp(stampEnd),
|
moment: AbsoluteTime.fromProtocolTimestamp(stampEnd),
|
||||||
denom,
|
denom,
|
||||||
});
|
});
|
||||||
return ps;
|
return ps;
|
||||||
@ -457,8 +457,8 @@ export function isWithdrawableDenom(
|
|||||||
denomselAllowLate?: boolean,
|
denomselAllowLate?: boolean,
|
||||||
): boolean {
|
): boolean {
|
||||||
const now = AbsoluteTime.now();
|
const now = AbsoluteTime.now();
|
||||||
const start = AbsoluteTime.fromTimestamp(d.stampStart);
|
const start = AbsoluteTime.fromProtocolTimestamp(d.stampStart);
|
||||||
const withdrawExpire = AbsoluteTime.fromTimestamp(d.stampExpireWithdraw);
|
const withdrawExpire = AbsoluteTime.fromProtocolTimestamp(d.stampExpireWithdraw);
|
||||||
const started = AbsoluteTime.cmp(now, start) >= 0;
|
const started = AbsoluteTime.cmp(now, start) >= 0;
|
||||||
let lastPossibleWithdraw: AbsoluteTime;
|
let lastPossibleWithdraw: AbsoluteTime;
|
||||||
if (denomselAllowLate) {
|
if (denomselAllowLate) {
|
||||||
|
@ -136,7 +136,7 @@ export function PendingTransactionsView({
|
|||||||
</Typography>
|
</Typography>
|
||||||
-
|
-
|
||||||
<Time
|
<Time
|
||||||
timestamp={AbsoluteTime.fromTimestamp(t.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(t.timestamp)}
|
||||||
format="dd MMMM yyyy"
|
format="dd MMMM yyyy"
|
||||||
/>
|
/>
|
||||||
</Grid>
|
</Grid>
|
||||||
|
@ -179,7 +179,7 @@ export function HiddenView({ showHandler }: States.Hidden): VNode {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export function ShowView({ contractTerms, hideHandler }: States.Show): VNode {
|
export function ShowView({ contractTerms, hideHandler }: States.Show): VNode {
|
||||||
const createdAt = AbsoluteTime.fromTimestamp(contractTerms.timestamp);
|
const createdAt = AbsoluteTime.fromProtocolTimestamp(contractTerms.timestamp);
|
||||||
const { i18n } = useTranslationContext();
|
const { i18n } = useTranslationContext();
|
||||||
|
|
||||||
return (
|
return (
|
||||||
@ -266,7 +266,7 @@ export function ShowView({ contractTerms, hideHandler }: States.Show): VNode {
|
|||||||
<td>
|
<td>
|
||||||
{contractTerms.deliveryDate && (
|
{contractTerms.deliveryDate && (
|
||||||
<Time
|
<Time
|
||||||
timestamp={AbsoluteTime.fromTimestamp(
|
timestamp={AbsoluteTime.fromProtocolTimestamp(
|
||||||
contractTerms.deliveryDate,
|
contractTerms.deliveryDate,
|
||||||
)}
|
)}
|
||||||
format="dd MMMM yyyy, HH:mm"
|
format="dd MMMM yyyy, HH:mm"
|
||||||
@ -299,7 +299,7 @@ export function ShowView({ contractTerms, hideHandler }: States.Show): VNode {
|
|||||||
<td>
|
<td>
|
||||||
{contractTerms.timestamp && (
|
{contractTerms.timestamp && (
|
||||||
<Time
|
<Time
|
||||||
timestamp={AbsoluteTime.fromTimestamp(
|
timestamp={AbsoluteTime.fromProtocolTimestamp(
|
||||||
contractTerms.timestamp,
|
contractTerms.timestamp,
|
||||||
)}
|
)}
|
||||||
format="dd MMMM yyyy, HH:mm"
|
format="dd MMMM yyyy, HH:mm"
|
||||||
@ -314,7 +314,7 @@ export function ShowView({ contractTerms, hideHandler }: States.Show): VNode {
|
|||||||
<td>
|
<td>
|
||||||
{
|
{
|
||||||
<Time
|
<Time
|
||||||
timestamp={AbsoluteTime.fromTimestamp(
|
timestamp={AbsoluteTime.fromProtocolTimestamp(
|
||||||
contractTerms.refundDeadline,
|
contractTerms.refundDeadline,
|
||||||
)}
|
)}
|
||||||
format="dd MMMM yyyy, HH:mm"
|
format="dd MMMM yyyy, HH:mm"
|
||||||
@ -349,7 +349,7 @@ export function ShowView({ contractTerms, hideHandler }: States.Show): VNode {
|
|||||||
<td>
|
<td>
|
||||||
{
|
{
|
||||||
<Time
|
<Time
|
||||||
timestamp={AbsoluteTime.fromTimestamp(
|
timestamp={AbsoluteTime.fromProtocolTimestamp(
|
||||||
contractTerms.payDeadline,
|
contractTerms.payDeadline,
|
||||||
)}
|
)}
|
||||||
format="dd MMMM yyyy, HH:mm"
|
format="dd MMMM yyyy, HH:mm"
|
||||||
|
@ -53,7 +53,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
amount={tx.amountEffective}
|
amount={tx.amountEffective}
|
||||||
debitCreditIndicator={"credit"}
|
debitCreditIndicator={"credit"}
|
||||||
title={new URL(tx.exchangeBaseUrl).hostname}
|
title={new URL(tx.exchangeBaseUrl).hostname}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"W"}
|
iconPath={"W"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -76,7 +76,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
amount={tx.amountEffective}
|
amount={tx.amountEffective}
|
||||||
debitCreditIndicator={"credit"}
|
debitCreditIndicator={"credit"}
|
||||||
title={new URL(tx.exchangeBaseUrl).hostname}
|
title={new URL(tx.exchangeBaseUrl).hostname}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"I"}
|
iconPath={"I"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -100,7 +100,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
debitCreditIndicator={"debit"}
|
debitCreditIndicator={"debit"}
|
||||||
title={tx.info.merchant.name}
|
title={tx.info.merchant.name}
|
||||||
subtitle={tx.info.summary}
|
subtitle={tx.info.summary}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"P"}
|
iconPath={"P"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -121,7 +121,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
? tx.paymentInfo.merchant.name
|
? tx.paymentInfo.merchant.name
|
||||||
: "--unknown merchant--"
|
: "--unknown merchant--"
|
||||||
} //FIXME: DD37 wallet-core is not returning this value
|
} //FIXME: DD37 wallet-core is not returning this value
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"R"}
|
iconPath={"R"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -137,7 +137,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
amount={tx.amountEffective}
|
amount={tx.amountEffective}
|
||||||
debitCreditIndicator={"credit"}
|
debitCreditIndicator={"credit"}
|
||||||
title={new URL(tx.merchantBaseUrl).hostname}
|
title={new URL(tx.merchantBaseUrl).hostname}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"T"}
|
iconPath={"T"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -153,7 +153,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
amount={tx.amountEffective}
|
amount={tx.amountEffective}
|
||||||
debitCreditIndicator={"credit"}
|
debitCreditIndicator={"credit"}
|
||||||
title={"Refresh"}
|
title={"Refresh"}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"R"}
|
iconPath={"R"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -169,7 +169,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
amount={tx.amountEffective}
|
amount={tx.amountEffective}
|
||||||
debitCreditIndicator={"debit"}
|
debitCreditIndicator={"debit"}
|
||||||
title={tx.targetPaytoUri}
|
title={tx.targetPaytoUri}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"D"}
|
iconPath={"D"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -185,7 +185,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
amount={tx.amountEffective}
|
amount={tx.amountEffective}
|
||||||
debitCreditIndicator={"credit"}
|
debitCreditIndicator={"credit"}
|
||||||
title={tx.info.summary || "Invoice"}
|
title={tx.info.summary || "Invoice"}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"I"}
|
iconPath={"I"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -201,7 +201,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
amount={tx.amountEffective}
|
amount={tx.amountEffective}
|
||||||
debitCreditIndicator={"debit"}
|
debitCreditIndicator={"debit"}
|
||||||
title={tx.info.summary || "Invoice"}
|
title={tx.info.summary || "Invoice"}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"I"}
|
iconPath={"I"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -217,7 +217,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
amount={tx.amountEffective}
|
amount={tx.amountEffective}
|
||||||
debitCreditIndicator={"credit"}
|
debitCreditIndicator={"credit"}
|
||||||
title={tx.info.summary || "Transfer"}
|
title={tx.info.summary || "Transfer"}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"T"}
|
iconPath={"T"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
@ -233,7 +233,7 @@ export function TransactionItem(props: { tx: Transaction }): VNode {
|
|||||||
amount={tx.amountEffective}
|
amount={tx.amountEffective}
|
||||||
debitCreditIndicator={"debit"}
|
debitCreditIndicator={"debit"}
|
||||||
title={tx.info.summary || "Transfer"}
|
title={tx.info.summary || "Transfer"}
|
||||||
timestamp={AbsoluteTime.fromTimestamp(tx.timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(tx.timestamp)}
|
||||||
iconPath={"T"}
|
iconPath={"T"}
|
||||||
pending={
|
pending={
|
||||||
tx.txState.major === TransactionMajorState.Pending
|
tx.txState.major === TransactionMajorState.Pending
|
||||||
|
@ -123,7 +123,7 @@ export function useComponentState({
|
|||||||
raw,
|
raw,
|
||||||
goToWalletManualWithdraw,
|
goToWalletManualWithdraw,
|
||||||
summary,
|
summary,
|
||||||
expiration: expiration ? AbsoluteTime.fromTimestamp(expiration) : undefined,
|
expiration: expiration ? AbsoluteTime.fromProtocolTimestamp(expiration) : undefined,
|
||||||
};
|
};
|
||||||
|
|
||||||
if (!foundBalance) {
|
if (!foundBalance) {
|
||||||
|
@ -93,7 +93,7 @@ export function BaseView(state: SupportedStates): VNode {
|
|||||||
title={i18n.str`Valid until`}
|
title={i18n.str`Valid until`}
|
||||||
text={
|
text={
|
||||||
<Time
|
<Time
|
||||||
timestamp={AbsoluteTime.fromTimestamp(
|
timestamp={AbsoluteTime.fromProtocolTimestamp(
|
||||||
contractTerms.pay_deadline,
|
contractTerms.pay_deadline,
|
||||||
)}
|
)}
|
||||||
format="dd MMMM yyyy, HH:mm"
|
format="dd MMMM yyyy, HH:mm"
|
||||||
|
@ -86,7 +86,7 @@ export function useComponentState({
|
|||||||
onClick: pushAlertOnError(accept),
|
onClick: pushAlertOnError(accept),
|
||||||
},
|
},
|
||||||
summary,
|
summary,
|
||||||
expiration: expiration ? AbsoluteTime.fromTimestamp(expiration) : undefined,
|
expiration: expiration ? AbsoluteTime.fromProtocolTimestamp(expiration) : undefined,
|
||||||
cancel: {
|
cancel: {
|
||||||
onClick: pushAlertOnError(onClose),
|
onClick: pushAlertOnError(onClose),
|
||||||
},
|
},
|
||||||
|
@ -26,7 +26,7 @@ import {
|
|||||||
ShowRecoveryInfo,
|
ShowRecoveryInfo,
|
||||||
} from "./BackupPage.js";
|
} from "./BackupPage.js";
|
||||||
import * as tests from "@gnu-taler/web-util/testing";
|
import * as tests from "@gnu-taler/web-util/testing";
|
||||||
import { TalerProtocolTimestamp } from "@gnu-taler/taler-util";
|
import { TalerPreciseTimestamp, TalerProtocolTimestamp } from "@gnu-taler/taler-util";
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
title: "backup",
|
title: "backup",
|
||||||
@ -39,7 +39,7 @@ export const LotOfProviders = tests.createExample(TestedComponent, {
|
|||||||
name: "sync.demo",
|
name: "sync.demo",
|
||||||
syncProviderBaseUrl: "http://sync.taler:9967/",
|
syncProviderBaseUrl: "http://sync.taler:9967/",
|
||||||
lastSuccessfulBackupTimestamp:
|
lastSuccessfulBackupTimestamp:
|
||||||
TalerProtocolTimestamp.fromSeconds(1625063925),
|
TalerPreciseTimestamp.fromSeconds(1625063925),
|
||||||
paymentProposalIds: [
|
paymentProposalIds: [
|
||||||
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
||||||
],
|
],
|
||||||
@ -60,7 +60,7 @@ export const LotOfProviders = tests.createExample(TestedComponent, {
|
|||||||
name: "sync.demo",
|
name: "sync.demo",
|
||||||
syncProviderBaseUrl: "http://sync.taler:9967/",
|
syncProviderBaseUrl: "http://sync.taler:9967/",
|
||||||
lastSuccessfulBackupTimestamp:
|
lastSuccessfulBackupTimestamp:
|
||||||
TalerProtocolTimestamp.fromSeconds(1625063925),
|
TalerPreciseTimestamp.fromSeconds(1625063925),
|
||||||
paymentProposalIds: [
|
paymentProposalIds: [
|
||||||
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
||||||
],
|
],
|
||||||
@ -171,7 +171,7 @@ export const OneProvider = tests.createExample(TestedComponent, {
|
|||||||
name: "sync.demo",
|
name: "sync.demo",
|
||||||
syncProviderBaseUrl: "http://sync.taler:9967/",
|
syncProviderBaseUrl: "http://sync.taler:9967/",
|
||||||
lastSuccessfulBackupTimestamp:
|
lastSuccessfulBackupTimestamp:
|
||||||
TalerProtocolTimestamp.fromSeconds(1625063925),
|
TalerPreciseTimestamp.fromSeconds(1625063925),
|
||||||
paymentProposalIds: [
|
paymentProposalIds: [
|
||||||
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
||||||
],
|
],
|
||||||
|
@ -199,7 +199,7 @@ export function BackupView({
|
|||||||
status={provider.paymentStatus}
|
status={provider.paymentStatus}
|
||||||
timestamp={
|
timestamp={
|
||||||
provider.lastSuccessfulBackupTimestamp
|
provider.lastSuccessfulBackupTimestamp
|
||||||
? AbsoluteTime.fromTimestamp(
|
? AbsoluteTime.fromPreciseTimestamp(
|
||||||
provider.lastSuccessfulBackupTimestamp,
|
provider.lastSuccessfulBackupTimestamp,
|
||||||
)
|
)
|
||||||
: undefined
|
: undefined
|
||||||
|
@ -19,7 +19,7 @@
|
|||||||
* @author Sebastian Javier Marchano (sebasjm)
|
* @author Sebastian Javier Marchano (sebasjm)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { AbsoluteTime, TalerProtocolTimestamp } from "@gnu-taler/taler-util";
|
import { AbsoluteTime, TalerPreciseTimestamp, TalerProtocolTimestamp } from "@gnu-taler/taler-util";
|
||||||
import { ProviderPaymentType } from "@gnu-taler/taler-wallet-core";
|
import { ProviderPaymentType } from "@gnu-taler/taler-wallet-core";
|
||||||
import * as tests from "@gnu-taler/web-util/testing";
|
import * as tests from "@gnu-taler/web-util/testing";
|
||||||
import { ProviderView as TestedComponent } from "./ProviderDetailPage.js";
|
import { ProviderView as TestedComponent } from "./ProviderDetailPage.js";
|
||||||
@ -40,7 +40,7 @@ export const Active = tests.createExample(TestedComponent, {
|
|||||||
name: "sync.demo",
|
name: "sync.demo",
|
||||||
syncProviderBaseUrl: "http://sync.taler:9967/",
|
syncProviderBaseUrl: "http://sync.taler:9967/",
|
||||||
lastSuccessfulBackupTimestamp:
|
lastSuccessfulBackupTimestamp:
|
||||||
TalerProtocolTimestamp.fromSeconds(1625063925),
|
TalerPreciseTimestamp.fromSeconds(1625063925),
|
||||||
paymentProposalIds: [
|
paymentProposalIds: [
|
||||||
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
||||||
],
|
],
|
||||||
@ -64,9 +64,9 @@ export const ActiveErrorSync = tests.createExample(TestedComponent, {
|
|||||||
name: "sync.demo",
|
name: "sync.demo",
|
||||||
syncProviderBaseUrl: "http://sync.taler:9967/",
|
syncProviderBaseUrl: "http://sync.taler:9967/",
|
||||||
lastSuccessfulBackupTimestamp:
|
lastSuccessfulBackupTimestamp:
|
||||||
TalerProtocolTimestamp.fromSeconds(1625063925),
|
TalerPreciseTimestamp.fromSeconds(1625063925),
|
||||||
lastAttemptedBackupTimestamp:
|
lastAttemptedBackupTimestamp:
|
||||||
TalerProtocolTimestamp.fromSeconds(1625063925078),
|
TalerPreciseTimestamp.fromSeconds(1625063925078),
|
||||||
paymentProposalIds: [
|
paymentProposalIds: [
|
||||||
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
||||||
],
|
],
|
||||||
@ -99,7 +99,7 @@ export const ActiveBackupProblemUnreadable = tests.createExample(
|
|||||||
name: "sync.demo",
|
name: "sync.demo",
|
||||||
syncProviderBaseUrl: "http://sync.taler:9967/",
|
syncProviderBaseUrl: "http://sync.taler:9967/",
|
||||||
lastSuccessfulBackupTimestamp:
|
lastSuccessfulBackupTimestamp:
|
||||||
TalerProtocolTimestamp.fromSeconds(1625063925),
|
TalerPreciseTimestamp.fromSeconds(1625063925),
|
||||||
paymentProposalIds: [
|
paymentProposalIds: [
|
||||||
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
||||||
],
|
],
|
||||||
@ -127,7 +127,7 @@ export const ActiveBackupProblemDevice = tests.createExample(TestedComponent, {
|
|||||||
name: "sync.demo",
|
name: "sync.demo",
|
||||||
syncProviderBaseUrl: "http://sync.taler:9967/",
|
syncProviderBaseUrl: "http://sync.taler:9967/",
|
||||||
lastSuccessfulBackupTimestamp:
|
lastSuccessfulBackupTimestamp:
|
||||||
TalerProtocolTimestamp.fromSeconds(1625063925078),
|
TalerPreciseTimestamp.fromSeconds(1625063925078),
|
||||||
paymentProposalIds: [
|
paymentProposalIds: [
|
||||||
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
"43Q5WWRJPNS4SE9YKS54H9THDS94089EDGXW9EHBPN6E7M184XEG",
|
||||||
],
|
],
|
||||||
|
@ -151,7 +151,7 @@ export function ProviderView({
|
|||||||
}: ViewProps): VNode {
|
}: ViewProps): VNode {
|
||||||
const { i18n } = useTranslationContext();
|
const { i18n } = useTranslationContext();
|
||||||
const lb = info.lastSuccessfulBackupTimestamp
|
const lb = info.lastSuccessfulBackupTimestamp
|
||||||
? AbsoluteTime.fromTimestamp(info.lastSuccessfulBackupTimestamp)
|
? AbsoluteTime.fromPreciseTimestamp(info.lastSuccessfulBackupTimestamp)
|
||||||
: undefined;
|
: undefined;
|
||||||
const isPaid =
|
const isPaid =
|
||||||
info.paymentStatus.type === ProviderPaymentType.Paid ||
|
info.paymentStatus.type === ProviderPaymentType.Paid ||
|
||||||
|
@ -23,6 +23,7 @@ import {
|
|||||||
AbsoluteTime,
|
AbsoluteTime,
|
||||||
PaymentStatus,
|
PaymentStatus,
|
||||||
RefreshReason,
|
RefreshReason,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
TransactionCommon,
|
TransactionCommon,
|
||||||
TransactionDeposit,
|
TransactionDeposit,
|
||||||
@ -245,7 +246,7 @@ export const WithdrawFiveMinutesAgo = tests.createExample(
|
|||||||
() => ({
|
() => ({
|
||||||
transaction: {
|
transaction: {
|
||||||
...exampleData.withdraw,
|
...exampleData.withdraw,
|
||||||
timestamp: TalerProtocolTimestamp.fromSeconds(
|
timestamp: TalerPreciseTimestamp.fromSeconds(
|
||||||
new Date().getTime() / 1000 - 60 * 5,
|
new Date().getTime() / 1000 - 60 * 5,
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
@ -257,7 +258,7 @@ export const WithdrawFiveMinutesAgoAndPending = tests.createExample(
|
|||||||
() => ({
|
() => ({
|
||||||
transaction: {
|
transaction: {
|
||||||
...exampleData.withdraw,
|
...exampleData.withdraw,
|
||||||
timestamp: TalerProtocolTimestamp.fromSeconds(
|
timestamp: TalerPreciseTimestamp.fromSeconds(
|
||||||
new Date().getTime() / 1000 - 60 * 5,
|
new Date().getTime() / 1000 - 60 * 5,
|
||||||
),
|
),
|
||||||
txState: {
|
txState: {
|
||||||
|
@ -25,6 +25,7 @@ import {
|
|||||||
parsePaytoUri,
|
parsePaytoUri,
|
||||||
PaytoUri,
|
PaytoUri,
|
||||||
stringifyPaytoUri,
|
stringifyPaytoUri,
|
||||||
|
TalerPreciseTimestamp,
|
||||||
TalerProtocolTimestamp,
|
TalerProtocolTimestamp,
|
||||||
Transaction,
|
Transaction,
|
||||||
TransactionDeposit,
|
TransactionDeposit,
|
||||||
@ -585,7 +586,7 @@ export function TransactionView({
|
|||||||
on{" "}
|
on{" "}
|
||||||
{
|
{
|
||||||
<Time
|
<Time
|
||||||
timestamp={AbsoluteTime.fromTimestamp(
|
timestamp={AbsoluteTime.fromProtocolTimestamp(
|
||||||
r.timestamp,
|
r.timestamp,
|
||||||
)}
|
)}
|
||||||
format="dd MMMM yyyy"
|
format="dd MMMM yyyy"
|
||||||
@ -671,7 +672,7 @@ export function TransactionView({
|
|||||||
if (transaction.type === TransactionType.Deposit) {
|
if (transaction.type === TransactionType.Deposit) {
|
||||||
const payto = parsePaytoUri(transaction.targetPaytoUri);
|
const payto = parsePaytoUri(transaction.targetPaytoUri);
|
||||||
|
|
||||||
const wireTime = AbsoluteTime.fromTimestamp(
|
const wireTime = AbsoluteTime.fromProtocolTimestamp(
|
||||||
transaction.wireTransferDeadline,
|
transaction.wireTransferDeadline,
|
||||||
);
|
);
|
||||||
const shouldBeWired = wireTime.t_ms !== "never" && isPast(wireTime.t_ms);
|
const shouldBeWired = wireTime.t_ms !== "never" && isPast(wireTime.t_ms);
|
||||||
@ -1204,7 +1205,7 @@ function DeliveryDetails({
|
|||||||
</td>
|
</td>
|
||||||
<td>
|
<td>
|
||||||
<Time
|
<Time
|
||||||
timestamp={AbsoluteTime.fromTimestamp(date)}
|
timestamp={AbsoluteTime.fromProtocolTimestamp(date)}
|
||||||
format="dd MMMM yyyy, HH:mm"
|
format="dd MMMM yyyy, HH:mm"
|
||||||
/>
|
/>
|
||||||
</td>
|
</td>
|
||||||
@ -1768,7 +1769,7 @@ function Header({
|
|||||||
kind,
|
kind,
|
||||||
type,
|
type,
|
||||||
}: {
|
}: {
|
||||||
timestamp: TalerProtocolTimestamp;
|
timestamp: TalerPreciseTimestamp;
|
||||||
total: AmountJson;
|
total: AmountJson;
|
||||||
children: ComponentChildren;
|
children: ComponentChildren;
|
||||||
kind: Kind;
|
kind: Kind;
|
||||||
@ -1785,7 +1786,7 @@ function Header({
|
|||||||
<div>
|
<div>
|
||||||
<SubTitle>{children}</SubTitle>
|
<SubTitle>{children}</SubTitle>
|
||||||
<Time
|
<Time
|
||||||
timestamp={AbsoluteTime.fromTimestamp(timestamp)}
|
timestamp={AbsoluteTime.fromPreciseTimestamp(timestamp)}
|
||||||
format="dd MMMM yyyy, HH:mm"
|
format="dd MMMM yyyy, HH:mm"
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
Loading…
Reference in New Issue
Block a user