fix(ui): привязать flow-аналитику к контексту запроса
This commit is contained in:
1 parent
94dd453b33
commit
24313340d5
5 files changed
+163
-82
No files matched your search
+12
-15
@@ -32,19 +32,15 @@ export function useFlowLive(opts: {
|
||||
excludeMesh?: boolean
|
||||
excludeOverlay?: boolean
|
||||
}): { sample: FlowAnalyticsDto | null; error: string | null } {
|
||||
const [sample, setSample] = useState<FlowAnalyticsDto | null>(null)
|
||||
const [error, setError] = useState<string | null>(null)
|
||||
const key = JSON.stringify([opts.enabled, opts.backendUrl, opts.range, opts.serverId, opts.userId, opts.iface, opts.dedup, opts.excludeMesh, opts.excludeOverlay])
|
||||
const [result, setResult] = useState<{ key: string; sample: FlowAnalyticsDto | null; error: string | null } | null>(null)
|
||||
|
||||
useEffect(() => {
|
||||
if (!opts.enabled) {
|
||||
setSample(null)
|
||||
setError(null)
|
||||
return
|
||||
}
|
||||
|
||||
if (!opts.enabled) return
|
||||
const ac = new AbortController()
|
||||
setSample(null)
|
||||
setError(null)
|
||||
const setError = (error: string) => {
|
||||
if (!ac.signal.aborted) setResult(previous => ({ key, sample: previous?.key === key ? previous.sample : null, error }))
|
||||
}
|
||||
const path = `/api/traffic/flow/live${flowQuery({
|
||||
range: opts.range,
|
||||
serverId: opts.serverId,
|
||||
@@ -65,6 +61,7 @@ export function useFlowLive(opts: {
|
||||
signal: ac.signal,
|
||||
credentials: "include",
|
||||
})
|
||||
if (ac.signal.aborted) return
|
||||
if (!res.ok || !res.body) {
|
||||
setError(`live HTTP ${res.status}`)
|
||||
return
|
||||
@@ -73,7 +70,8 @@ export function useFlowLive(opts: {
|
||||
const decoder = new TextDecoder()
|
||||
while (!ac.signal.aborted) {
|
||||
const { done, value } = await reader.read()
|
||||
if (done) break
|
||||
if (ac.signal.aborted) return
|
||||
if (done) { setError("Поток live завершён"); break }
|
||||
buf += decoder.decode(value, { stream: true })
|
||||
const parts = buf.split("\n\n")
|
||||
buf = parts.pop() ?? ""
|
||||
@@ -86,8 +84,7 @@ export function useFlowLive(opts: {
|
||||
setError("live sample пустой")
|
||||
continue
|
||||
}
|
||||
setSample(parsed)
|
||||
setError(parsed.degraded ? "Коллектор перегружен: упрощённая аналитика" : null)
|
||||
setResult({ key, sample: parsed, error: parsed.degraded ? "Коллектор перегружен: упрощённая аналитика" : null })
|
||||
} else if (ev.event === "error" && ev.data) {
|
||||
const parsed = JSON.parse(ev.data) as { error?: string }
|
||||
setError(parsed.error ?? "live error")
|
||||
@@ -101,7 +98,7 @@ export function useFlowLive(opts: {
|
||||
})()
|
||||
|
||||
return () => ac.abort()
|
||||
}, [opts.enabled, opts.backendUrl, opts.range, opts.serverId, opts.userId, opts.iface, opts.dedup, opts.excludeMesh, opts.excludeOverlay])
|
||||
}, [opts.enabled, opts.backendUrl, opts.range, opts.serverId, opts.userId, opts.iface, opts.dedup, opts.excludeMesh, opts.excludeOverlay, key])
|
||||
|
||||
return { sample, error }
|
||||
return result?.key === key ? { sample: result.sample, error: result.error } : { sample: null, error: null }
|
||||
}
|
||||
Reference in new issue
Block a user