Fix first-login error, awards performance, filter animation, cache invalidation, and query fixes
- Guard onboarding tRPC queries with session hydration check (fixes UNAUTHORIZED on first login) - Defer expensive queries on awards page until UI elements are opened (dialog/tab) - Fix perPage: 500 exceeding backend Zod max of 100 on awards eligibility query - Add smooth open/close animation to project filters collapsible bar - Fix seeded user status from ACTIVE to INVITED in seed-candidatures.ts - Add router.refresh() cache invalidation across ~22 admin forms - Fix geographic analytics query to use programId instead of round.programId - Fix dashboard queries to scope by programId correctly - Fix project.listPool and round queries for projects outside round context - Add rounds page useEffect for state sync after mutations Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -132,6 +132,7 @@ function EditRoundContent({ roundId }: { roundId: string }) {
|
||||
// Mutations
|
||||
const saveAsTemplate = trpc.roundTemplate.create.useMutation({
|
||||
onSuccess: () => {
|
||||
utils.roundTemplate.list.invalidate()
|
||||
toast.success('Round saved as template')
|
||||
setSaveTemplateOpen(false)
|
||||
setTemplateName('')
|
||||
@@ -143,14 +144,18 @@ function EditRoundContent({ roundId }: { roundId: string }) {
|
||||
|
||||
const updateRound = trpc.round.update.useMutation({
|
||||
onSuccess: () => {
|
||||
// Invalidate cache to ensure fresh data
|
||||
utils.round.get.invalidate({ id: roundId })
|
||||
utils.round.list.invalidate()
|
||||
utils.program.list.invalidate({ includeRounds: true })
|
||||
router.push(`/admin/rounds/${roundId}`)
|
||||
},
|
||||
})
|
||||
|
||||
const updateEvaluationForm = trpc.round.updateEvaluationForm.useMutation()
|
||||
const updateEvaluationForm = trpc.round.updateEvaluationForm.useMutation({
|
||||
onSuccess: () => {
|
||||
utils.round.get.invalidate({ id: roundId })
|
||||
},
|
||||
})
|
||||
|
||||
// Initialize form with existing data
|
||||
const form = useForm<UpdateRoundForm>({
|
||||
|
||||
@@ -109,6 +109,8 @@ function RoundDetailContent({ roundId }: { roundId: string }) {
|
||||
const updateStatus = trpc.round.updateStatus.useMutation({
|
||||
onSuccess: () => {
|
||||
utils.round.get.invalidate({ id: roundId })
|
||||
utils.round.list.invalidate()
|
||||
utils.program.list.invalidate({ includeRounds: true })
|
||||
},
|
||||
})
|
||||
const deleteRound = trpc.round.delete.useMutation({
|
||||
@@ -125,7 +127,12 @@ function RoundDetailContent({ roundId }: { roundId: string }) {
|
||||
|
||||
// Filtering mutations
|
||||
const startJob = trpc.filtering.startJob.useMutation()
|
||||
const finalizeResults = trpc.filtering.finalizeResults.useMutation()
|
||||
const finalizeResults = trpc.filtering.finalizeResults.useMutation({
|
||||
onSuccess: () => {
|
||||
utils.round.get.invalidate({ id: roundId })
|
||||
utils.project.list.invalidate()
|
||||
},
|
||||
})
|
||||
|
||||
// Save as template
|
||||
const saveAsTemplate = trpc.roundTemplate.createFromRound.useMutation({
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
'use client'
|
||||
|
||||
import { Suspense, useState } from 'react'
|
||||
import { Suspense, useEffect, useState } from 'react'
|
||||
import Link from 'next/link'
|
||||
import { trpc } from '@/lib/trpc/client'
|
||||
import { toast } from 'sonner'
|
||||
@@ -119,6 +119,11 @@ function ProgramRounds({ program }: { program: any }) {
|
||||
const utils = trpc.useUtils()
|
||||
const [rounds, setRounds] = useState<RoundData[]>(program.rounds || [])
|
||||
|
||||
// Sync local state when query data refreshes (e.g. after status change)
|
||||
useEffect(() => {
|
||||
setRounds(program.rounds || [])
|
||||
}, [program.rounds])
|
||||
|
||||
const sensors = useSensors(
|
||||
useSensor(PointerSensor, {
|
||||
activationConstraint: {
|
||||
|
||||
Reference in New Issue
Block a user