From d746ffaab32e301d6dfffc2df6c1fe408a6626be Mon Sep 17 00:00:00 2001 From: Chad Curtis Date: Sun, 22 Feb 2026 01:43:45 -0600 Subject: [PATCH] Use dedicated media:true search query for profile media tab and sidebar MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Replaces client-side media URL extraction with a dedicated NIP-50 search query (media:true) routed to relay.ditto.pub. This provides more accurate media detection using the relay's index-time analysis. Also fixes a bug where the Posts tab could flash 'No posts yet' when navigating to a profile — filterByTab was a dependency of the feedItems memo, so switching tabs could momentarily empty the list when the first page was mostly replies. --- src/components/ProfileRightSidebar.tsx | 20 ++++---- src/hooks/useProfileMedia.ts | 70 ++++++++++++++++++++++++++ src/pages/ProfilePage.tsx | 60 ++++++++++++++++------ 3 files changed, 125 insertions(+), 25 deletions(-) create mode 100644 src/hooks/useProfileMedia.ts diff --git a/src/components/ProfileRightSidebar.tsx b/src/components/ProfileRightSidebar.tsx index 0a4567c2..2010637a 100644 --- a/src/components/ProfileRightSidebar.tsx +++ b/src/components/ProfileRightSidebar.tsx @@ -19,12 +19,10 @@ interface ProfileField { interface ProfileRightSidebarProps { fields?: ProfileField[]; - /** Events from the profile feed — media is extracted client-side instead of a separate query. */ - events?: NostrEvent[]; - /** Whether the feed events are still loading. */ - eventsLoading?: boolean; - /** Whether all feed pages have been loaded (no more pages to fetch). */ - eventsComplete?: boolean; + /** Media events fetched via a dedicated search query (video:true image:true). */ + mediaEvents?: NostrEvent[]; + /** Whether the media events are still loading. */ + mediaLoading?: boolean; } interface MediaItem { @@ -243,13 +241,13 @@ function ProfileFieldRow({ field }: { field: ProfileField }) { ); } -export function ProfileRightSidebar({ fields, events, eventsLoading, eventsComplete }: ProfileRightSidebarProps) { +export function ProfileRightSidebar({ fields, mediaEvents, mediaLoading: mediaLoadingProp }: ProfileRightSidebarProps) { const { config } = useAppContext(); const media = useMemo( - () => extractMedia(events ?? [], config.contentWarningPolicy), - [events, config.contentWarningPolicy], + () => extractMedia(mediaEvents ?? [], config.contentWarningPolicy), + [mediaEvents, config.contentWarningPolicy], ); - const mediaLoading = (eventsLoading ?? false) || (media.length === 0 && !eventsComplete); + const mediaLoading = mediaLoadingProp ?? false; return (