demo / frontend /src /components /BenchmarkEvaluation.jsx
tfrere's picture
add prerendered documents | update filename | refactor
ffa4ae8
raw
history blame
7.18 kB
import React, { useState, useEffect, useRef } from "react";
import { Box, Typography, CircularProgress, Alert, Paper } from "@mui/material";
import { useNavigate, useSearchParams } from "react-router-dom";
import API_CONFIG from "../config/api";
// Temps de simulation en millisecondes pour les documents précalculés
const SIMULATION_DURATION = 20000; // 20 secondes
// Intervalle de changement des messages pour les documents standards vs précalculés
const MESSAGE_CHANGE_INTERVAL = {
DEFAULT: 20000, // 20 secondes pour documents standards
PRECALCULATED: 5000, // 5 secondes pour documents précalculés
};
// Starting messages with their timing
const STARTING_MESSAGES = [
{ message: "Initializing evaluation environment...", progress: 0 },
{ message: "Starting evaluation process...", progress: 27 },
{ message: "Evaluating models...", progress: 54 },
{ message: "Storing evaluation results...", progress: 84 },
];
const BenchmarkEvaluation = ({ sessionId, isDefaultDocument, onComplete }) => {
const [searchParams] = useSearchParams();
const isDefault =
isDefaultDocument ||
["the-bitter-lesson", "hurricane-faq", "pokemon-guide"].includes(sessionId);
const [evaluationComplete, setEvaluationComplete] = useState(false);
const [error, setError] = useState(null);
const [elapsedTime, setElapsedTime] = useState(0);
const [startingMessageIndex, setStartingMessageIndex] = useState(0);
const timerIntervalRef = useRef(null);
const startTimeRef = useRef(null);
const startingMessageIntervalRef = useRef(null);
const pollingIntervalRef = useRef(null);
const simulationTimeoutRef = useRef(null);
const navigate = useNavigate();
// Add effect to handle automatic redirection when evaluation is complete
useEffect(() => {
if (evaluationComplete) {
navigate(`/evaluation-display?session=${sessionId}`);
}
}, [evaluationComplete, sessionId, navigate]);
// Add effect to handle starting messages
useEffect(() => {
startingMessageIntervalRef.current = setInterval(
() => {
setStartingMessageIndex((prev) => {
if (prev < STARTING_MESSAGES.length - 1) {
return prev + 1;
}
return prev;
});
},
isDefault
? MESSAGE_CHANGE_INTERVAL.PRECALCULATED
: MESSAGE_CHANGE_INTERVAL.DEFAULT
);
return () => {
if (startingMessageIntervalRef.current) {
clearInterval(startingMessageIntervalRef.current);
}
};
}, [isDefault]);
// Start evaluation when component mounts
useEffect(() => {
// Set start time
startTimeRef.current = Date.now();
// Start timer
timerIntervalRef.current = setInterval(() => {
const timeElapsed = Math.floor(
(Date.now() - startTimeRef.current) / 1000
);
setElapsedTime(timeElapsed);
}, 1000);
if (isDefault) {
simulateEvaluation();
} else {
startEvaluation();
}
// Clean up intervals on unmount
return () => {
if (pollingIntervalRef.current) {
clearInterval(pollingIntervalRef.current);
}
if (timerIntervalRef.current) {
clearInterval(timerIntervalRef.current);
}
if (simulationTimeoutRef.current) {
clearTimeout(simulationTimeoutRef.current);
}
};
}, [isDefault]);
// Simulate the evaluation process for pre-calculated documents
const simulateEvaluation = () => {
// Complete after 20 seconds
simulationTimeoutRef.current = setTimeout(() => {
setEvaluationComplete(true);
if (startingMessageIntervalRef.current) {
clearInterval(startingMessageIntervalRef.current);
}
setStartingMessageIndex(STARTING_MESSAGES.length - 1); // Set to last message
}, SIMULATION_DURATION);
};
// Format elapsed time as HH:MM:SS
const formatElapsedTime = () => {
const hours = Math.floor(elapsedTime / 3600);
const minutes = Math.floor((elapsedTime % 3600) / 60);
const seconds = elapsedTime % 60;
return [
hours.toString().padStart(2, "0"),
minutes.toString().padStart(2, "0"),
seconds.toString().padStart(2, "0"),
].join(":");
};
// Start benchmark evaluation
const startEvaluation = async () => {
if (!sessionId) {
setError("Missing session ID");
return;
}
try {
// Call API to start evaluation
const response = await fetch(
`${API_CONFIG.BASE_URL}/evaluate-benchmark`,
{
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify({
session_id: sessionId,
}),
}
);
const result = await response.json();
if (response.ok) {
// Set up polling to check completion
pollingIntervalRef.current = setInterval(async () => {
try {
const logsResponse = await fetch(
`${API_CONFIG.BASE_URL}/evaluation-logs/${sessionId}`
);
if (logsResponse.ok) {
const logsResult = await logsResponse.json();
if (logsResult.is_completed) {
setEvaluationComplete(true);
clearInterval(pollingIntervalRef.current);
}
}
} catch (error) {
console.log("Error polling logs:", error);
}
}, 2000);
} else {
setError(result.error || "Benchmark evaluation failed");
}
} catch (error) {
console.error("Error starting evaluation:", error);
setError("Error connecting to server");
}
};
return (
<Paper
elevation={3}
sx={{
p: 4,
mt: 3,
mb: 3,
display: "flex",
flexDirection: "column",
alignItems: "center",
justifyContent: "center",
minHeight: 200,
}}
>
{error ? (
<Alert severity="error" sx={{ width: "100%" }}>
{error}
</Alert>
) : (
<>
{evaluationComplete ? (
<Alert severity="success" sx={{ width: "100%", mb: 3 }}>
Evaluation completed successfully!
</Alert>
) : (
<>
<CircularProgress size={60} sx={{ mb: 2 }} />
<Typography variant="h6" component="div" gutterBottom>
Benchmark evaluation...
</Typography>
{/* Step progress indicator */}
<Typography variant="body1" color="text.secondary">
{`${STARTING_MESSAGES[startingMessageIndex].message} (${STARTING_MESSAGES[startingMessageIndex].progress}%)`}
</Typography>
{/* Timer display */}
<Box
sx={{
display: "flex",
alignItems: "center",
mt: 1,
color: "text.secondary",
opacity: 0.5,
}}
>
<Typography variant="body2">{formatElapsedTime()}</Typography>
</Box>
</>
)}
</>
)}
</Paper>
);
};
export default BenchmarkEvaluation;