- actions/jobs-page.ts: beide kolommen orderBy created_at desc - stores/jobs-store.ts: nieuwe actieve jobs unshift (top) i.p.v. push (bottom) Hiermee komen nieuw aangemaakte QUEUED/CLAIMED jobs bovenaan in de linker kolom, in plaats van onderaan waar ze buiten het scrollbare deel kunnen vallen. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
59 lines
1.6 KiB
TypeScript
59 lines
1.6 KiB
TypeScript
import { create } from 'zustand'
|
|
import { immer } from 'zustand/middleware/immer'
|
|
import type { JobWithRelations } from '@/actions/jobs-page'
|
|
|
|
type JobsState = {
|
|
activeJobs: JobWithRelations[]
|
|
doneJobs: JobWithRelations[]
|
|
selectedJobId: string | null
|
|
}
|
|
|
|
type JobsActions = {
|
|
initJobs(active: JobWithRelations[], done: JobWithRelations[]): void
|
|
setSelectedJobId(id: string | null): void
|
|
upsertJob(job: Partial<JobWithRelations> & { id: string; status: string }): void
|
|
}
|
|
|
|
export const useJobsStore = create<JobsState & JobsActions>()(
|
|
immer((set) => ({
|
|
activeJobs: [],
|
|
doneJobs: [],
|
|
selectedJobId: null,
|
|
|
|
initJobs(active, done) {
|
|
set((state) => {
|
|
state.activeJobs = active
|
|
state.doneJobs = done
|
|
})
|
|
},
|
|
|
|
setSelectedJobId(id) {
|
|
set((state) => {
|
|
state.selectedJobId = id
|
|
})
|
|
},
|
|
|
|
upsertJob(job) {
|
|
set((state) => {
|
|
const isDone = job.status.toUpperCase() === 'DONE'
|
|
|
|
if (isDone) {
|
|
state.activeJobs = state.activeJobs.filter(j => j.id !== job.id)
|
|
if (!state.doneJobs.find(j => j.id === job.id)) {
|
|
state.doneJobs.unshift(job as JobWithRelations)
|
|
if (state.doneJobs.length > 100) {
|
|
state.doneJobs = state.doneJobs.slice(0, 100)
|
|
}
|
|
}
|
|
} else {
|
|
const idx = state.activeJobs.findIndex(j => j.id === job.id)
|
|
if (idx !== -1) {
|
|
Object.assign(state.activeJobs[idx], job)
|
|
} else {
|
|
state.activeJobs.unshift(job as JobWithRelations)
|
|
}
|
|
}
|
|
})
|
|
},
|
|
}))
|
|
)
|