Use startTransition for delete refresh and fix filter updates

- DeleteItemButton now uses startTransition for router.refresh()
- ListDetailView re-applies filters when initialItems changes
- This ensures deleted items disappear after refresh completes
- Transition provides better React 18 concurrent rendering support
This commit is contained in:
2025-12-02 14:47:43 +00:00
parent 35e20fb16d
commit bd61aaa5b2
2 changed files with 15 additions and 12 deletions

View File

@@ -1,6 +1,6 @@
'use client' 'use client'
import { useState } from 'react' import { useState, useTransition } from 'react'
import { useRouter } from 'next/navigation' import { useRouter } from 'next/navigation'
import { deleteItem } from '@/lib/actions' import { deleteItem } from '@/lib/actions'
import { Trash2 } from 'lucide-react' import { Trash2 } from 'lucide-react'
@@ -17,18 +17,25 @@ export default function DeleteItemButton({ itemId, listId, variant = 'full' }: D
const { showToast } = useToast() const { showToast } = useToast()
const [isDeleting, setIsDeleting] = useState(false) const [isDeleting, setIsDeleting] = useState(false)
const [showConfirm, setShowConfirm] = useState(false) const [showConfirm, setShowConfirm] = useState(false)
const [isPending, startTransition] = useTransition()
const handleDelete = async (e: React.MouseEvent) => { const handleDelete = async (e: React.MouseEvent) => {
e.preventDefault() e.preventDefault()
e.stopPropagation() e.stopPropagation()
setIsDeleting(true) setIsDeleting(true)
try { try {
await deleteItem(itemId) await deleteItem(itemId)
showToast('Task deleted successfully', 'success') showToast('Task deleted successfully', 'success')
// Reset state immediately
setShowConfirm(false) setShowConfirm(false)
setIsDeleting(false) setIsDeleting(false)
// Always refresh to update the UI
router.refresh() // Use startTransition to refresh the route
startTransition(() => {
router.refresh()
})
} catch (error) { } catch (error) {
console.error('Error deleting item:', error) console.error('Error deleting item:', error)
showToast('Failed to delete task', 'error') showToast('Failed to delete task', 'error')
@@ -54,14 +61,14 @@ export default function DeleteItemButton({ itemId, listId, variant = 'full' }: D
<div className="flex items-center gap-2"> <div className="flex items-center gap-2">
<button <button
onClick={handleDelete} onClick={handleDelete}
disabled={isDeleting} disabled={isDeleting || isPending}
className="px-3 sm:px-4 py-2 sm:py-2.5 bg-red-500 hover:bg-red-600 active:bg-red-700 disabled:bg-red-300 text-white rounded-lg text-xs sm:text-sm transition-colors tap-target-sm font-medium" className="px-3 sm:px-4 py-2 sm:py-2.5 bg-red-500 hover:bg-red-600 active:bg-red-700 disabled:bg-red-300 text-white rounded-lg text-xs sm:text-sm transition-colors tap-target-sm font-medium"
> >
{isDeleting ? 'Deleting...' : 'Confirm'} {isDeleting || isPending ? 'Deleting...' : 'Confirm'}
</button> </button>
<button <button
onClick={handleCancel} onClick={handleCancel}
disabled={isDeleting} disabled={isDeleting || isPending}
className="px-3 sm:px-4 py-2 sm:py-2.5 bg-gray-200 hover:bg-gray-300 active:bg-gray-400 text-gray-700 rounded-lg text-xs sm:text-sm transition-colors tap-target-sm font-medium" className="px-3 sm:px-4 py-2 sm:py-2.5 bg-gray-200 hover:bg-gray-300 active:bg-gray-400 text-gray-700 rounded-lg text-xs sm:text-sm transition-colors tap-target-sm font-medium"
> >
Cancel Cancel

View File

@@ -144,14 +144,10 @@ export default function ListDetailView({
}) })
// Update filtered items when initialItems changes (after refresh) // Update filtered items when initialItems changes (after refresh)
useEffect(() => { // Re-apply filters to the new data
setFilteredItems(initialItems)
}, [initialItems])
// Apply initial filters on mount
useEffect(() => { useEffect(() => {
handleFiltersCallback(filters) handleFiltersCallback(filters)
}, []) // Only run on mount }, [initialItems, handleFiltersCallback, filters])
// Determine which items to display // Determine which items to display
const displayItems = debouncedQuery.trim() ? searchResults : filteredItems const displayItems = debouncedQuery.trim() ? searchResults : filteredItems