efc72b720e
- scoreCalculator: apply dataQuality/confidence modifiers to finalScore (were computed but hardcoded to 0) - authService: call queryClient.clear() on logout to prevent cross-session data leakage - queryClient: extract to src/lib/queryClient.ts singleton so services can access it without circular imports - matchSyncService: new service layer owns match-generation logic; MockupNeedProvider no longer imports other providers directly - hooks (11 files): add onError + German toast feedback to every useMutation Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
87 lines
2.9 KiB
TypeScript
87 lines
2.9 KiB
TypeScript
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query'
|
|
import { marketIntelligenceService } from '../services/marketIntelligenceService'
|
|
import { reviewService } from '../services/reviewService'
|
|
import type { MarketSignalFilters, SignalProcessingStatus } from '../domain/marketSignal'
|
|
import { useToastStore } from '../stores/toastStore'
|
|
|
|
const STALE_SIGNALS = 30_000
|
|
|
|
export function useMarketSignals(filters?: MarketSignalFilters) {
|
|
return useQuery({
|
|
queryKey: ['market-signals', filters ?? {}],
|
|
queryFn: () => marketIntelligenceService.getSignals(filters),
|
|
staleTime: STALE_SIGNALS,
|
|
select: (res) => res.data ?? [],
|
|
})
|
|
}
|
|
|
|
export function useMarketSignalDetail(id: string | null) {
|
|
return useQuery({
|
|
queryKey: ['market-signal', id],
|
|
queryFn: () => marketIntelligenceService.getSignalDetail(id!),
|
|
enabled: id !== null,
|
|
staleTime: STALE_SIGNALS,
|
|
select: (res) => res.data ?? null,
|
|
})
|
|
}
|
|
|
|
export function useUpdateSignalStatus() {
|
|
const queryClient = useQueryClient()
|
|
return useMutation({
|
|
mutationFn: ({ id, status }: { id: string; status: SignalProcessingStatus }) =>
|
|
marketIntelligenceService.updateSignalStatus(id, status),
|
|
onSuccess: () => {
|
|
queryClient.invalidateQueries({ queryKey: ['market-signals'] })
|
|
queryClient.invalidateQueries({ queryKey: ['market-signal'] })
|
|
},
|
|
onError: () => {
|
|
useToastStore.getState().showToast('Signal-Status konnte nicht aktualisiert werden.', 'error')
|
|
},
|
|
})
|
|
}
|
|
|
|
export function useConvertToFutureSignal() {
|
|
const queryClient = useQueryClient()
|
|
return useMutation({
|
|
mutationFn: (id: string) => marketIntelligenceService.convertToFutureSignal(id),
|
|
onSuccess: () => {
|
|
queryClient.invalidateQueries({ queryKey: ['market-signals'] })
|
|
queryClient.invalidateQueries({ queryKey: ['market-signal'] })
|
|
},
|
|
onError: () => {
|
|
useToastStore.getState().showToast('Konvertierung zu Future Signal fehlgeschlagen.', 'error')
|
|
},
|
|
})
|
|
}
|
|
|
|
export function useLinkSignalToEntity() {
|
|
const queryClient = useQueryClient()
|
|
return useMutation({
|
|
mutationFn: ({
|
|
id,
|
|
entityType,
|
|
entityId,
|
|
}: {
|
|
id: string
|
|
entityType: 'property' | 'need'
|
|
entityId: string
|
|
}) => marketIntelligenceService.linkSignalToEntity(id, entityType, entityId),
|
|
onSuccess: () => {
|
|
queryClient.invalidateQueries({ queryKey: ['market-signals'] })
|
|
queryClient.invalidateQueries({ queryKey: ['market-signal'] })
|
|
},
|
|
onError: () => {
|
|
useToastStore.getState().showToast('Signal konnte nicht verknüpft werden.', 'error')
|
|
},
|
|
})
|
|
}
|
|
|
|
export function useCreateReviewTask() {
|
|
return useMutation({
|
|
mutationFn: (signalId: string) => reviewService.createReviewTask(signalId),
|
|
onError: () => {
|
|
useToastStore.getState().showToast('Überprüfungsaufgabe konnte nicht erstellt werden.', 'error')
|
|
},
|
|
})
|
|
}
|