From 152fc76bc09b9526d057961b487f062ee306ff3c Mon Sep 17 00:00:00 2001 From: Claude Date: Thu, 16 Jul 2026 00:03:38 +0000 Subject: [PATCH] fix(desktop): fetch account config (incl. blossom) from outbox relays MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The account-config bootstrap subscription only queried the default relays, so a user's Blossom server list (kind 10063) — published to their own write relays, not the defaults — was never fetched, and the UI fell back to the default server. NIP-65 relay lists hid the same gap because they're broadcast widely and also have a local backup. Add a subscription that re-fetches the account-config kinds (10002/10050/ 10007/10006/10063) from the user's NIP-65 outbox (write + untagged relays) once it's known, routing kind 10063 / 10002 through justConsumeMyOwnEvent like the bootstrap does. This matches mobile's outbox model: the user's own data comes from their write relays. Co-Authored-By: Claude Opus 4.8 Claude-Session: https://claude.ai/code/session_011dkzkEY6cUsRfqEb7giHi2 --- .../vitorpamplona/amethyst/desktop/Main.kt | 46 +++++++++++++++++++ 1 file changed, 46 insertions(+) diff --git a/desktopApp/src/jvmMain/kotlin/com/vitorpamplona/amethyst/desktop/Main.kt b/desktopApp/src/jvmMain/kotlin/com/vitorpamplona/amethyst/desktop/Main.kt index ec885a40b6..ff86c0acb4 100644 --- a/desktopApp/src/jvmMain/kotlin/com/vitorpamplona/amethyst/desktop/Main.kt +++ b/desktopApp/src/jvmMain/kotlin/com/vitorpamplona/amethyst/desktop/Main.kt @@ -1728,6 +1728,52 @@ fun MainContent( onDispose { relayManager.unsubscribe(bootstrapSubId) } } + // The bootstrap subscription above only reaches the default relays. A user's + // own account data — Blossom server list (kind 10063), DM/search/blocked + // relay lists — is published to their write relays, not the defaults, so it + // won't be found there. Re-fetch those kinds from the NIP-65 outbox + // (write + untagged relays) whenever it becomes known. + LaunchedEffect(iAccount) { + iAccount.nip65RelayList.outboxFlow.collect { outbox -> + if (outbox.isEmpty()) return@collect + relayManager.subscribe( + subId = "account-config-outbox", + filters = + listOf( + Filter( + kinds = + listOf( + AdvertisedRelayListEvent.KIND, + ChatMessageRelayListEvent.KIND, + SearchRelayListEvent.KIND, + BlockedRelayListEvent.KIND, + BlossomServersEvent.KIND, + ), + authors = listOf(account.pubKeyHex), + limit = 10, + ), + ), + relays = outbox, + listener = + object : SubscriptionListener { + override fun onEvent( + event: com.vitorpamplona.quartz.nip01Core.core.Event, + isLive: Boolean, + relay: NormalizedRelayUrl, + forFilters: List?, + ) { + if (event is AdvertisedRelayListEvent || event is BlossomServersEvent) { + scope.launch(Dispatchers.IO) { + localCache.justConsumeMyOwnEvent(event) + } + } + accountRelays.consumeIfRelevant(event) + } + }, + ) + } + } + // Subscribe to incoming DMs and process into chatroomList LaunchedEffect(account) { relayManager.connectedRelays.first { it.isNotEmpty() }