Skip to content

Commit 591be72

Browse files
committed
Merge branch 'frontend-question-sort-branch'
# Conflicts: # Frontend/src/components/question/Question.jsx
2 parents 0020efd + 397908c commit 591be72

File tree

2 files changed

+60
-53
lines changed

2 files changed

+60
-53
lines changed

Frontend/package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
"@testing-library/jest-dom": "^5.17.0",
88
"@testing-library/react": "^13.4.0",
99
"@testing-library/user-event": "^13.5.0",
10+
"ag-grid-react": "^32.3.2",
1011
"axios": "^1.7.7",
1112
"bootstrap": "^5.3.3",
1213
"jwt-decode": "^4.0.0",

Frontend/src/components/question/Question.jsx

Lines changed: 59 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,9 @@ import EditQn from "./EditQn";
77
import questionService from "../../services/questions"
88
import userService from "../../services/users";
99
import categoryService from "../../services/categories";
10-
10+
import { AgGridReact } from 'ag-grid-react'; // React Data Grid Component
11+
import "ag-grid-community/styles/ag-grid.css"; // Mandatory CSS required by the Data Grid
12+
import "ag-grid-community/styles/ag-theme-quartz.css"; // Optional Theme applied to the Data Grid
1113

1214
function Question() {
1315
const [questions, setQuestions] = useState([]);
@@ -50,10 +52,6 @@ function Question() {
5052
console.log('Error:', e);
5153
});
5254
}, []);
53-
54-
const easyQuestions = questions.filter(q => q.complexity === "Easy")
55-
const mediumQuestions = questions.filter(q => q.complexity === "Medium")
56-
const hardQuestions = questions.filter(q => q.complexity === "Hard")
5755

5856
const addQuestion = (newQuestion) => {
5957
setQuestions((prevQuestions) => [...prevQuestions, newQuestion]);
@@ -128,52 +126,67 @@ function Question() {
128126
};
129127

130128

131-
const renderQuestionsTable = (questions) => {
132-
const sortedQuestions = [...questions].sort((a, b) => a.id - b.id)
129+
const renderQuestionsTable = () => {
130+
const CustomButtonComponent = (props) => {
131+
const question = props.data
132+
return <ButtonGroup className="mb-2">
133+
<button
134+
className='btn btn-success'
135+
onClick={() => handleShowEditModal(question)}
136+
>
137+
Edit
138+
</button>
139+
<button className='btn btn-danger' size="sm"
140+
onClick={() => handleShowDelete(question._id)}>
141+
Delete
142+
</button>
143+
</ButtonGroup>
144+
};
145+
146+
const colDefs = [
147+
{ field: "id", flex: 1, wrapText: true, sort: "asc" },
148+
{ field: "title", flex: 2 },
149+
{ field: "description", flex: 5, wrapText: true, autoHeight: true},
150+
{ field: "complexity", flex: 1.5,
151+
comparator: (valueA, valueB, nodeA, nodeB, isDescending) => {
152+
if (valueA == valueB) return 0;
153+
if (valueA == "Easy" || valueB == "Hard") return -1;
154+
if (valueA == "Hard" || valueB == "Easy") return 1;
155+
}
156+
}
157+
];
158+
159+
if (isAdmin) {
160+
colDefs = [
161+
{ field: "id", flex: 1, wrapText: true, sort: "asc" },
162+
{ field: "title", flex: 2 },
163+
{ field: "description", flex: 5, wrapText: true, autoHeight: true},
164+
{ field: "complexity", flex: 1.5,
165+
comparator: (valueA, valueB, nodeA, nodeB, isDescending) => {
166+
if (valueA == valueB) return 0;
167+
if (valueA == "Easy" || valueB == "Hard") return -1;
168+
if (valueA == "Hard" || valueB == "Easy") return 1;
169+
}
170+
},
171+
{ field: "action", width: 200, resizable: false, sortable: false, cellRenderer: CustomButtonComponent }
172+
];
173+
}
133174

134175
return (
135-
<Table>
136-
<thead>
137-
<tr>
138-
<th>ID</th>
139-
<th>Title</th>
140-
<th>Description</th>
141-
<th>Category</th>
142-
{isAdmin && (<th>Action</th>)}
143-
</tr>
144-
</thead>
145-
<tbody>
146-
{sortedQuestions.map((question) => (
147-
<tr key={question.id}>
148-
<td>{question.id}</td>
149-
<td>{question.title}</td>
150-
<td>{question.description}</td>
151-
<td>{question.category ? question.category.join(", ") : ''}</td>
152-
{isAdmin && (
153-
<td>
154-
<ButtonGroup className="mb-2">
155-
<button
156-
className='btn btn-success'
157-
onClick={() => handleShowEditModal(question)}
158-
>
159-
Edit
160-
</button>
161-
<button className='btn btn-danger' size="sm"
162-
onClick={() => handleShowDelete(question._id)}>
163-
Delete
164-
</button>
165-
</ButtonGroup>
166-
</td>
167-
)}
168-
</tr>
169-
))}
170-
</tbody>
171-
</Table>
176+
<div
177+
className="container-fluid ag-theme-quartz" // applying the Data Grid theme
178+
style={{ height: 500 }} // the Data Grid will fill the size of the parent container
179+
>
180+
<AgGridReact
181+
rowData={questions}
182+
columnDefs={colDefs}
183+
/>
184+
</div>
172185
);
173186
};
174187

175188
return (
176-
<div className="d-flex">
189+
<div className="container-fluid">
177190
<div className='bg-white rounded p-3 m-3'>
178191
<div className="d-flex justify-content-between">
179192
<h1>Questions</h1>
@@ -194,14 +207,7 @@ function Question() {
194207
<hr/>
195208

196209
<div className="container">
197-
<h2 className="p-2">Easy Questions</h2>
198-
{renderQuestionsTable(easyQuestions)}
199-
200-
<h2 className="p-2">Medium Questions</h2>
201-
{renderQuestionsTable(mediumQuestions)}
202-
203-
<h2 className="p-2">Hard Questions</h2>
204-
{renderQuestionsTable(hardQuestions)}
210+
{renderQuestionsTable()}
205211

206212
{/* Edit Modal */}
207213
<Modal show={showEditModal} onHide={handleCloseEditModal} backdrop="static">

0 commit comments

Comments
 (0)