mirror of
https://github.com/bluewave-labs/Checkmate.git
synced 2025-12-22 10:47:08 +00:00
Ajout de l'interface pour selectionner des disques et modifications du coté serveur pour la sauvegarde
This commit is contained in:
@@ -0,0 +1,92 @@
|
||||
import React from "react";
|
||||
import ConfigBox from "@/Components/v1/ConfigBox/index.jsx";
|
||||
import { Box, Stack, Typography } from "@mui/material";
|
||||
import Checkbox from "@/Components/v1/Inputs/Checkbox/index.jsx";
|
||||
import { useTheme } from "@emotion/react";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import PropTypes from "prop-types";
|
||||
|
||||
const DiskSelection = ({ availableDisks, selectedDisks, onChange }) => {
|
||||
const theme = useTheme();
|
||||
const { t } = useTranslation();
|
||||
|
||||
const handleDiskChange = (event, mountpoint) => {
|
||||
// Le composant Checkbox personnalisé renvoie l'event natif
|
||||
const isChecked = event.target.checked;
|
||||
let newSelectedDisks = [];
|
||||
|
||||
if (isChecked) {
|
||||
newSelectedDisks = [...selectedDisks, mountpoint];
|
||||
} else {
|
||||
newSelectedDisks = selectedDisks.filter((disk) => disk !== mountpoint);
|
||||
}
|
||||
|
||||
onChange(newSelectedDisks);
|
||||
};
|
||||
|
||||
return (
|
||||
<ConfigBox>
|
||||
<Box>
|
||||
<Typography component="h2" variant="h2">
|
||||
{t("v1.infrastructure.disk_selection_title")}
|
||||
</Typography>
|
||||
<Typography component="p">
|
||||
{t("v1.infrastructure.disk_selection_description")}
|
||||
</Typography>
|
||||
</Box>
|
||||
|
||||
<Stack gap={theme.spacing(6)}>
|
||||
{(!availableDisks || availableDisks.length === 0) ? (
|
||||
<Typography
|
||||
variant="body2"
|
||||
sx={{ fontStyle: 'italic', opacity: 0.8 }}
|
||||
>
|
||||
{t("v1.infrastructure.disk_selection_info")}
|
||||
</Typography>
|
||||
) : (
|
||||
availableDisks.map((disk) => (
|
||||
/* Reproduction exacte de la structure de CustomThreshold
|
||||
pour garantir l'alignement parfait avec la section Alertes
|
||||
*/
|
||||
<Stack
|
||||
key={disk.mountpoint}
|
||||
direction={{ sm: "column", md: "row" }}
|
||||
spacing={theme.spacing(2)}
|
||||
>
|
||||
<Box
|
||||
sx={{
|
||||
// Mêmes largeurs que dans CustomThreshold pour aligner les labels
|
||||
width: { md: "45%", lg: "25%", xl: "20%" },
|
||||
}}
|
||||
justifyContent="flex-start"
|
||||
>
|
||||
<Checkbox
|
||||
id={`disk-${disk.mountpoint}`}
|
||||
name={disk.mountpoint}
|
||||
label={disk.mountpoint}
|
||||
isChecked={selectedDisks.includes(disk.mountpoint)}
|
||||
onChange={(e) => handleDiskChange(e, disk.mountpoint)}
|
||||
/>
|
||||
</Box>
|
||||
{/* Pas de deuxième Stack ici car nous n'avons pas besoin
|
||||
du champ TextInput pour la sélection simple
|
||||
*/}
|
||||
</Stack>
|
||||
))
|
||||
)}
|
||||
</Stack>
|
||||
</ConfigBox>
|
||||
);
|
||||
};
|
||||
|
||||
DiskSelection.propTypes = {
|
||||
availableDisks: PropTypes.arrayOf(
|
||||
PropTypes.shape({
|
||||
mountpoint: PropTypes.string.isRequired,
|
||||
})
|
||||
),
|
||||
selectedDisks: PropTypes.arrayOf(PropTypes.string).isRequired,
|
||||
onChange: PropTypes.func.isRequired,
|
||||
};
|
||||
|
||||
export default DiskSelection;
|
||||
@@ -17,6 +17,7 @@ const useInfrastructureMonitorForm = () => {
|
||||
temperature: false,
|
||||
usage_temperature: "",
|
||||
secret: "",
|
||||
selectedDisks: [],
|
||||
});
|
||||
|
||||
const onChangeForm = (name, value) => {
|
||||
@@ -48,6 +49,7 @@ const useInfrastructureMonitorForm = () => {
|
||||
temperature: gt.temperature !== undefined,
|
||||
usage_temperature: gt.temperature !== undefined ? gt.temperature.toString() : "",
|
||||
secret: "",
|
||||
selectedDisks: [],
|
||||
}));
|
||||
}, []);
|
||||
|
||||
@@ -81,6 +83,7 @@ const useInfrastructureMonitorForm = () => {
|
||||
? (thresholds.usage_temperature * 100).toString()
|
||||
: "",
|
||||
secret: monitor.secret || "",
|
||||
selectedDisks: monitor.selectedDisks || [],
|
||||
}));
|
||||
}, []);
|
||||
return {
|
||||
|
||||
@@ -10,9 +10,11 @@ import { HttpAdornment } from "@/Components/v1/Inputs/TextInput/Adornments/index
|
||||
import MonitorStatusHeader from "./Components/MonitorStatusHeader.jsx";
|
||||
import MonitorActionButtons from "./Components/MonitorActionButtons.jsx";
|
||||
import CustomAlertsSection from "./Components/CustomAlertsSection.jsx";
|
||||
import DiskSelection from "./Components/DiskSelection.jsx";
|
||||
// Utils
|
||||
import NotificationsConfig from "@/Components/v1/NotificationConfig/index.jsx";
|
||||
import { useGetNotificationsByTeamId } from "../../../../Hooks/v1/useNotifications.js";
|
||||
import NetworkService from "../../../../Utils/NetworkService";
|
||||
import { useParams } from "react-router-dom";
|
||||
import { useState, useEffect } from "react";
|
||||
import { useTheme } from "@emotion/react";
|
||||
@@ -37,6 +39,7 @@ const CreateInfrastructureMonitor = () => {
|
||||
// State
|
||||
const [https, setHttps] = useState(false);
|
||||
const [updateTrigger, setUpdateTrigger] = useState(false);
|
||||
const [availableDisks, setAvailableDisks] = useState([]);
|
||||
|
||||
// Fetch monitor details if editing
|
||||
const [monitor, isLoading] = useFetchHardwareMonitorById({
|
||||
@@ -85,6 +88,24 @@ const CreateInfrastructureMonitor = () => {
|
||||
} else if (monitor) {
|
||||
setHttps(monitor.url.startsWith("https"));
|
||||
initializeInfrastructureMonitorForUpdate(monitor);
|
||||
const fetchLastCheck = async () => {
|
||||
try {
|
||||
const params = {
|
||||
dateRange: "recent",
|
||||
limit: 1,
|
||||
sortOrder: "desc",
|
||||
};
|
||||
// On utilise NetworkService directement
|
||||
const response = await NetworkService.get(`/api/v1/checks/${monitorId}`, { params });
|
||||
const disks = response?.data?.checks?.[0]?.payload?.disks || [];
|
||||
setAvailableDisks(disks);
|
||||
} catch (error) {
|
||||
console.error("Erreur pendant la récupération des disques:", error);
|
||||
setAvailableDisks([]); // En cas d'erreur, on met un tableau vide
|
||||
}
|
||||
};
|
||||
|
||||
fetchLastCheck();
|
||||
}
|
||||
}, [
|
||||
isCreate,
|
||||
@@ -133,6 +154,15 @@ const CreateInfrastructureMonitor = () => {
|
||||
isPausing ||
|
||||
notificationsAreLoading;
|
||||
|
||||
// --- AJOUT TEMPORAIRE : Fausses données ---
|
||||
const MOCK_DISKS = [
|
||||
{ mountpoint: "C:" },
|
||||
{ mountpoint: "D:" },
|
||||
{ mountpoint: "/mnt/data" },
|
||||
{ mountpoint: "/var/lib/docker" }
|
||||
];
|
||||
// -----------------------------------------
|
||||
|
||||
return (
|
||||
<Box className="create-infrastructure-monitor">
|
||||
<Breadcrumbs list={CRUMBS} />
|
||||
@@ -327,6 +357,17 @@ const CreateInfrastructureMonitor = () => {
|
||||
infrastructureMonitor={infrastructureMonitor}
|
||||
handleCheckboxChange={handleCheckboxChange}
|
||||
/>
|
||||
|
||||
{monitorId && (
|
||||
<DiskSelection
|
||||
availableDisks={availableDisks}
|
||||
selectedDisks={infrastructureMonitor.selectedDisks}
|
||||
onChange={(newSelectedDisks) =>
|
||||
onChangeForm("selectedDisks", newSelectedDisks)
|
||||
}
|
||||
/>
|
||||
)}
|
||||
|
||||
<ConfigBox>
|
||||
<Box>
|
||||
<Typography
|
||||
|
||||
@@ -1136,5 +1136,12 @@
|
||||
"packetsReceivedRate": "Packets Received Rate",
|
||||
"packetsSent": "Packets Sent",
|
||||
"rate": "Rate",
|
||||
"selectInterface": "Select Interface"
|
||||
"selectInterface": "Select Interface",
|
||||
"v1": {
|
||||
"infrastructure": {
|
||||
"disk_selection_title": "Disk Selection",
|
||||
"disk_selection_info": "No disk detected for the moment.",
|
||||
"disk_selection_description": "Select the specific disks you want to monitor."
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -12,6 +12,9 @@ export default defineConfig(({}) => {
|
||||
return {
|
||||
base: "/",
|
||||
plugins: [svgr(), react()],
|
||||
server: {
|
||||
host: true,
|
||||
},
|
||||
resolve: {
|
||||
alias: {
|
||||
"@": path.resolve(__dirname, "src"),
|
||||
|
||||
@@ -125,6 +125,10 @@ const MonitorSchema = mongoose.Schema(
|
||||
return this.alertThreshold;
|
||||
},
|
||||
},
|
||||
selectedDisks: {
|
||||
type: [String],
|
||||
default: [],
|
||||
},
|
||||
gameId: {
|
||||
type: String,
|
||||
},
|
||||
|
||||
@@ -174,6 +174,7 @@ const createMonitorBodyValidation = joi.object({
|
||||
expectedValue: joi.string().allow(""),
|
||||
matchMethod: joi.string(),
|
||||
gameId: joi.string().allow(""),
|
||||
selectedDisks: joi.array().items(joi.string()).optional(),
|
||||
group: joi.string().max(50).trim().allow(null, "").optional(),
|
||||
});
|
||||
|
||||
@@ -204,6 +205,7 @@ const editMonitorBodyValidation = joi.object({
|
||||
usage_temperature: joi.number(),
|
||||
}),
|
||||
gameId: joi.string(),
|
||||
selectedDisks: joi.array().items(joi.string()).optional(),
|
||||
group: joi.string().max(50).trim().allow(null, "").optional(),
|
||||
});
|
||||
|
||||
|
||||
Reference in New Issue
Block a user