From ee79f08e69a53760621d750c5bc93c2886c4abf3 Mon Sep 17 00:00:00 2001 From: Scott Idem Date: Thu, 5 Feb 2026 13:51:17 -0500 Subject: [PATCH] fix(idaa): resolve broken reactivity and sorting in Archive modules - Fixed ReferenceError in Archive Content liveQuery (variable name mismatch). - Corrected main Archive list sorting by removing incorrect .reverse() call. - Implemented robust in-memory sorting for Archive Content to handle mixed directions (Group DESC + Sort ASC). - Simplified dependency tracking in Svelte 5 derivations to prevent empty list flickers. --- src/lib/ae_posts/ae_posts__post_comment.ts | 2 +- src/routes/idaa/(idaa)/archives/+page.svelte | 2 +- .../(idaa)/archives/[archive_id]/+page.svelte | 107 +++++++++++------- 3 files changed, 70 insertions(+), 41 deletions(-) diff --git a/src/lib/ae_posts/ae_posts__post_comment.ts b/src/lib/ae_posts/ae_posts__post_comment.ts index 79fa1fbb..97d4546f 100644 --- a/src/lib/ae_posts/ae_posts__post_comment.ts +++ b/src/lib/ae_posts/ae_posts__post_comment.ts @@ -365,7 +365,7 @@ export async function process_ae_obj__post_comment_props({ sort_val }_${obj.updated_on ?? obj.created_on}`; obj.tmp_sort_2 = `${obj.group ?? ''}_${obj.priority ? '1' : '0'}_${ - (obj.sort ?? 0).toString().padStart(2, '0') + sort_val }_${obj.updated_on}_${obj.created_on}`; return obj; diff --git a/src/routes/idaa/(idaa)/archives/+page.svelte b/src/routes/idaa/(idaa)/archives/+page.svelte index f5172e04..66eeb717 100644 --- a/src/routes/idaa/(idaa)/archives/+page.svelte +++ b/src/routes/idaa/(idaa)/archives/+page.svelte @@ -44,7 +44,7 @@ .equals($slct.account_id) // .orderBy('updated_on') // .toArray() - .reverse() + // .reverse() // Removed reverse: sortBy('sort') already provides the correct 1, 2, 3... order .sortBy('sort'); // .sortBy('updated_on'); // .sortBy('updated_on, created_on'); diff --git a/src/routes/idaa/(idaa)/archives/[archive_id]/+page.svelte b/src/routes/idaa/(idaa)/archives/[archive_id]/+page.svelte index 628d2e5e..81e29895 100644 --- a/src/routes/idaa/(idaa)/archives/[archive_id]/+page.svelte +++ b/src/routes/idaa/(idaa)/archives/[archive_id]/+page.svelte @@ -89,51 +89,80 @@ }) ); - let lq__archive_content_obj_li = $derived( - liveQuery(async () => { - if (log_lvl) { - console.log(`$lq__archive_obj.cfg_json = `, $lq__archive_obj?.cfg_json); + // Reactive Archive Content list using Dexie LiveQuery + let lq__archive_content_obj_li = $derived.by(() => { + // SVELTE 5 REACTIVITY: Track the archive_id store synchronously + const archive_id = $idaa_slct.archive_id; + + return liveQuery(async () => { + if (!archive_id) return []; + + // Fetch the parent archive and its contents in parallel + // Dexie will automatically track these table accesses and re-run this query if they change. + const [parent_archive, results] = await Promise.all([ + db_archives.archive.get(archive_id), + db_archives.content.where('archive_id').equals(archive_id).toArray() + ]); + + if (!results || results.length === 0) { + if (log_lvl) console.log('lq__archive_content_obj_li: No content records found in cache.'); + return []; } - if ($lq__archive_obj?.cfg_json?.content_group_sort === 'DESC') { - // Really this should be called sort by original datetime with the newest being first - let results = await db_archives.content - .where('archive_id') - .equals($idaa_slct?.archive_id ?? '') // null or undefined does not reset things like '' does - // .reverse() // Incorrect usage: reverse() on collection is ignored by sortBy() - .sortBy('tmp_sort_2'); - // .sortBy('updated_on'); - return results.reverse(); - } else { - let results = await db_archives.content - .where('archive_id') - .equals($idaa_slct?.archive_id ?? '') // null or undefined does not reset things like '' does - // .reverse() - .sortBy('tmp_sort_1'); + // Determine sort mode from the parent archive configuration + const sort_mode = parent_archive?.cfg_json?.content_group_sort ?? 'ASC'; + const is_desc = sort_mode === 'DESC'; - if ( - $idaa_slct.archive_content_obj_li && - JSON.stringify($idaa_slct.archive_content_obj_li) !== JSON.stringify(results) - ) { - $idaa_slct.archive_content_obj_li = [...results]; - if (log_lvl) { - console.log( - `$idaa_slct.archive_content_obj_li = `, - $idaa_slct.archive_content_obj_li - ); - } + if (log_lvl) { + console.log(`lq__archive_content_obj_li: Sorting ${results.length} items using ${sort_mode} mode.`); + } + + // Apply multi-step in-memory sort to handle mixed directions (e.g. Group DESC + Sort ASC) + results.sort((a, b) => { + const groupA = a.group ?? ''; + const groupB = b.group ?? ''; + + if (is_desc) { + // MODE: Newest First (DESC) - Typically used for years or chronological groupings + + // 1. Group (DESC) - e.g. Year "2024" should appear before "2023" + if (groupA !== groupB) return groupB.localeCompare(groupA); + + // 2. Original Datetime (DESC) - Newer items within the same group first + const dateA = a.original_datetime ? new Date(a.original_datetime).getTime() : 0; + const dateB = b.original_datetime ? new Date(b.original_datetime).getTime() : 0; + if (dateA !== dateB) return dateB - dateA; } else { - if (log_lvl) { - console.log( - `Archive content object list has not changed for archive_id: ${$idaa_slct.archive_id}` - ); - } + // MODE: Standard (ASC) - Typically used for Parts, Chapters, or alphabetical groupings + + // 1. Group (ASC) - e.g. "Part 1" before "Part 2" + if (groupA !== groupB) return groupA.localeCompare(groupB); } - return results; - } - }) - ); + // 3. Priority (DESC) - Starred items always at the top of their subgroup + const prioA = a.priority ? 1 : 0; + const prioB = b.priority ? 1 : 0; + if (prioA !== prioB) return prioB - prioA; + + // 4. Sort (ASC) - Manual Sort order "1" should remain above "2" even in DESC mode + const sortA = a.sort ?? 0; + const sortB = b.sort ?? 0; + if (sortA !== sortB) return sortA - sortB; + + // 5. Fallback: Original Datetime ASC (if in Standard mode and manual sorts are equal) + if (!is_desc) { + const dateA = a.original_datetime ? new Date(a.original_datetime).getTime() : 0; + const dateB = b.original_datetime ? new Date(b.original_datetime).getTime() : 0; + if (dateA !== dateB) return dateA - dateB; + } + + // 6. Final fallback: Name ASC + return (a.name ?? '').localeCompare(b.name ?? ''); + }); + + return results; + }); + }); let lq__archive_content_obj = $derived( liveQuery(async () => {