rewriting the component structure
This commit is contained in:
committed by
satti-hari-krishna-reddy
parent
2318d92c3a
commit
809fc2c202
@@ -15,7 +15,7 @@ import HealthPage from "./components/HealthPage.jsx";
|
|||||||
import theme from "./theme";
|
import theme from "./theme";
|
||||||
import Apps from "./views/Apps";
|
import Apps from "./views/Apps";
|
||||||
import AppCreator from "./views/AppCreator";
|
import AppCreator from "./views/AppCreator";
|
||||||
import Dectection from "./views/Detection.jsx";
|
import DetectionDashBoard from "./views/DetectionDashboard.jsx";
|
||||||
|
|
||||||
import Welcome from "./views/Welcome.jsx";
|
import Welcome from "./views/Welcome.jsx";
|
||||||
import Dashboard from "./views/Dashboard.jsx";
|
import Dashboard from "./views/Dashboard.jsx";
|
||||||
@@ -418,7 +418,7 @@ const App = (message, props) => {
|
|||||||
<Route
|
<Route
|
||||||
exact
|
exact
|
||||||
path="/detections/sigma"
|
path="/detections/sigma"
|
||||||
element={<Dectection globalUrl={globalUrl} />}
|
element={<DetectionDashBoard globalUrl={globalUrl} />}
|
||||||
/>
|
/>
|
||||||
<Route
|
<Route
|
||||||
exact
|
exact
|
||||||
|
|||||||
@@ -4,124 +4,18 @@ import {
|
|||||||
Box,
|
Box,
|
||||||
TextField,
|
TextField,
|
||||||
Switch,
|
Switch,
|
||||||
Card,
|
|
||||||
CardContent,
|
|
||||||
IconButton,
|
|
||||||
Typography,
|
Typography,
|
||||||
Button,
|
Button,
|
||||||
} from "@mui/material";
|
} from "@mui/material";
|
||||||
import EditIcon from "@mui/icons-material/Edit";
|
import RuleCard from "./RuleCard";
|
||||||
import { styled } from "@mui/system";
|
import { styled } from "@mui/system";
|
||||||
import { toast } from "react-toastify";
|
|
||||||
|
|
||||||
const ConnectedButton = styled(Button)({
|
const ConnectedButton = styled(Button)({
|
||||||
backgroundColor: "red",
|
backgroundColor: "red",
|
||||||
color: "white",
|
color: "white",
|
||||||
});
|
});
|
||||||
|
|
||||||
const RuleCard = ({ ruleName, description, file_id, globalUrl, ...otherProps }) => {
|
const Detection = ({ globalUrl, ruleInfo, openEditBar }) => {
|
||||||
const [additionalProps, setAdditionalProps] = React.useState(otherProps);
|
|
||||||
|
|
||||||
const handleSwitchChange = (event) => {
|
|
||||||
const isEnabled = event.target.checked;
|
|
||||||
toggleRule(file_id, !isEnabled, globalUrl, () => {
|
|
||||||
setAdditionalProps((prevProps) => ({
|
|
||||||
...prevProps,
|
|
||||||
is_enabled: isEnabled,
|
|
||||||
}));
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Card variant="outlined" sx={{ mb: 2 }}>
|
|
||||||
<CardContent>
|
|
||||||
<div
|
|
||||||
style={{
|
|
||||||
display: 'flex',
|
|
||||||
justifyContent: 'space-between',
|
|
||||||
alignItems: 'center',
|
|
||||||
marginBottom: 16,
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<Typography variant="h6">{ruleName}</Typography>
|
|
||||||
<div style={{ display: 'flex', alignItems: 'center' }}>
|
|
||||||
<IconButton>
|
|
||||||
<EditIcon />
|
|
||||||
</IconButton>
|
|
||||||
<Switch
|
|
||||||
checked={additionalProps.is_enabled}
|
|
||||||
onChange={handleSwitchChange}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<Typography variant="body2" style={{ marginTop: '2%' }}>
|
|
||||||
{description}
|
|
||||||
</Typography>
|
|
||||||
</CardContent>
|
|
||||||
</Card>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
|
|
||||||
const toggleRule = (fileId, isCurrentlyEnabled, globalUrl, callback) => {
|
|
||||||
const action = isCurrentlyEnabled ? "disable" : "enable";
|
|
||||||
const url = `${globalUrl}/api/v1/files/${fileId}/${action}_rule`;
|
|
||||||
|
|
||||||
fetch(url, {
|
|
||||||
method: "PUT",
|
|
||||||
credentials: "include",
|
|
||||||
headers: {
|
|
||||||
"Content-Type": "application/json",
|
|
||||||
},
|
|
||||||
})
|
|
||||||
.then((response) =>
|
|
||||||
response.json().then((responseJson) => {
|
|
||||||
if (responseJson["success"] === false) {
|
|
||||||
toast(`Failed to ${action} the rule`);
|
|
||||||
} else {
|
|
||||||
toast(`Rule ${action}d successfully`);
|
|
||||||
callback();
|
|
||||||
}
|
|
||||||
})
|
|
||||||
)
|
|
||||||
.catch((error) => {
|
|
||||||
console.log(`Error in ${action}ing the rule: `, error);
|
|
||||||
toast(`An error occurred while ${action}ing the rule`);
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
const Detection = (props) => {
|
|
||||||
const { globalUrl } = props;
|
|
||||||
const [ruleInfo, setRuleInfo] = React.useState([]);
|
|
||||||
|
|
||||||
const getSigmaInfo = () => {
|
|
||||||
const url = globalUrl + "/api/v1/files/detection/sigma_rules";
|
|
||||||
|
|
||||||
fetch(url, {
|
|
||||||
method: "GET",
|
|
||||||
credentials: "include",
|
|
||||||
headers: {
|
|
||||||
"Content-Type": "application/json",
|
|
||||||
},
|
|
||||||
})
|
|
||||||
.then((response) =>
|
|
||||||
response.json().then((responseJson) => {
|
|
||||||
if (responseJson["success"] === false) {
|
|
||||||
toast("Failed to get sigma rules");
|
|
||||||
} else {
|
|
||||||
setRuleInfo(responseJson);
|
|
||||||
}
|
|
||||||
})
|
|
||||||
)
|
|
||||||
.catch((error) => {
|
|
||||||
console.log("Error in getting sigma files: ", error);
|
|
||||||
toast("An error occurred while fetching sigma rules");
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
React.useEffect(() => {
|
|
||||||
getSigmaInfo();
|
|
||||||
}, []);
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Container sx={{ mt: 4 }}>
|
<Container sx={{ mt: 4 }}>
|
||||||
<Box sx={{ border: "1px solid #ccc", borderRadius: 2, p: 3 }}>
|
<Box sx={{ border: "1px solid #ccc", borderRadius: 2, p: 3 }}>
|
||||||
@@ -164,6 +58,7 @@ const Detection = (props) => {
|
|||||||
description={card.description}
|
description={card.description}
|
||||||
file_id={card.file_id}
|
file_id={card.file_id}
|
||||||
globalUrl={globalUrl}
|
globalUrl={globalUrl}
|
||||||
|
openEditBar={() => openEditBar(card)}
|
||||||
{...card}
|
{...card}
|
||||||
/>
|
/>
|
||||||
))}
|
))}
|
||||||
|
|||||||
@@ -0,0 +1,102 @@
|
|||||||
|
import React, { useState, useEffect } from "react";
|
||||||
|
import { Container} from "@mui/material";
|
||||||
|
import { toast } from "react-toastify";
|
||||||
|
import Detection from "./Detection";
|
||||||
|
import EditComponent from "./EditRules";
|
||||||
|
|
||||||
|
const getSigmaInfo = (globalUrl, setRuleInfo) => {
|
||||||
|
const url = globalUrl + "/api/v1/files/detection/sigma_rules";
|
||||||
|
|
||||||
|
fetch(url, {
|
||||||
|
method: "GET",
|
||||||
|
credentials: "include",
|
||||||
|
headers: {
|
||||||
|
"Content-Type": "application/json",
|
||||||
|
},
|
||||||
|
})
|
||||||
|
.then((response) =>
|
||||||
|
response.json().then((responseJson) => {
|
||||||
|
if (responseJson["success"] === false) {
|
||||||
|
toast("Failed to get sigma rules");
|
||||||
|
} else {
|
||||||
|
setRuleInfo(responseJson);
|
||||||
|
}
|
||||||
|
})
|
||||||
|
)
|
||||||
|
.catch((error) => {
|
||||||
|
console.log("Error in getting sigma files: ", error);
|
||||||
|
toast("An error occurred while fetching sigma rules");
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const DetectionDashBoard = (props) => {
|
||||||
|
const { globalUrl } = props;
|
||||||
|
const [ruleInfo, setRuleInfo] = useState([]);
|
||||||
|
const [selectedRule, setSelectedRule] = useState(null);
|
||||||
|
const [fileData, setFileData] = useState("")
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
getSigmaInfo(globalUrl, setRuleInfo);
|
||||||
|
}, [globalUrl]);
|
||||||
|
|
||||||
|
const openEditBar = (rule) => {
|
||||||
|
setSelectedRule(rule);
|
||||||
|
getFileContent(rule.file_id)
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleSave = (updatedContent) => {
|
||||||
|
toast("this will be saved");
|
||||||
|
setSelectedRule(null); // Close the edit bar after saving
|
||||||
|
};
|
||||||
|
|
||||||
|
const getFileContent = (file_id) => {
|
||||||
|
fetch(globalUrl + "/api/v1/files/" + file_id + "/content", {
|
||||||
|
method: "GET",
|
||||||
|
headers: {
|
||||||
|
"Content-Type": "application/json",
|
||||||
|
Accept: "application/json",
|
||||||
|
},
|
||||||
|
credentials: "include",
|
||||||
|
})
|
||||||
|
.then((response) => {
|
||||||
|
if (response.status !== 200) {
|
||||||
|
console.log("Status not 200 for file :O!");
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
return response.text();
|
||||||
|
})
|
||||||
|
.then((respdata) => {
|
||||||
|
if (respdata.length === 0) {
|
||||||
|
toast("Failed getting file. Is it deleted?");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
return respdata
|
||||||
|
})
|
||||||
|
.then((responseData) => {
|
||||||
|
|
||||||
|
setFileData(responseData);
|
||||||
|
})
|
||||||
|
.catch((error) => {
|
||||||
|
toast(error.toString());
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Container style={{display: "flex", width: "100%"}}>
|
||||||
|
{selectedRule ? (
|
||||||
|
<EditComponent
|
||||||
|
ruleName={selectedRule.ruleName}
|
||||||
|
description={selectedRule.description}
|
||||||
|
content={fileData}
|
||||||
|
setContent={setFileData}
|
||||||
|
lastEdited={selectedRule.lastEdited}
|
||||||
|
editedBy={selectedRule.editedBy}
|
||||||
|
onSave={handleSave}
|
||||||
|
/>
|
||||||
|
) : null}
|
||||||
|
<Detection globalUrl={globalUrl} ruleInfo={ruleInfo} openEditBar={openEditBar} />
|
||||||
|
</Container>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export default DetectionDashBoard;
|
||||||
@@ -0,0 +1,46 @@
|
|||||||
|
import React, { useState } from 'react';
|
||||||
|
import { Box, Typography, Button, Switch, TextField } from '@mui/material';
|
||||||
|
|
||||||
|
const EditComponent = ({ ruleName, description, content, setContent, lastEdited, editedBy, onSave }) => {
|
||||||
|
|
||||||
|
const handleSave = () => {
|
||||||
|
onSave(content);
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Box sx={{ p: 2, border: '1px solid #ccc', borderRadius: 2, width: '100%' }}>
|
||||||
|
<Box sx={{ display: 'flex', justifyContent: 'space-between', alignItems: 'center' }}>
|
||||||
|
<Typography variant="body2" style={{ marginTop: '2%' }}>{ruleName}</Typography>
|
||||||
|
<Box sx={{ display: 'flex', alignItems: 'center' }}>
|
||||||
|
<Switch checked={true} />
|
||||||
|
</Box>
|
||||||
|
</Box>
|
||||||
|
<Typography variant="body2" style={{ marginTop: '2%' }}>
|
||||||
|
{description}
|
||||||
|
</Typography>
|
||||||
|
<Typography variant="body2" sx={{ mt: 1 }}>
|
||||||
|
Last edited: {lastEdited}
|
||||||
|
</Typography>
|
||||||
|
<Typography variant="body2">
|
||||||
|
Edited By: {editedBy}
|
||||||
|
</Typography>
|
||||||
|
<Box sx={{ mt: 2 }}>
|
||||||
|
<TextField
|
||||||
|
multiline
|
||||||
|
rows={12}
|
||||||
|
value={content}
|
||||||
|
onChange={(e) => setContent(e.target.value)}
|
||||||
|
variant="outlined"
|
||||||
|
fullWidth
|
||||||
|
/>
|
||||||
|
</Box>
|
||||||
|
<Box sx={{ display: 'flex', justifyContent: 'flex-end', mt: 2 }}>
|
||||||
|
<Button variant="contained" color="primary" onClick={handleSave}>
|
||||||
|
Save
|
||||||
|
</Button>
|
||||||
|
</Box>
|
||||||
|
</Box>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
export default EditComponent;
|
||||||
@@ -0,0 +1,82 @@
|
|||||||
|
import React from "react";
|
||||||
|
import {
|
||||||
|
Card,
|
||||||
|
CardContent,
|
||||||
|
IconButton,
|
||||||
|
Typography,
|
||||||
|
Switch,
|
||||||
|
} from "@mui/material";
|
||||||
|
import EditIcon from "@mui/icons-material/Edit";
|
||||||
|
import { toast } from "react-toastify";
|
||||||
|
|
||||||
|
const RuleCard = ({ ruleName, description, file_id, globalUrl, openEditBar, ...otherProps }) => {
|
||||||
|
const [additionalProps, setAdditionalProps] = React.useState(otherProps);
|
||||||
|
|
||||||
|
const handleSwitchChange = (event) => {
|
||||||
|
const isEnabled = event.target.checked;
|
||||||
|
toggleRule(file_id, !isEnabled, globalUrl, () => {
|
||||||
|
setAdditionalProps((prevProps) => ({
|
||||||
|
...prevProps,
|
||||||
|
is_enabled: isEnabled,
|
||||||
|
}));
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Card variant="outlined" sx={{ mb: 2 }}>
|
||||||
|
<CardContent>
|
||||||
|
<div
|
||||||
|
style={{
|
||||||
|
display: 'flex',
|
||||||
|
justifyContent: 'space-between',
|
||||||
|
alignItems: 'center',
|
||||||
|
marginBottom: 16,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<Typography variant="h6">{ruleName}</Typography>
|
||||||
|
<div style={{ display: 'flex', alignItems: 'center' }}>
|
||||||
|
<IconButton onClick={() => openEditBar({ ruleName, description, file_id, ...additionalProps })}>
|
||||||
|
<EditIcon />
|
||||||
|
</IconButton>
|
||||||
|
<Switch
|
||||||
|
checked={additionalProps.is_enabled}
|
||||||
|
onChange={handleSwitchChange}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<Typography variant="body2" style={{ marginTop: '2%' }}>
|
||||||
|
{description}
|
||||||
|
</Typography>
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
const toggleRule = (fileId, isCurrentlyEnabled, globalUrl, callback) => {
|
||||||
|
const action = isCurrentlyEnabled ? "disable" : "enable";
|
||||||
|
const url = `${globalUrl}/api/v1/files/${fileId}/${action}_rule`;
|
||||||
|
|
||||||
|
fetch(url, {
|
||||||
|
method: "PUT",
|
||||||
|
credentials: "include",
|
||||||
|
headers: {
|
||||||
|
"Content-Type": "application/json",
|
||||||
|
},
|
||||||
|
})
|
||||||
|
.then((response) =>
|
||||||
|
response.json().then((responseJson) => {
|
||||||
|
if (responseJson["success"] === false) {
|
||||||
|
toast(`Failed to ${action} the rule`);
|
||||||
|
} else {
|
||||||
|
toast(`Rule ${action}d successfully`);
|
||||||
|
callback();
|
||||||
|
}
|
||||||
|
})
|
||||||
|
)
|
||||||
|
.catch((error) => {
|
||||||
|
console.log(`Error in ${action}ing the rule: `, error);
|
||||||
|
toast(`An error occurred while ${action}ing the rule`);
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
export default RuleCard;
|
||||||
Reference in New Issue
Block a user