diff --git a/src/components/BookmarkViews/CardView.tsx b/src/components/BookmarkViews/CardView.tsx index ae453d8b..7a8ada4a 100644 --- a/src/components/BookmarkViews/CardView.tsx +++ b/src/components/BookmarkViews/CardView.tsx @@ -112,10 +112,10 @@ export const CardView: React.FC = ({ title="Open event in search" onClick={(e) => e.stopPropagation()} > - {formatDate(bookmark.created_at || bookmark.listUpdatedAt || Math.floor(Date.now() / 1000))} + {formatDate(bookmark.created_at ?? bookmark.listUpdatedAt)} ) : ( - {formatDate(bookmark.created_at || bookmark.listUpdatedAt || Math.floor(Date.now() / 1000))} + {formatDate(bookmark.created_at ?? bookmark.listUpdatedAt)} )} diff --git a/src/components/BookmarkViews/CompactView.tsx b/src/components/BookmarkViews/CompactView.tsx index 1c778d8e..5667b9da 100644 --- a/src/components/BookmarkViews/CompactView.tsx +++ b/src/components/BookmarkViews/CompactView.tsx @@ -73,7 +73,7 @@ export const CompactView: React.FC = ({ {bookmark.id.slice(0, 12)}... )} - {formatDateCompact(bookmark.created_at || bookmark.listUpdatedAt || Math.floor(Date.now() / 1000))} + {formatDateCompact(bookmark.created_at ?? bookmark.listUpdatedAt)} {/* CTA removed */} diff --git a/src/components/BookmarkViews/LargeView.tsx b/src/components/BookmarkViews/LargeView.tsx index 9064acdf..6054b706 100644 --- a/src/components/BookmarkViews/LargeView.tsx +++ b/src/components/BookmarkViews/LargeView.tsx @@ -144,7 +144,7 @@ export const LargeView: React.FC = ({ className="bookmark-date-link" onClick={(e) => e.stopPropagation()} > - {formatDate(bookmark.created_at || bookmark.listUpdatedAt || Math.floor(Date.now() / 1000))} + {formatDate(bookmark.created_at ?? bookmark.listUpdatedAt)} )} diff --git a/src/components/Me.tsx b/src/components/Me.tsx index c4386c66..abaed6f9 100644 --- a/src/components/Me.tsx +++ b/src/components/Me.tsx @@ -419,7 +419,7 @@ const Me: React.FC = ({ const mockEvent = { id: item.id, pubkey: item.author || '', - created_at: item.readingTimestamp || Math.floor(Date.now() / 1000), + created_at: item.readingTimestamp || 0, kind: 1, tags: [] as string[][], content: item.title || item.url || 'Untitled', diff --git a/src/services/bookmarkController.ts b/src/services/bookmarkController.ts index fa2f0e87..71fded3a 100644 --- a/src/services/bookmarkController.ts +++ b/src/services/bookmarkController.ts @@ -343,7 +343,7 @@ class BookmarkController { ...b, tags: b.tags || [], content: b.content || this.externalEventStore?.getEvent(b.id)?.content || '', // Fallback to eventStore content - created_at: b.created_at || this.externalEventStore?.getEvent(b.id)?.created_at || b.created_at + created_at: (b.created_at ?? this.externalEventStore?.getEvent(b.id)?.created_at ?? null) })) const sortedBookmarks = enriched @@ -352,9 +352,10 @@ class BookmarkController { urlReferences: extractUrlsFromContent(b.content) })) .sort((a, b) => { - // Sort by listUpdatedAt (timestamp of bookmark list event = proxy for when bookmarked) - // Newest first (descending) - return (b.listUpdatedAt || 0) - (a.listUpdatedAt || 0) + // Sort by listUpdatedAt desc, nulls last + const aTs = a.listUpdatedAt ?? -Infinity + const bTs = b.listUpdatedAt ?? -Infinity + return bTs - aTs }) // DEBUG: Show top 5 sorted bookmarks @@ -370,7 +371,7 @@ class BookmarkController { title: `Bookmarks (${sortedBookmarks.length})`, url: '', content: latestContent, - created_at: newestCreatedAt || Math.floor(Date.now() / 1000), + created_at: newestCreatedAt || 0, tags: allTags, bookmarkCount: sortedBookmarks.length, eventReferences: allTags.filter((tag: string[]) => tag[0] === 'e').map((tag: string[]) => tag[1]), diff --git a/src/services/bookmarkHelpers.ts b/src/services/bookmarkHelpers.ts index fc12ac05..4dfd8e0a 100644 --- a/src/services/bookmarkHelpers.ts +++ b/src/services/bookmarkHelpers.ts @@ -81,7 +81,7 @@ export const processApplesauceBookmarks = ( allItems.push({ id: note.id, content: '', - created_at: note.created_at || 0, + created_at: note.created_at ?? null, pubkey: note.author || activeAccount.pubkey, kind: 1, // Short note kind tags: [], @@ -101,14 +101,14 @@ export const processApplesauceBookmarks = ( allItems.push({ id: coordinate, content: '', - created_at: article.created_at || 0, + created_at: article.created_at ?? null, pubkey: article.pubkey, kind: article.kind, // Usually 30023 for long-form articles tags: [], parsedContent: undefined, type: 'event' as const, isPrivate, - listUpdatedAt: parentCreatedAt || 0 + listUpdatedAt: parentCreatedAt ?? null }) }) } @@ -126,7 +126,7 @@ export const processApplesauceBookmarks = ( parsedContent: undefined, type: 'event' as const, isPrivate, - listUpdatedAt: parentCreatedAt || 0 + listUpdatedAt: parentCreatedAt ?? null }) }) } @@ -159,14 +159,14 @@ export const processApplesauceBookmarks = ( return { id: bookmark.id!, content: bookmark.content || '', - created_at: bookmark.created_at || 0, + created_at: bookmark.created_at ?? null, pubkey: activeAccount.pubkey, kind: bookmark.kind || 30001, tags: bookmark.tags || [], parsedContent: bookmark.content ? (getParsedContent(bookmark.content) as ParsedContent) : undefined, type: 'event' as const, isPrivate, - listUpdatedAt: parentCreatedAt || 0 + listUpdatedAt: parentCreatedAt ?? null } }) diff --git a/src/services/bookmarkProcessing.ts b/src/services/bookmarkProcessing.ts index e00ec433..ece801fb 100644 --- a/src/services/bookmarkProcessing.ts +++ b/src/services/bookmarkProcessing.ts @@ -136,7 +136,7 @@ export async function collectBookmarksFromEvents( publicItemsAll.push({ id: evt.id, content: evt.content || '', - created_at: evt.created_at || Math.floor(Date.now() / 1000), + created_at: evt.created_at ?? null, pubkey: evt.pubkey, kind: evt.kind, tags: evt.tags || [], @@ -148,7 +148,7 @@ export async function collectBookmarksFromEvents( setTitle, setDescription, setImage, - listUpdatedAt: evt.created_at || Math.floor(Date.now() / 1000) + listUpdatedAt: evt.created_at ?? null }) continue } diff --git a/src/services/readsService.ts b/src/services/readsService.ts index 18bbe948..2ccac036 100644 --- a/src/services/readsService.ts +++ b/src/services/readsService.ts @@ -76,7 +76,7 @@ export async function fetchAllReads( source: 'bookmark', type: 'article', readingProgress: 0, - readingTimestamp: bookmark.created_at + readingTimestamp: bookmark.created_at ?? undefined } readsMap.set(coordinate, item) if (onItem) emitItem(item) diff --git a/src/types/bookmarks.ts b/src/types/bookmarks.ts index 91531b86..311b6987 100644 --- a/src/types/bookmarks.ts +++ b/src/types/bookmarks.ts @@ -32,7 +32,7 @@ export interface IndividualBookmark { id: string content: string // Timestamp when the content was created (from the content event itself) - created_at: number + created_at: number | null pubkey: string kind: number tags: string[][] @@ -51,7 +51,7 @@ export interface IndividualBookmark { setImage?: string // Timestamp of the bookmark list event (best proxy for "when bookmarked") // Note: This is imperfect - it's when the list was last updated, not necessarily when this item was added - listUpdatedAt?: number + listUpdatedAt?: number | null } export interface ActiveAccount { diff --git a/src/utils/bookmarkUtils.tsx b/src/utils/bookmarkUtils.tsx index 50a47b59..833a87c4 100644 --- a/src/utils/bookmarkUtils.tsx +++ b/src/utils/bookmarkUtils.tsx @@ -4,16 +4,16 @@ import { ParsedContent, ParsedNode, IndividualBookmark } from '../types/bookmark import ResolvedMention from '../components/ResolvedMention' // Note: RichContent is imported by components directly to keep this file component-only for fast refresh -export const formatDate = (timestamp: number) => { - const safe = typeof timestamp === 'number' && isFinite(timestamp) && timestamp > 0 ? timestamp : Math.floor(Date.now() / 1000) - const date = new Date(safe * 1000) +export const formatDate = (timestamp: number | null | undefined) => { + if (!timestamp || !isFinite(timestamp) || timestamp <= 0) return '' + const date = new Date(timestamp * 1000) return formatDistanceToNow(date, { addSuffix: true }) } // Ultra-compact date format for tight spaces (e.g., compact view) -export const formatDateCompact = (timestamp: number) => { - const safe = typeof timestamp === 'number' && isFinite(timestamp) && timestamp > 0 ? timestamp : Math.floor(Date.now() / 1000) - const date = new Date(safe * 1000) +export const formatDateCompact = (timestamp: number | null | undefined) => { + if (!timestamp || !isFinite(timestamp) || timestamp <= 0) return '' + const date = new Date(timestamp * 1000) const now = new Date() const seconds = differenceInSeconds(now, date) @@ -89,7 +89,11 @@ export const renderParsedContent = (parsedContent: ParsedContent) => { export const sortIndividualBookmarks = (items: IndividualBookmark[]) => { return items .slice() - .sort((a, b) => (b.listUpdatedAt || 0) - (a.listUpdatedAt || 0)) + .sort((a, b) => { + const aTs = a.listUpdatedAt ?? -Infinity + const bTs = b.listUpdatedAt ?? -Infinity + return bTs - aTs + }) } export function groupIndividualBookmarks(items: IndividualBookmark[]) { @@ -124,10 +128,7 @@ export function hasContent(bookmark: IndividualBookmark): boolean { export function hasCreationDate(bookmark: IndividualBookmark): boolean { if (!bookmark.created_at) return false // If timestamp is missing or equals current time (within 1 second), consider it invalid - const now = Math.floor(Date.now() / 1000) - const createdAt = Math.floor(bookmark.created_at) - // If created_at is within 1 second of now, it's likely missing/placeholder - return Math.abs(createdAt - now) > 1 + return true } // Bookmark sets helpers (kind 30003) diff --git a/src/utils/linksFromBookmarks.ts b/src/utils/linksFromBookmarks.ts index 0cf58bd1..ec83c5e4 100644 --- a/src/utils/linksFromBookmarks.ts +++ b/src/utils/linksFromBookmarks.ts @@ -51,7 +51,7 @@ export function deriveLinksFromBookmarks(bookmarks: Bookmark[]): ReadItem[] { summary, image, readingProgress: 0, - readingTimestamp: bookmark.created_at + readingTimestamp: bookmark.created_at ?? undefined } linksMap.set(url, item) diff --git a/src/utils/readsFromBookmarks.ts b/src/utils/readsFromBookmarks.ts index 4bf35538..3a453350 100644 --- a/src/utils/readsFromBookmarks.ts +++ b/src/utils/readsFromBookmarks.ts @@ -49,7 +49,7 @@ export function deriveReadsFromBookmarks(bookmarks: Bookmark[]): ReadItem[] { source: 'bookmark', type: 'article', readingProgress: 0, - readingTimestamp: bookmark.created_at, + readingTimestamp: bookmark.created_at ?? undefined, title, summary, image,