**Motivations:** - Consigner l'état actuel du dépôt (cron, service-login-verify, website-skeleton, userwallet, docs). - Centraliser les modifications en attente. **Root causes:** - N/A (commit groupé). **Correctifs:** - N/A. **Evolutions:** - Cron quotidien restart services : script local sans SSH, systemd (bitcoin-signet, bitcoin, APIs, dashboard, userwallet, website-skeleton) + Docker (mempool, bitcoin-signet-instance). - Feature cron-restart-services-local : documentation et règle scripts locaux / pas d'SSH. - service-login-verify : module vérification login (buildAllowedPubkeys, verifyLoginProof, nonceCache). - website-skeleton : app iframe UserWallet, config, systemd unit. - userwallet : collectSignatures, relay. - docs : DOMAINS_AND_PORTS, README, WEBSITE_SKELETON ; features userwallet-contrat-login, timeouts-backoff, service-login-verify. **Pages affectées:** - data/restart-services-cron.sh, data/restart-services.log, data/sync-utxos.log - features/cron-restart-services-local.md, features/service-login-verify.md, features/userwallet-contrat-login-reste-a-faire.md, features/userwallet-timeouts-backoff.md - docs/DOMAINS_AND_PORTS.md, docs/README.md, docs/WEBSITE_SKELETON.md - configure-nginx-proxy.sh - service-login-verify/ (src, dist, node_modules) - userwallet/src/utils/collectSignatures.ts, userwallet/src/utils/relay.ts - website-skeleton/
38 lines
948 B
JavaScript
38 lines
948 B
JavaScript
/**
|
|
* In-memory nonce cache for anti-replay.
|
|
* TTL defines how long a nonce is considered "seen".
|
|
*/
|
|
export class NonceCache {
|
|
cache = new Map();
|
|
ttlMs;
|
|
constructor(ttlMs = 3600000) {
|
|
this.ttlMs = ttlMs;
|
|
}
|
|
/**
|
|
* Returns true if nonce is valid (not seen within TTL). Records nonce on success.
|
|
*/
|
|
isValid(nonce, timestamp) {
|
|
const now = Date.now();
|
|
const cached = this.cache.get(nonce);
|
|
if (cached !== undefined) {
|
|
if (now - cached < this.ttlMs) {
|
|
return false;
|
|
}
|
|
this.cache.delete(nonce);
|
|
}
|
|
this.cache.set(nonce, timestamp);
|
|
this.cleanup(now);
|
|
return true;
|
|
}
|
|
cleanup(now) {
|
|
for (const [n, ts] of this.cache.entries()) {
|
|
if (now - ts >= this.ttlMs) {
|
|
this.cache.delete(n);
|
|
}
|
|
}
|
|
}
|
|
clear() {
|
|
this.cache.clear();
|
|
}
|
|
}
|