an atproto based link aggregator

Fix lint warnings and type errors

- Add eslint-disable comments for intentional @html usage (sanitized snippets)
- Add keys to each blocks in admin page
- Fix incomplete Omit<> type arguments in pending stores

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

+11 -7
+2
src/lib/components/PostTitle.svelte
··· 20 20 {#if url} 21 21 <a href={url} target="_blank" rel="noopener noreferrer" class={titleClass}> 22 22 {#if titleSnippet} 23 + <!-- eslint-disable-next-line svelte/no-at-html-tags -- Sanitized search snippet --> 23 24 {@html titleSnippet} 24 25 {:else} 25 26 {title} ··· 34 35 {:else} 35 36 <a href="/post/{rkey}" class={titleClass}> 36 37 {#if titleSnippet} 38 + <!-- eslint-disable-next-line svelte/no-at-html-tags -- Sanitized search snippet --> 37 39 {@html titleSnippet} 38 40 {:else} 39 41 {title}
+3 -3
src/routes/admin/+page.svelte
··· 56 56 <div 57 57 class="bg-white dark:bg-gray-800 rounded-lg shadow-sm border border-gray-200 dark:border-gray-700 divide-y divide-gray-200 dark:divide-gray-700" 58 58 > 59 - {#each data.recentReports as report} 59 + {#each data.recentReports as report (report.id)} 60 60 <div class="p-4"> 61 61 <div class="flex justify-between items-start gap-4"> 62 62 <div class="flex-1 min-w-0"> ··· 118 118 <div 119 119 class="bg-white dark:bg-gray-800 rounded-lg shadow-sm border border-gray-200 dark:border-gray-700 divide-y divide-gray-200 dark:divide-gray-700" 120 120 > 121 - {#each data.recentlyHiddenPosts as post} 121 + {#each data.recentlyHiddenPosts as post (post.uri)} 122 122 <div class="p-3 flex justify-between items-center gap-2"> 123 123 <div class="flex-1 min-w-0"> 124 124 <div class="text-sm font-medium text-gray-900 dark:text-gray-100 truncate"> ··· 154 154 <div 155 155 class="bg-white dark:bg-gray-800 rounded-lg shadow-sm border border-gray-200 dark:border-gray-700 divide-y divide-gray-200 dark:divide-gray-700" 156 156 > 157 - {#each data.recentlyHiddenComments as comment} 157 + {#each data.recentlyHiddenComments as comment (comment.uri)} 158 158 <div class="p-3 flex justify-between items-center gap-2"> 159 159 <div class="flex-1 min-w-0"> 160 160 <div class="text-sm text-gray-900 dark:text-gray-100 truncate">
+2 -2
src/routes/post/[rkey]/+page.svelte
··· 240 240 return async ({ update, result }) => { 241 241 if (result.type === 'success' && result.data?.success && result.data?.comment) { 242 242 // Add to pending store for optimistic UI 243 - pendingComments.add(result.data.comment as Omit); 243 + pendingComments.add(result.data.comment as Omit<PendingComment, 'submittedAt'>); 244 244 commentText = ''; 245 245 } else { 246 246 await update(); ··· 392 392 return async ({ update, result }) => { 393 393 if (result.type === 'success' && result.data?.success && result.data?.comment) { 394 394 // Add to pending store for optimistic UI 395 - pendingComments.add(result.data.comment as Omit); 395 + pendingComments.add(result.data.comment as Omit<PendingComment, 'submittedAt'>); 396 396 cancelReply(); 397 397 } else { 398 398 await update();
+2
src/routes/search/+page.svelte
··· 85 85 </div> 86 86 {#if post.textSnippet} 87 87 <p class="text-xs text-gray-600 dark:text-gray-400 mt-0.5"> 88 + <!-- eslint-disable-next-line svelte/no-at-html-tags -- Sanitized search snippet --> 88 89 {@html post.textSnippet} 89 90 </p> 90 91 {/if} ··· 136 137 </a> 137 138 </div> 138 139 <p class="text-gray-700 dark:text-gray-300"> 140 + <!-- eslint-disable-next-line svelte/no-at-html-tags -- Sanitized search snippet --> 139 141 {@html comment.textSnippet || comment.text} 140 142 </p> 141 143 </li>
+2 -2
src/routes/submit/+page.svelte
··· 1 1 <script lang="ts"> 2 2 import { enhance } from '$app/forms'; 3 3 import { goto } from '$app/navigation'; 4 - import { pendingPosts } from '$lib/stores/pending'; 4 + import { pendingPosts, type PendingPost } from '$lib/stores/pending'; 5 5 6 6 let { form } = $props(); 7 7 let submitting = $state(false); ··· 29 29 return async ({ result, update }) => { 30 30 if (result.type === 'success' && result.data?.success && result.data?.post) { 31 31 // Add to pending store for optimistic UI 32 - pendingPosts.add(result.data.post as Omit); 32 + pendingPosts.add(result.data.post as Omit<PendingPost, 'submittedAt'>); 33 33 // Navigate to home 34 34 await goto('/'); 35 35 } else {