From ed878f57f484a25fe52dd4e29f944d2c130effea Mon Sep 17 00:00:00 2001 From: Kieran Date: Thu, 20 Apr 2023 21:42:21 +0100 Subject: [PATCH] feat: offload zapper key loading to timer task --- packages/app/src/Cache/UserCache.ts | 68 +++++++++++++++++-------- packages/app/src/System/ProfileCache.ts | 2 +- 2 files changed, 47 insertions(+), 23 deletions(-) diff --git a/packages/app/src/Cache/UserCache.ts b/packages/app/src/Cache/UserCache.ts index cb14a2ccb..79bf2b4be 100644 --- a/packages/app/src/Cache/UserCache.ts +++ b/packages/app/src/Cache/UserCache.ts @@ -1,11 +1,14 @@ import FeedCache from "Cache/FeedCache"; import { db } from "Db"; -import { LNURL } from "LNURL"; import { MetadataCache } from "Cache"; +import { LNURL } from "LNURL"; class UserProfileCache extends FeedCache { + #zapperQueue: Array<{ pubkey: string; lnurl: string }> = []; + constructor() { super("UserCache", db.users); + this.#processZapperQueue(); } key(of: MetadataCache): string { @@ -63,38 +66,59 @@ class UserProfileCache extends FeedCache { })(); console.debug(`Updating ${m.pubkey} ${updateType}`, m); if (updateType !== "no_change") { - if (updateType !== "refresh_profile") { - // fetch zapper key - const lnurl = m.lud16 || m.lud06; - if (lnurl) { - try { - const svc = new LNURL(lnurl); - await svc.load(); - m.zapService = svc.zapperPubkey; - } catch { - console.warn("Failed to load LNURL for zapper pubkey", lnurl); - } - } - } - const writeProfile = { ...existing, ...m, }; - this.cache.set(m.pubkey, writeProfile); - if (db.ready) { - await db.users.put(writeProfile); - this.onTable.add(m.pubkey); + await this.#setItem(writeProfile); + if (updateType !== "refresh_profile") { + const lnurl = m.lud16 ?? m.lud06; + if (lnurl) { + this.#zapperQueue.push({ + pubkey: m.pubkey, + lnurl, + }); + } } - this.notifyChange([m.pubkey]); - return true; } - return false; + return updateType; } takeSnapshot(): MetadataCache[] { return []; } + + async #setItem(m: MetadataCache) { + this.cache.set(m.pubkey, m); + if (db.ready) { + await db.users.put(m); + this.onTable.add(m.pubkey); + } + this.notifyChange([m.pubkey]); + } + + async #processZapperQueue() { + while (this.#zapperQueue.length > 0) { + const i = this.#zapperQueue.shift(); + if (i) { + try { + const svc = new LNURL(i.lnurl); + await svc.load(); + const p = this.getFromCache(i.pubkey); + if (p) { + this.#setItem({ + ...p, + zapService: svc.zapperPubkey, + }); + } + } catch { + console.warn("Failed to load LNURL for zapper pubkey", i.lnurl); + } + } + } + + setTimeout(() => this.#processZapperQueue(), 1_000); + } } export const UserCache = new UserProfileCache(); diff --git a/packages/app/src/System/ProfileCache.ts b/packages/app/src/System/ProfileCache.ts index 820177223..bd5496387 100644 --- a/packages/app/src/System/ProfileCache.ts +++ b/packages/app/src/System/ProfileCache.ts @@ -65,7 +65,7 @@ class ProfileLoaderService { const q = System.Query(PubkeyReplaceableNoteStore, sub); // never release this callback, it will stop firing anyway after eose - const releaseOnEvent = q.onEvent(this.onProfileEvent); + const releaseOnEvent = q.onEvent(e => this.onProfileEvent(e)); const results = await new Promise>>(resolve => { let timeout: ReturnType | undefined = undefined; const release = q.hook(() => {