debug fix
This commit is contained in:
@@ -137,13 +137,18 @@ export default function ResourceDebugOverlay({ enabled }: ResourceDebugOverlayPr
|
|||||||
});
|
});
|
||||||
|
|
||||||
if (response.ok) {
|
if (response.ok) {
|
||||||
const data = await response.json();
|
const responseData = await response.json();
|
||||||
|
// Extract data from unified API response format: {success: true, data: {...}}
|
||||||
|
const data = responseData?.data || responseData;
|
||||||
// Only log in debug mode to reduce console noise
|
// Only log in debug mode to reduce console noise
|
||||||
if (import.meta.env.DEV) {
|
if (import.meta.env.DEV) {
|
||||||
console.debug('Fetched metrics for request:', requestId, data);
|
console.debug('Fetched metrics for request:', requestId, data);
|
||||||
}
|
}
|
||||||
metricsRef.current = [...metricsRef.current, data];
|
// Validate data structure before adding
|
||||||
setMetrics([...metricsRef.current]);
|
if (data && typeof data === 'object' && data.request_id) {
|
||||||
|
metricsRef.current = [...metricsRef.current, data];
|
||||||
|
setMetrics([...metricsRef.current]);
|
||||||
|
}
|
||||||
} else if (response.status === 401) {
|
} else if (response.status === 401) {
|
||||||
// Token might be expired - try to refresh and retry once
|
// Token might be expired - try to refresh and retry once
|
||||||
try {
|
try {
|
||||||
@@ -160,9 +165,14 @@ export default function ResourceDebugOverlay({ enabled }: ResourceDebugOverlayPr
|
|||||||
credentials: 'include',
|
credentials: 'include',
|
||||||
});
|
});
|
||||||
if (retryResponse.ok) {
|
if (retryResponse.ok) {
|
||||||
const data = await retryResponse.json();
|
const responseData = await retryResponse.json();
|
||||||
metricsRef.current = [...metricsRef.current, data];
|
// Extract data from unified API response format: {success: true, data: {...}}
|
||||||
setMetrics([...metricsRef.current]);
|
const data = responseData?.data || responseData;
|
||||||
|
// Validate data structure before adding
|
||||||
|
if (data && typeof data === 'object' && data.request_id) {
|
||||||
|
metricsRef.current = [...metricsRef.current, data];
|
||||||
|
setMetrics([...metricsRef.current]);
|
||||||
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -191,14 +201,23 @@ export default function ResourceDebugOverlay({ enabled }: ResourceDebugOverlayPr
|
|||||||
// Calculate page load time
|
// Calculate page load time
|
||||||
const pageLoadTime = pageLoadStart ? performance.now() - pageLoadStart : null;
|
const pageLoadTime = pageLoadStart ? performance.now() - pageLoadStart : null;
|
||||||
|
|
||||||
// Calculate totals
|
// Calculate totals - with null safety checks
|
||||||
const totals = metrics.reduce((acc, m) => ({
|
const totals = metrics.reduce((acc, m) => {
|
||||||
elapsed_time_ms: acc.elapsed_time_ms + m.elapsed_time_ms,
|
// Safely access nested properties with defaults
|
||||||
cpu_total_ms: acc.cpu_total_ms + m.cpu.total_time_ms,
|
const elapsed = m?.elapsed_time_ms || 0;
|
||||||
memory_delta_mb: acc.memory_delta_mb + m.memory.delta_mb,
|
const cpuTotal = m?.cpu?.total_time_ms || 0;
|
||||||
io_read_mb: acc.io_read_mb + m.io.read_mb,
|
const memoryDelta = m?.memory?.delta_mb || 0;
|
||||||
io_write_mb: acc.io_write_mb + m.io.write_mb,
|
const ioRead = m?.io?.read_mb || 0;
|
||||||
}), {
|
const ioWrite = m?.io?.write_mb || 0;
|
||||||
|
|
||||||
|
return {
|
||||||
|
elapsed_time_ms: acc.elapsed_time_ms + elapsed,
|
||||||
|
cpu_total_ms: acc.cpu_total_ms + cpuTotal,
|
||||||
|
memory_delta_mb: acc.memory_delta_mb + memoryDelta,
|
||||||
|
io_read_mb: acc.io_read_mb + ioRead,
|
||||||
|
io_write_mb: acc.io_write_mb + ioWrite,
|
||||||
|
};
|
||||||
|
}, {
|
||||||
elapsed_time_ms: 0,
|
elapsed_time_ms: 0,
|
||||||
cpu_total_ms: 0,
|
cpu_total_ms: 0,
|
||||||
memory_delta_mb: 0,
|
memory_delta_mb: 0,
|
||||||
@@ -206,25 +225,31 @@ export default function ResourceDebugOverlay({ enabled }: ResourceDebugOverlayPr
|
|||||||
io_write_mb: 0,
|
io_write_mb: 0,
|
||||||
});
|
});
|
||||||
|
|
||||||
// Find the slowest request
|
// Find the slowest request - with null safety
|
||||||
const slowestRequest = metrics.length > 0
|
const slowestRequest = metrics.length > 0
|
||||||
? metrics.reduce((prev, current) =>
|
? metrics.reduce((prev, current) => {
|
||||||
(current.elapsed_time_ms > prev.elapsed_time_ms) ? current : prev
|
const prevTime = prev?.elapsed_time_ms || 0;
|
||||||
)
|
const currentTime = current?.elapsed_time_ms || 0;
|
||||||
|
return (currentTime > prevTime) ? current : prev;
|
||||||
|
})
|
||||||
: null;
|
: null;
|
||||||
|
|
||||||
// Find the request with highest CPU usage
|
// Find the request with highest CPU usage - with null safety
|
||||||
const highestCpuRequest = metrics.length > 0
|
const highestCpuRequest = metrics.length > 0
|
||||||
? metrics.reduce((prev, current) =>
|
? metrics.reduce((prev, current) => {
|
||||||
(current.cpu.total_time_ms > prev.cpu.total_time_ms) ? current : prev
|
const prevCpu = prev?.cpu?.total_time_ms || 0;
|
||||||
)
|
const currentCpu = current?.cpu?.total_time_ms || 0;
|
||||||
|
return (currentCpu > prevCpu) ? current : prev;
|
||||||
|
})
|
||||||
: null;
|
: null;
|
||||||
|
|
||||||
// Find the request with highest memory usage
|
// Find the request with highest memory usage - with null safety
|
||||||
const highestMemoryRequest = metrics.length > 0
|
const highestMemoryRequest = metrics.length > 0
|
||||||
? metrics.reduce((prev, current) =>
|
? metrics.reduce((prev, current) => {
|
||||||
(current.memory.delta_mb > prev.memory.delta_mb) ? current : prev
|
const prevMemory = prev?.memory?.delta_mb || 0;
|
||||||
)
|
const currentMemory = current?.memory?.delta_mb || 0;
|
||||||
|
return (currentMemory > prevMemory) ? current : prev;
|
||||||
|
})
|
||||||
: null;
|
: null;
|
||||||
|
|
||||||
if (!enabled || !isAdminOrDeveloper) return null;
|
if (!enabled || !isAdminOrDeveloper) return null;
|
||||||
@@ -272,23 +297,23 @@ export default function ResourceDebugOverlay({ enabled }: ResourceDebugOverlayPr
|
|||||||
<div className="text-xs space-y-2 text-yellow-800 dark:text-yellow-300">
|
<div className="text-xs space-y-2 text-yellow-800 dark:text-yellow-300">
|
||||||
{slowestRequest && (
|
{slowestRequest && (
|
||||||
<div>
|
<div>
|
||||||
<span className="font-semibold">Slowest Request:</span> {slowestRequest.method} {slowestRequest.path}
|
<span className="font-semibold">Slowest Request:</span> {slowestRequest.method || 'N/A'} {slowestRequest.path || 'N/A'}
|
||||||
<br />
|
<br />
|
||||||
<span className="ml-4">Time: {slowestRequest.elapsed_time_ms.toFixed(2)} ms</span>
|
<span className="ml-4">Time: {(slowestRequest.elapsed_time_ms || 0).toFixed(2)} ms</span>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
{highestCpuRequest && highestCpuRequest.cpu.total_time_ms > 100 && (
|
{highestCpuRequest && highestCpuRequest.cpu && (highestCpuRequest.cpu.total_time_ms || 0) > 100 && (
|
||||||
<div>
|
<div>
|
||||||
<span className="font-semibold">Highest CPU:</span> {highestCpuRequest.method} {highestCpuRequest.path}
|
<span className="font-semibold">Highest CPU:</span> {highestCpuRequest.method || 'N/A'} {highestCpuRequest.path || 'N/A'}
|
||||||
<br />
|
<br />
|
||||||
<span className="ml-4">CPU: {highestCpuRequest.cpu.total_time_ms.toFixed(2)} ms (System: {highestCpuRequest.cpu.system_percent.toFixed(1)}%)</span>
|
<span className="ml-4">CPU: {(highestCpuRequest.cpu.total_time_ms || 0).toFixed(2)} ms (System: {(highestCpuRequest.cpu.system_percent || 0).toFixed(1)}%)</span>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
{highestMemoryRequest && highestMemoryRequest.memory.delta_mb > 1 && (
|
{highestMemoryRequest && highestMemoryRequest.memory && (highestMemoryRequest.memory.delta_mb || 0) > 1 && (
|
||||||
<div>
|
<div>
|
||||||
<span className="font-semibold">Highest Memory:</span> {highestMemoryRequest.method} {highestMemoryRequest.path}
|
<span className="font-semibold">Highest Memory:</span> {highestMemoryRequest.method || 'N/A'} {highestMemoryRequest.path || 'N/A'}
|
||||||
<br />
|
<br />
|
||||||
<span className="ml-4">Memory: {highestMemoryRequest.memory.delta_mb > 0 ? '+' : ''}{highestMemoryRequest.memory.delta_mb.toFixed(2)} MB</span>
|
<span className="ml-4">Memory: {(highestMemoryRequest.memory.delta_mb || 0) > 0 ? '+' : ''}{(highestMemoryRequest.memory.delta_mb || 0).toFixed(2)} MB</span>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
@@ -321,9 +346,14 @@ export default function ResourceDebugOverlay({ enabled }: ResourceDebugOverlayPr
|
|||||||
</div>
|
</div>
|
||||||
) : (
|
) : (
|
||||||
metrics.map((m, idx) => {
|
metrics.map((m, idx) => {
|
||||||
const isSlow = m.elapsed_time_ms > 1000;
|
// Safely access properties with defaults
|
||||||
const isHighCpu = m.cpu.total_time_ms > 100;
|
const elapsedTime = m?.elapsed_time_ms || 0;
|
||||||
const isHighMemory = m.memory.delta_mb > 1;
|
const cpuTotal = m?.cpu?.total_time_ms || 0;
|
||||||
|
const memoryDelta = m?.memory?.delta_mb || 0;
|
||||||
|
|
||||||
|
const isSlow = elapsedTime > 1000;
|
||||||
|
const isHighCpu = cpuTotal > 100;
|
||||||
|
const isHighMemory = memoryDelta > 1;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div
|
<div
|
||||||
@@ -343,28 +373,32 @@ export default function ResourceDebugOverlay({ enabled }: ResourceDebugOverlayPr
|
|||||||
</div>
|
</div>
|
||||||
<div className="space-y-1 text-gray-700 dark:text-gray-300">
|
<div className="space-y-1 text-gray-700 dark:text-gray-300">
|
||||||
<div className={isSlow ? 'font-semibold text-red-700 dark:text-red-300' : ''}>
|
<div className={isSlow ? 'font-semibold text-red-700 dark:text-red-300' : ''}>
|
||||||
⏱️ Time: {m.elapsed_time_ms.toFixed(2)} ms
|
⏱️ Time: {elapsedTime.toFixed(2)} ms
|
||||||
</div>
|
</div>
|
||||||
<div className={isHighCpu ? 'font-semibold text-red-700 dark:text-red-300' : ''}>
|
{m?.cpu && (
|
||||||
🔥 CPU: {m.cpu.total_time_ms.toFixed(2)} ms
|
<div className={isHighCpu ? 'font-semibold text-red-700 dark:text-red-300' : ''}>
|
||||||
<span className="text-gray-500"> (User: {m.cpu.user_time_ms.toFixed(2)}ms, System: {m.cpu.system_time_ms.toFixed(2)}ms)</span>
|
🔥 CPU: {cpuTotal.toFixed(2)} ms
|
||||||
<br />
|
<span className="text-gray-500"> (User: {(m.cpu.user_time_ms || 0).toFixed(2)}ms, System: {(m.cpu.system_time_ms || 0).toFixed(2)}ms)</span>
|
||||||
<span className="ml-4 text-gray-500">System CPU: {m.cpu.system_percent.toFixed(1)}%</span>
|
<br />
|
||||||
</div>
|
<span className="ml-4 text-gray-500">System CPU: {(m.cpu.system_percent || 0).toFixed(1)}%</span>
|
||||||
<div className={isHighMemory ? 'font-semibold text-red-700 dark:text-red-300' : ''}>
|
|
||||||
💾 Memory: {m.memory.delta_mb > 0 ? '+' : ''}{m.memory.delta_mb.toFixed(2)} MB
|
|
||||||
<span className="text-gray-500"> (Final RSS: {m.memory.final_rss_mb.toFixed(2)} MB)</span>
|
|
||||||
<br />
|
|
||||||
<span className="ml-4 text-gray-500">System Memory: {m.memory.system_used_percent.toFixed(1)}%</span>
|
|
||||||
</div>
|
|
||||||
{m.io.read_mb > 0 && (
|
|
||||||
<div>
|
|
||||||
📖 I/O Read: {m.io.read_mb.toFixed(2)} MB ({m.io.read_bytes.toLocaleString()} bytes)
|
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
{m.io.write_mb > 0 && (
|
{m?.memory && (
|
||||||
|
<div className={isHighMemory ? 'font-semibold text-red-700 dark:text-red-300' : ''}>
|
||||||
|
💾 Memory: {memoryDelta > 0 ? '+' : ''}{memoryDelta.toFixed(2)} MB
|
||||||
|
<span className="text-gray-500"> (Final RSS: {(m.memory.final_rss_mb || 0).toFixed(2)} MB)</span>
|
||||||
|
<br />
|
||||||
|
<span className="ml-4 text-gray-500">System Memory: {(m.memory.system_used_percent || 0).toFixed(1)}%</span>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
{m?.io?.read_mb > 0 && (
|
||||||
<div>
|
<div>
|
||||||
📝 I/O Write: {m.io.write_mb.toFixed(2)} MB ({m.io.write_bytes.toLocaleString()} bytes)
|
📖 I/O Read: {m.io.read_mb.toFixed(2)} MB ({(m.io.read_bytes || 0).toLocaleString()} bytes)
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
{m?.io?.write_mb > 0 && (
|
||||||
|
<div>
|
||||||
|
📝 I/O Write: {m.io.write_mb.toFixed(2)} MB ({(m.io.write_bytes || 0).toLocaleString()} bytes)
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
Reference in New Issue
Block a user