feat(ticket): add audit timeline and safeguard extension rejection

This commit is contained in:
2026-07-31 11:51:32 +05:30
parent 58098af0fe
commit 44d3be5d27
16 changed files with 394 additions and 210 deletions

View File

@@ -70,6 +70,14 @@ export function useTicketOverviewQuery(ticketId: string | undefined) {
});
}
export function useTicketTimelineQuery(ticketId: string | undefined) {
return useQuery({
queryKey: ticketKeys.timeline(ticketId ?? ''),
queryFn: () => ticketService.getTicketTimeline(ticketId as string),
enabled: Boolean(ticketId),
});
}
export function useTicketClassDetailQuery(
ticketId: string | undefined,
defectClass: string | undefined,
@@ -296,6 +304,9 @@ export function useReviewDetectionRepairProofMutation({
queryClient.invalidateQueries({
queryKey: ticketKeys.overview(ticketId),
}),
queryClient.invalidateQueries({
queryKey: ticketKeys.timeline(ticketId),
}),
queryClient.invalidateQueries({ queryKey: ticketKeys.lists() }),
]);
},
@@ -326,19 +337,6 @@ export function useAssignableTicketUsersQuery(enabled: boolean) {
});
}
function mergeTicketDetailResponse(
current: TicketDetail | undefined,
next: TicketDetail,
) {
if (!current) return next;
return {
...current,
...next,
history: next.history ?? current.history,
};
}
export function useAssignTicketMutation(ticketId: string, videoId?: string) {
const queryClient = useQueryClient();
@@ -351,6 +349,9 @@ export function useAssignTicketMutation(ticketId: string, videoId?: string) {
queryClient.invalidateQueries({
queryKey: ticketKeys.overview(ticketId),
}),
queryClient.invalidateQueries({
queryKey: ticketKeys.timeline(ticketId),
}),
queryClient.invalidateQueries({ queryKey: ticketKeys.lists() }),
...(videoId
? [
@@ -397,6 +398,9 @@ export function useRequestTicketExtensionMutation(
queryClient.invalidateQueries({
queryKey: ticketKeys.assignments(ticketId),
});
queryClient.invalidateQueries({
queryKey: ticketKeys.timeline(ticketId),
});
queryClient.invalidateQueries({ queryKey: ticketKeys.lists() });
},
onError: () => toast.error('Failed to request an extension'),
@@ -427,6 +431,9 @@ export function useReviewTicketExtensionMutation(
queryClient.invalidateQueries({
queryKey: ticketKeys.assignments(ticketId),
});
queryClient.invalidateQueries({
queryKey: ticketKeys.timeline(ticketId),
});
queryClient.invalidateQueries({ queryKey: ticketKeys.lists() });
},
onError: () => toast.error('Failed to review extension request'),
@@ -442,8 +449,11 @@ export function useCloseTicketMutation(ticketId: string) {
toast.success('Ticket closed');
queryClient.setQueryData<TicketDetail>(
ticketKeys.classDetail(ticketId, payload.defect_class),
(current) => mergeTicketDetailResponse(current, ticket),
ticket,
);
queryClient.invalidateQueries({
queryKey: ticketKeys.timeline(ticketId),
});
queryClient.invalidateQueries({ queryKey: ticketKeys.lists() });
},
onError: () => toast.error('Failed to close ticket'),