├── backend ├── README.md ├── Procfile ├── consumerPhotos │ ├── 05300498-6f2c-45e5-813b-38d547ff666f.jpeg │ ├── 05a75d96-b38d-40c2-9916-66aed2b83d1e.pdf │ ├── 0f95e68d-2b37-42e1-9af5-8f2e3e4825a8.jpeg │ ├── 12d740a8-20ce-4485-b537-4fab2c461ee1.jpg │ ├── 1e13ce80-b767-4db5-95fe-873b6629fc3f.jpeg │ ├── 2ac7d480-65c3-49de-8b8c-1bab8ddb3b7a.png │ ├── 30b493da-8bf0-45f2-89d7-be96c18dfbac.jpeg │ ├── 33120d77-4b5b-4383-990c-96233fffdd95.jpg │ ├── 3a7dad16-c89a-429f-bac8-726bd4eef8c1.jpg │ ├── 42ce594f-c32f-46f3-bb32-75ac76e297da.jpeg │ ├── 44aa6abe-dd58-400a-8e5e-6466a2e81d40.jpg │ ├── 46bae746-9a14-425d-8ee3-1476a6c1541f.jpeg │ ├── 5307cbcd-5575-451c-91b1-171d0c4dbb08.pdf │ ├── 53ae4bb0-976a-4548-98ed-01b4f2670732.jpg │ ├── 53dcda69-a894-4177-9f27-9702cef9d538.jpeg │ ├── 543c8a0a-d53c-4096-b21f-8811d0383b44.jpeg │ ├── 563caf75-26c5-40dd-9e79-f3ae1710b503.pdf │ ├── 5e6d7e80-d35b-4e11-a4e1-a59d484f5ede.jpg │ ├── 695bb3d3-23a1-4b6e-9b57-dad981b39acd.pdf │ ├── 6ed934b1-f60b-42bb-bd6c-1ea681107327.jpeg │ ├── 7009f5f1-958f-4f34-bf7a-87ca695137f1.jpeg │ ├── 71ebfba1-f897-41e6-a993-90518da22d53.png │ ├── 7dbde21c-636c-41e0-8da8-7ddc89bb685c.jpeg │ ├── 7dd09eac-d4cd-4161-bba7-d81e03c33523.jpeg │ ├── 82541090-cd1d-41f7-be24-78f240b80927.jpeg │ ├── 8959b711-21f8-416c-9a9f-5c0ac5176be0.jpeg │ ├── 8d97010e-3b9c-4569-be9d-4c5af3db435e.jpg │ ├── 8e3d3bac-67ae-4aaf-aa19-294f45f57f2c.pdf │ ├── 9324f03a-35b0-42df-9e85-84ad9c288891.jpg │ ├── 9643d006-b000-4b15-8c97-e8cc5fc37286.jpg │ ├── 9757ddaa-b227-4485-9df0-f0bb68aeff8d.pdf │ ├── 9f97256a-b708-4008-a425-fe5f0b9f5b37.jpeg │ ├── a4564394-9fc6-40bb-a8e3-8382282d1f03.jpeg │ ├── a9013430-da00-4bda-bd69-d46f7d6bf79f.pdf │ ├── b0a5c32f-e624-4425-afb4-1f50a23ec70b.jpeg │ ├── b1f8f8e6-fe36-4a81-8144-9dae24fa9dee.jpg │ ├── b2e697d8-4f7a-40fd-bcd8-e8c6beb0943d.jpeg │ ├── b976a4f4-23b5-48ee-ba9e-eb2b26fdf2df.jpeg │ ├── bea9f1da-7333-4ec2-95c1-0c6e511f41a9.jpeg │ ├── bf8bc150-d7e1-42d3-8905-2d86c7421b6f.png │ ├── c2fd58d0-e8e8-4cef-83dd-c7e6f5899275.jpeg │ ├── c36aa638-3e0a-4573-a0a4-44fbfe8de49c.jpeg │ ├── c70caa7b-b226-49d5-933d-127b1f81fc69.zip │ ├── c84cee96-1d6d-4217-8bda-049ad9500b92.jpeg │ ├── ce707db5-490f-47b6-b7cd-3b8b2089f13f.jpg │ ├── cf201943-e6b2-4440-a8e1-7e096cd4d25a.pdf │ ├── d58ccaec-1ab4-4d1c-baa7-985053ab65a2.jpeg │ ├── d93d8bcc-dae9-4015-b32a-b9aea532f80e.jpeg │ ├── dd5eaca8-74f0-4ac6-ae3f-f53b7e41d869.jpg │ ├── df636d37-1cea-44f9-9973-b4e368e1f35a.jpg │ ├── e002cf22-2e87-4369-882b-9ba49f49eef8.jpg │ ├── e16e7bd7-8c6b-445a-92a8-a7e5f0d6dd25.zip │ ├── e31f20ca-ca48-470c-8653-d61a816ace3b.jpeg │ ├── e3b01c49-f956-4561-96be-909daa94b45d.jpeg │ ├── e9a532bb-ef8d-47d6-96d1-bea9591b0d05.pdf │ ├── f1e6d2cf-4ff6-41ba-bb4c-ccdf94760423.jpeg │ ├── f66dd77d-0177-4ead-b22b-73e926985dcd.jpeg │ └── fdf1e2b5-fc16-42c5-a972-9ecd11914434.png ├── middlewares │ ├── variables.js │ ├── cloudinary.js │ ├── Nodemailer.js │ ├── utils.js │ └── multer.js ├── public │ └── consumerPhotos │ │ └── 4cfc8243-fa18-465c-9b9f-97ea8f4e77ad.png ├── models │ ├── ActivityLogs.js │ ├── DivisionModel.js │ ├── DepartmentsModel.js │ ├── SectionModel.js │ ├── YearGroupModel.js │ ├── DeductionsModel.js │ ├── CampusesModel.js │ ├── PayRow.Model.js │ ├── OptionsModel.js │ ├── DormitoriesModel.js │ ├── CurrentModel.js │ ├── TaskModel.js │ ├── UsersModel.js │ ├── ScholarshipsModel.js │ ├── PrefectsModel.js │ ├── StoreItemsModel.js │ ├── NoticeModel.js │ ├── NotificationMessageModel.js │ ├── AttendenceModel.js │ ├── FilesModel.js │ ├── CalenderModel.js │ ├── NextofKinModel.js │ ├── CorrespondanceModel.js │ ├── SchoolModel.js │ ├── NonBillModel.js │ ├── SSNITModel.js │ ├── PaymentPlanModel.js │ ├── StoreSalesModel.js │ ├── StaffPayModel.js │ ├── CoursesModel.js │ ├── CanteenModel.js │ ├── ClassesModel.js │ ├── SBAModel.js │ ├── BankingModel.js │ ├── ChatModel.js │ ├── NonTeacherModel.js │ ├── TransactionsModel.js │ └── FeesModel.js ├── .gitignore ├── config │ └── mongodb.js ├── routes │ ├── Uploads.js │ ├── DivisionRoutes.js │ ├── YeargroupRoutes.js │ └── DepartmentRoutes.js └── package.json ├── frontend ├── .vscodeignore ├── README.md ├── src │ ├── AdminComponents │ │ ├── users │ │ │ └── UserRestrictions.js │ │ ├── store │ │ │ ├── store │ │ │ │ └── Store.js │ │ │ └── reports │ │ │ │ ├── Reports.js │ │ │ │ └── PaymentsReceipt.js │ │ ├── Profile │ │ │ ├── academicsReports │ │ │ │ └── EndofYearReport.js │ │ │ ├── FinanceCard.js │ │ │ ├── Profile.js │ │ │ ├── SummaryCard.js │ │ │ ├── ProfileInfo.js │ │ │ ├── StaffTabs.js │ │ │ ├── FinancialTabs.js │ │ │ └── StudentsTabs.js │ │ ├── staff │ │ │ ├── Index.js │ │ │ ├── Attendence.js │ │ │ ├── SearchForm.js │ │ │ ├── PayrowPage.js │ │ │ ├── SearchPayrow.js │ │ │ ├── StaffDetails.js │ │ │ └── SearchAttendance.js │ │ ├── academics │ │ │ ├── calender │ │ │ │ └── ViewCalendar.js │ │ │ ├── classGroups │ │ │ │ └── AddClassGroup.js │ │ │ ├── combinedReports │ │ │ │ └── CombinedReports.js │ │ │ ├── progressReports │ │ │ │ └── ProgressReports.js │ │ │ └── yearGroups │ │ │ │ └── AddYearGroup.js │ │ ├── shared │ │ │ ├── GoBack.js │ │ │ ├── ProfilePicture.js │ │ │ ├── HandleDelete.js │ │ │ └── ViewOptions.js │ │ ├── students │ │ │ ├── campuses │ │ │ │ └── AddCampus.js │ │ │ ├── section │ │ │ │ └── AddSection.js │ │ │ ├── dormitories │ │ │ │ └── AddDormitories.js │ │ │ ├── upGrade │ │ │ │ └── Upgrade.js │ │ │ └── pastStudents │ │ │ │ └── ViewOptions.js │ │ ├── messages │ │ │ └── Chat.js │ │ ├── canteen │ │ │ ├── CanteenNav.js │ │ │ └── Members.js │ │ ├── dashboard │ │ │ ├── RecentActivity.js │ │ │ ├── StaffPopulation.js │ │ │ ├── SchoolPopulation.js │ │ │ └── Attendance.js │ │ ├── finance │ │ │ ├── setfees │ │ │ │ └── DeleteFeesModal.js │ │ │ ├── banking │ │ │ │ ├── Banking.js │ │ │ │ └── AddBank.js │ │ │ └── expenditure │ │ │ │ └── ViewPayment.js │ │ └── attendance │ │ │ ├── StaffAttendance │ │ │ ├── StaffAttendanceRegister.js │ │ │ └── EditStaffAttendance.js │ │ │ └── StudentAttendance │ │ │ └── EditAttendance.js │ ├── scss │ │ ├── _custom.scss │ │ ├── _variables.scss │ │ ├── _fixes.scss │ │ ├── style.scss │ │ ├── _students.scss │ │ └── _admin.scss │ ├── assets │ │ └── icons │ │ │ ├── logo.png │ │ │ └── sygnet.js │ ├── store │ │ ├── axios.js │ │ ├── localStorage.js │ │ ├── index.js │ │ └── slices │ │ │ ├── appSlice.js │ │ │ └── userSlice.js │ ├── StudentComponents │ │ ├── settings │ │ │ └── SettingsPage.js │ │ ├── messages │ │ │ ├── Chat.js │ │ │ └── MessageAdmin.js │ │ ├── attendence │ │ │ └── AttendancePage.js │ │ ├── classes │ │ │ ├── CalendarPage.js │ │ │ ├── CoursesPage.js │ │ │ ├── Classes.js │ │ │ ├── ClassCard.js │ │ │ └── CoursePage.js │ │ ├── finances │ │ │ └── DuePayments.js │ │ └── profile │ │ │ └── ProfilePage.js │ ├── TeachersComponents │ │ ├── settings │ │ │ └── SettingsPage.js │ │ ├── academics │ │ │ ├── ClassDetails.js │ │ │ ├── AllClasses.js │ │ │ ├── ClassCard.js │ │ │ └── AllCourses.js │ │ ├── message │ │ │ ├── Chat.js │ │ │ ├── Broadcast.js │ │ │ └── MessageAdmin.js │ │ ├── attendance │ │ │ └── Attendance.js │ │ └── dashboard │ │ │ └── Profile.js │ ├── components │ │ ├── userInfoTabs │ │ │ ├── NextofKinTab.js │ │ │ ├── GuadanceTab.js │ │ │ ├── ContactInfo.js │ │ │ ├── UserInfo.js │ │ │ ├── StudentDetails.js │ │ │ └── EmploymentTab.js │ │ ├── messages │ │ │ └── inbox │ │ │ │ ├── DefaultView.js │ │ │ │ ├── Message.js │ │ │ │ └── Messaging.js │ │ ├── settings │ │ │ ├── Settings.js │ │ │ └── Logout.js │ │ ├── tables │ │ │ └── ExcelExport.js │ │ ├── dashboard │ │ │ ├── Card.js │ │ │ ├── SchoolCalender.js │ │ │ ├── NoticeBoard.js │ │ │ └── Notice.js │ │ └── courses │ │ │ └── ClassCard.js │ ├── setupTests.js │ ├── containers │ │ ├── TheFooter.js │ │ ├── index.js │ │ ├── TheContent.js │ │ └── TheSidebar.js │ ├── App.test.js │ ├── ProtectedRoutes.js │ ├── Loading.js │ ├── index.js │ ├── polyfill.js │ ├── AppLoading.js │ └── pages │ │ ├── page404 │ │ └── Page404.js │ │ └── page500 │ │ └── Page500.js ├── jsconfig.json ├── public │ ├── avatars │ │ ├── 1.jpg │ │ ├── 2.jpg │ │ ├── 3.jpg │ │ ├── 4.jpg │ │ ├── 5.jpg │ │ ├── 6.jpg │ │ ├── 7.jpg │ │ └── 8.jpg │ ├── favicon.ico │ ├── manifest.json │ └── index.html └── .gitignore ├── .DS_Store ├── Documentation.docx ├── screenshots ├── adminDashboard.png ├── Screen Shot 2021-02-26 at 10.24.40 PM.png ├── Screen Shot 2021-02-26 at 10.24.55 PM.png ├── Screen Shot 2021-02-26 at 10.25.06 PM.png ├── Screen Shot 2021-02-26 at 10.25.25 PM.png ├── Screen Shot 2021-02-26 at 10.26.01 PM.png ├── Screen Shot 2021-02-26 at 10.26.16 PM.png ├── Screen Shot 2021-02-26 at 10.31.05 PM.png ├── Screen Shot 2021-02-26 at 10.31.33 PM.png ├── Screen Shot 2021-02-26 at 10.34.42 PM.png ├── Screen Shot 2021-02-26 at 10.36.10 PM.png ├── Screen Shot 2021-02-26 at 10.36.31 PM.png ├── Screen Shot 2021-02-26 at 10.36.51 PM.png ├── Screen Shot 2021-02-26 at 10.36.58 PM.png ├── Screen Shot 2021-02-26 at 7.25.06 PM.png ├── Screen Shot 2021-02-26 at 7.29.45 PM.png ├── Screen Shot 2021-02-26 at 7.34.23 PM.png ├── Screen Shot 2021-02-26 at 8.42.10 PM.png ├── Screen Shot 2021-02-26 at 8.42.27 PM.png ├── Screen Shot 2021-02-26 at 8.42.36 PM.png ├── Screen Shot 2021-02-26 at 8.42.45 PM.png ├── Screen Shot 2021-02-26 at 8.43.04 PM.png ├── Screen Shot 2021-02-26 at 8.43.15 PM.png ├── Screen Shot 2021-02-26 at 8.43.59 PM.png ├── Screen Shot 2021-02-26 at 8.44.09 PM.png ├── Screen Shot 2021-02-26 at 8.44.26 PM.png ├── Screen Shot 2021-02-26 at 8.56.09 PM.png ├── Screen Shot 2021-02-26 at 9.03.32 PM.png ├── Screen Shot 2021-02-26 at 9.03.53 PM.png ├── Screen Shot 2021-02-26 at 9.04.10 PM.png ├── Screen Shot 2021-02-26 at 9.04.21 PM.png ├── Screen Shot 2021-02-26 at 9.11.56 PM.png ├── Screen Shot 2021-02-26 at 9.12.13 PM.png ├── Screen Shot 2021-02-26 at 9.13.56 PM.png ├── Screen Shot 2021-02-26 at 9.14.18 PM.png ├── Screen Shot 2021-02-26 at 9.15.22 PM.png ├── Screen Shot 2021-02-26 at 9.15.44 PM.png ├── Screen Shot 2021-02-26 at 9.16.40 PM.png ├── Screen Shot 2021-02-26 at 9.16.54 PM.png ├── Screen Shot 2021-02-26 at 9.17.11 PM.png ├── Screen Shot 2021-02-26 at 9.17.28 PM.png ├── Screen Shot 2021-02-26 at 9.17.51 PM.png ├── Screen Shot 2021-02-26 at 9.50.44 PM.png ├── Screen Shot 2021-02-26 at 9.53.18 PM.png ├── Screen Shot 2021-02-26 at 9.53.20 PM.png ├── Screen Shot 2021-02-26 at 9.53.42 PM.png ├── Screen Shot 2021-02-26 at 9.53.54 PM.png ├── Screen Shot 2021-02-26 at 9.54.11 PM.png ├── Screen Shot 2021-02-26 at 9.54.24 PM.png └── Screen Shot 2021-02-26 at 9.58.16 PM.png └── README.md /backend/README.md: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /frontend/.vscodeignore: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /backend/Procfile: -------------------------------------------------------------------------------- 1 | web: node server.js -------------------------------------------------------------------------------- /frontend/README.md: -------------------------------------------------------------------------------- 1 | https://vimeo.com/532774674/2dfa52f69f -------------------------------------------------------------------------------- /frontend/src/AdminComponents/users/UserRestrictions.js: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /frontend/src/scss/_custom.scss: -------------------------------------------------------------------------------- 1 | // Here you can add other styles 2 | -------------------------------------------------------------------------------- /.DS_Store: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/.DS_Store -------------------------------------------------------------------------------- /frontend/jsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "baseUrl": "." 4 | }, 5 | "include": ["src"] 6 | } -------------------------------------------------------------------------------- /Documentation.docx: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/Documentation.docx -------------------------------------------------------------------------------- /frontend/public/avatars/1.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/public/avatars/1.jpg -------------------------------------------------------------------------------- /frontend/public/avatars/2.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/public/avatars/2.jpg -------------------------------------------------------------------------------- /frontend/public/avatars/3.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/public/avatars/3.jpg -------------------------------------------------------------------------------- /frontend/public/avatars/4.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/public/avatars/4.jpg -------------------------------------------------------------------------------- /frontend/public/avatars/5.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/public/avatars/5.jpg -------------------------------------------------------------------------------- /frontend/public/avatars/6.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/public/avatars/6.jpg -------------------------------------------------------------------------------- /frontend/public/avatars/7.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/public/avatars/7.jpg -------------------------------------------------------------------------------- /frontend/public/avatars/8.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/public/avatars/8.jpg -------------------------------------------------------------------------------- /frontend/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/public/favicon.ico -------------------------------------------------------------------------------- /screenshots/adminDashboard.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/adminDashboard.png -------------------------------------------------------------------------------- /frontend/src/assets/icons/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/frontend/src/assets/icons/logo.png -------------------------------------------------------------------------------- /frontend/src/AdminComponents/store/store/Store.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | 3 | function Store() { 4 | return
Store
; 5 | } 6 | 7 | export default Store; 8 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/store/reports/Reports.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | 3 | function Reports() { 4 | return
Reports
; 5 | } 6 | 7 | export default Reports; 8 | -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.24.40 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.24.40 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.24.55 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.24.55 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.25.06 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.25.06 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.25.25 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.25.25 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.26.01 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.26.01 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.26.16 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.26.16 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.31.05 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.31.05 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.31.33 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.31.33 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.34.42 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.34.42 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.36.10 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.36.10 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.36.31 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.36.31 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.36.51 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.36.51 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 10.36.58 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 10.36.58 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 7.25.06 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 7.25.06 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 7.29.45 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 7.29.45 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 7.34.23 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 7.34.23 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.42.10 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.42.10 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.42.27 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.42.27 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.42.36 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.42.36 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.42.45 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.42.45 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.43.04 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.43.04 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.43.15 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.43.15 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.43.59 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.43.59 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.44.09 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.44.09 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.44.26 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.44.26 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 8.56.09 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 8.56.09 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.03.32 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.03.32 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.03.53 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.03.53 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.04.10 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.04.10 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.04.21 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.04.21 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.11.56 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.11.56 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.12.13 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.12.13 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.13.56 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.13.56 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.14.18 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.14.18 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.15.22 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.15.22 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.15.44 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.15.44 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.16.40 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.16.40 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.16.54 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.16.54 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.17.11 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.17.11 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.17.28 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.17.28 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.17.51 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.17.51 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.50.44 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.50.44 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.53.18 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.53.18 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.53.20 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.53.20 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.53.42 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.53.42 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.53.54 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.53.54 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.54.11 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.54.11 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.54.24 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.54.24 PM.png -------------------------------------------------------------------------------- /screenshots/Screen Shot 2021-02-26 at 9.58.16 PM.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/screenshots/Screen Shot 2021-02-26 at 9.58.16 PM.png -------------------------------------------------------------------------------- /frontend/src/store/axios.js: -------------------------------------------------------------------------------- 1 | import axios from 'axios'; 2 | 3 | 4 | const instance = axios.create({ 5 | baseURL: "http://localhost:5000/api" 6 | }) 7 | 8 | 9 | export default instance -------------------------------------------------------------------------------- /backend/consumerPhotos/05300498-6f2c-45e5-813b-38d547ff666f.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/05300498-6f2c-45e5-813b-38d547ff666f.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/05a75d96-b38d-40c2-9916-66aed2b83d1e.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/05a75d96-b38d-40c2-9916-66aed2b83d1e.pdf -------------------------------------------------------------------------------- /backend/consumerPhotos/0f95e68d-2b37-42e1-9af5-8f2e3e4825a8.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/0f95e68d-2b37-42e1-9af5-8f2e3e4825a8.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/12d740a8-20ce-4485-b537-4fab2c461ee1.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/12d740a8-20ce-4485-b537-4fab2c461ee1.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/1e13ce80-b767-4db5-95fe-873b6629fc3f.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/1e13ce80-b767-4db5-95fe-873b6629fc3f.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/2ac7d480-65c3-49de-8b8c-1bab8ddb3b7a.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/2ac7d480-65c3-49de-8b8c-1bab8ddb3b7a.png -------------------------------------------------------------------------------- /backend/consumerPhotos/30b493da-8bf0-45f2-89d7-be96c18dfbac.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/30b493da-8bf0-45f2-89d7-be96c18dfbac.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/33120d77-4b5b-4383-990c-96233fffdd95.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/33120d77-4b5b-4383-990c-96233fffdd95.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/3a7dad16-c89a-429f-bac8-726bd4eef8c1.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/3a7dad16-c89a-429f-bac8-726bd4eef8c1.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/42ce594f-c32f-46f3-bb32-75ac76e297da.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/42ce594f-c32f-46f3-bb32-75ac76e297da.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/44aa6abe-dd58-400a-8e5e-6466a2e81d40.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/44aa6abe-dd58-400a-8e5e-6466a2e81d40.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/46bae746-9a14-425d-8ee3-1476a6c1541f.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/46bae746-9a14-425d-8ee3-1476a6c1541f.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/5307cbcd-5575-451c-91b1-171d0c4dbb08.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/5307cbcd-5575-451c-91b1-171d0c4dbb08.pdf -------------------------------------------------------------------------------- /backend/consumerPhotos/53ae4bb0-976a-4548-98ed-01b4f2670732.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/53ae4bb0-976a-4548-98ed-01b4f2670732.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/53dcda69-a894-4177-9f27-9702cef9d538.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/53dcda69-a894-4177-9f27-9702cef9d538.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/543c8a0a-d53c-4096-b21f-8811d0383b44.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/543c8a0a-d53c-4096-b21f-8811d0383b44.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/563caf75-26c5-40dd-9e79-f3ae1710b503.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/563caf75-26c5-40dd-9e79-f3ae1710b503.pdf -------------------------------------------------------------------------------- /backend/consumerPhotos/5e6d7e80-d35b-4e11-a4e1-a59d484f5ede.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/5e6d7e80-d35b-4e11-a4e1-a59d484f5ede.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/695bb3d3-23a1-4b6e-9b57-dad981b39acd.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/695bb3d3-23a1-4b6e-9b57-dad981b39acd.pdf -------------------------------------------------------------------------------- /backend/consumerPhotos/6ed934b1-f60b-42bb-bd6c-1ea681107327.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/6ed934b1-f60b-42bb-bd6c-1ea681107327.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/7009f5f1-958f-4f34-bf7a-87ca695137f1.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/7009f5f1-958f-4f34-bf7a-87ca695137f1.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/71ebfba1-f897-41e6-a993-90518da22d53.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/71ebfba1-f897-41e6-a993-90518da22d53.png -------------------------------------------------------------------------------- /backend/consumerPhotos/7dbde21c-636c-41e0-8da8-7ddc89bb685c.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/7dbde21c-636c-41e0-8da8-7ddc89bb685c.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/7dd09eac-d4cd-4161-bba7-d81e03c33523.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/7dd09eac-d4cd-4161-bba7-d81e03c33523.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/82541090-cd1d-41f7-be24-78f240b80927.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/82541090-cd1d-41f7-be24-78f240b80927.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/8959b711-21f8-416c-9a9f-5c0ac5176be0.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/8959b711-21f8-416c-9a9f-5c0ac5176be0.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/8d97010e-3b9c-4569-be9d-4c5af3db435e.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/8d97010e-3b9c-4569-be9d-4c5af3db435e.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/8e3d3bac-67ae-4aaf-aa19-294f45f57f2c.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/8e3d3bac-67ae-4aaf-aa19-294f45f57f2c.pdf -------------------------------------------------------------------------------- /backend/consumerPhotos/9324f03a-35b0-42df-9e85-84ad9c288891.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/9324f03a-35b0-42df-9e85-84ad9c288891.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/9643d006-b000-4b15-8c97-e8cc5fc37286.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/9643d006-b000-4b15-8c97-e8cc5fc37286.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/9757ddaa-b227-4485-9df0-f0bb68aeff8d.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/9757ddaa-b227-4485-9df0-f0bb68aeff8d.pdf -------------------------------------------------------------------------------- /backend/consumerPhotos/9f97256a-b708-4008-a425-fe5f0b9f5b37.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/9f97256a-b708-4008-a425-fe5f0b9f5b37.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/a4564394-9fc6-40bb-a8e3-8382282d1f03.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/a4564394-9fc6-40bb-a8e3-8382282d1f03.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/a9013430-da00-4bda-bd69-d46f7d6bf79f.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/a9013430-da00-4bda-bd69-d46f7d6bf79f.pdf -------------------------------------------------------------------------------- /backend/consumerPhotos/b0a5c32f-e624-4425-afb4-1f50a23ec70b.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/b0a5c32f-e624-4425-afb4-1f50a23ec70b.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/b1f8f8e6-fe36-4a81-8144-9dae24fa9dee.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/b1f8f8e6-fe36-4a81-8144-9dae24fa9dee.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/b2e697d8-4f7a-40fd-bcd8-e8c6beb0943d.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/b2e697d8-4f7a-40fd-bcd8-e8c6beb0943d.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/b976a4f4-23b5-48ee-ba9e-eb2b26fdf2df.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/b976a4f4-23b5-48ee-ba9e-eb2b26fdf2df.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/bea9f1da-7333-4ec2-95c1-0c6e511f41a9.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/bea9f1da-7333-4ec2-95c1-0c6e511f41a9.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/bf8bc150-d7e1-42d3-8905-2d86c7421b6f.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/bf8bc150-d7e1-42d3-8905-2d86c7421b6f.png -------------------------------------------------------------------------------- /backend/consumerPhotos/c2fd58d0-e8e8-4cef-83dd-c7e6f5899275.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/c2fd58d0-e8e8-4cef-83dd-c7e6f5899275.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/c36aa638-3e0a-4573-a0a4-44fbfe8de49c.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/c36aa638-3e0a-4573-a0a4-44fbfe8de49c.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/c70caa7b-b226-49d5-933d-127b1f81fc69.zip: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/c70caa7b-b226-49d5-933d-127b1f81fc69.zip -------------------------------------------------------------------------------- /backend/consumerPhotos/c84cee96-1d6d-4217-8bda-049ad9500b92.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/c84cee96-1d6d-4217-8bda-049ad9500b92.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/ce707db5-490f-47b6-b7cd-3b8b2089f13f.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/ce707db5-490f-47b6-b7cd-3b8b2089f13f.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/cf201943-e6b2-4440-a8e1-7e096cd4d25a.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/cf201943-e6b2-4440-a8e1-7e096cd4d25a.pdf -------------------------------------------------------------------------------- /backend/consumerPhotos/d58ccaec-1ab4-4d1c-baa7-985053ab65a2.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/d58ccaec-1ab4-4d1c-baa7-985053ab65a2.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/d93d8bcc-dae9-4015-b32a-b9aea532f80e.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/d93d8bcc-dae9-4015-b32a-b9aea532f80e.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/dd5eaca8-74f0-4ac6-ae3f-f53b7e41d869.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/dd5eaca8-74f0-4ac6-ae3f-f53b7e41d869.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/df636d37-1cea-44f9-9973-b4e368e1f35a.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/df636d37-1cea-44f9-9973-b4e368e1f35a.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/e002cf22-2e87-4369-882b-9ba49f49eef8.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/e002cf22-2e87-4369-882b-9ba49f49eef8.jpg -------------------------------------------------------------------------------- /backend/consumerPhotos/e16e7bd7-8c6b-445a-92a8-a7e5f0d6dd25.zip: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/e16e7bd7-8c6b-445a-92a8-a7e5f0d6dd25.zip -------------------------------------------------------------------------------- /backend/consumerPhotos/e31f20ca-ca48-470c-8653-d61a816ace3b.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/e31f20ca-ca48-470c-8653-d61a816ace3b.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/e3b01c49-f956-4561-96be-909daa94b45d.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/e3b01c49-f956-4561-96be-909daa94b45d.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/e9a532bb-ef8d-47d6-96d1-bea9591b0d05.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/e9a532bb-ef8d-47d6-96d1-bea9591b0d05.pdf -------------------------------------------------------------------------------- /backend/consumerPhotos/f1e6d2cf-4ff6-41ba-bb4c-ccdf94760423.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/f1e6d2cf-4ff6-41ba-bb4c-ccdf94760423.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/f66dd77d-0177-4ead-b22b-73e926985dcd.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/f66dd77d-0177-4ead-b22b-73e926985dcd.jpeg -------------------------------------------------------------------------------- /backend/consumerPhotos/fdf1e2b5-fc16-42c5-a972-9ecd11914434.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/consumerPhotos/fdf1e2b5-fc16-42c5-a972-9ecd11914434.png -------------------------------------------------------------------------------- /frontend/src/AdminComponents/store/reports/PaymentsReceipt.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | 3 | function PaymentsReceipt() { 4 | return
payment
; 5 | } 6 | 7 | export default PaymentsReceipt; 8 | -------------------------------------------------------------------------------- /backend/middlewares/variables.js: -------------------------------------------------------------------------------- 1 | const role = { 2 | Student: "student", 3 | Teacher: "teacher", 4 | NonTeacher: "nonteacher", 5 | Admin: "admin", 6 | }; 7 | 8 | module.exports = { 9 | role, 10 | }; 11 | -------------------------------------------------------------------------------- /backend/public/consumerPhotos/4cfc8243-fa18-465c-9b9f-97ea8f4e77ad.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/samuelajalode/School-management-System-MERN_/HEAD/backend/public/consumerPhotos/4cfc8243-fa18-465c-9b9f-97ea8f4e77ad.png -------------------------------------------------------------------------------- /frontend/src/AdminComponents/Profile/academicsReports/EndofYearReport.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | 3 | function EndofYearReport() { 4 | return
end of year
; 5 | } 6 | 7 | export default EndofYearReport; 8 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/staff/Index.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | 3 | function Index() { 4 | return ( 5 |
6 | All Teachers Ppage 7 |
8 | ) 9 | } 10 | 11 | export default Index 12 | -------------------------------------------------------------------------------- /frontend/src/scss/_variables.scss: -------------------------------------------------------------------------------- 1 | // Variable overrides 2 | 3 | $orange: #ffa201; 4 | $white: #fff; 5 | $darkBlue: #051f3e; 6 | $darkBlue2: #042954; 7 | $lightBlue: #2ad7c5; 8 | $red: #fe3131; 9 | $background: #f0f1f3; 10 | $mobile_device: "(max-width: 767px)"; 11 | -------------------------------------------------------------------------------- /frontend/src/store/localStorage.js: -------------------------------------------------------------------------------- 1 | export const LoginString = { 2 | ID: 'id', 3 | PhotoURL: 'PhotoURL', 4 | NAME : "name", 5 | EMAIL: "email", 6 | TOKEN: 'token', 7 | USERROLE: 'role', 8 | MIDNAME: "middleName", 9 | LASTNAME: "lastname" 10 | } -------------------------------------------------------------------------------- /frontend/src/StudentComponents/settings/SettingsPage.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import Settings from '../../components/settings/Settings' 3 | 4 | function SettingsPage() { 5 | return ( 6 |
7 | 8 |
9 | ) 10 | } 11 | 12 | export default SettingsPage 13 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/settings/SettingsPage.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import Settings from '../../components/settings/Settings' 3 | 4 | 5 | function SettingsPage() { 6 | return ( 7 |
8 | 9 |
10 | ) 11 | } 12 | 13 | export default SettingsPage 14 | -------------------------------------------------------------------------------- /frontend/src/scss/_fixes.scss: -------------------------------------------------------------------------------- 1 | // todo: disabled button styles 2 | button { 3 | &:disabled { 4 | cursor: default; 5 | } 6 | &.disabled { 7 | cursor: default; 8 | } 9 | } 10 | 11 | // todo: brand button icon margin 12 | .btn-brand:not(:only-child) { 13 | .c-icon { 14 | margin-top: 0 !important; 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/academics/calender/ViewCalendar.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import Calender from '../../../components/dashboard/SchoolCalender' 3 | 4 | function ViewCalendar() { 5 | return ( 6 |
7 | 8 |
9 | ) 10 | } 11 | 12 | export default ViewCalendar 13 | -------------------------------------------------------------------------------- /backend/middlewares/cloudinary.js: -------------------------------------------------------------------------------- 1 | const cloudinary = require("cloudinary"); 2 | 3 | cloudinary.config({ 4 | cloud_name: process.env.CLOUDINARY_NAME, 5 | api_key: process.env.CLOUDINARY_API_KEY, 6 | api_secret: process.env.CLOUDINARY_API_SECRET, 7 | shorten: true, 8 | secure: true, 9 | ssl_detected: true, 10 | }); 11 | 12 | module.exports = { cloudinary }; 13 | -------------------------------------------------------------------------------- /frontend/src/components/userInfoTabs/NextofKinTab.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import GuadianCard from './GuadianCard' 3 | 4 | function GuadanceTab({user}) { 5 | return ( 6 |
7 | {user ? :
No nextofkin info
} 8 |
9 | ) 10 | } 11 | 12 | export default GuadanceTab 13 | -------------------------------------------------------------------------------- /frontend/src/components/messages/inbox/DefaultView.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | 3 | function DefaultView() { 4 | return ( 5 |
6 |
7 |

Welcome , Admin

8 |

Messaging Chat system

9 |
10 |
11 | ) 12 | } 13 | 14 | export default DefaultView 15 | -------------------------------------------------------------------------------- /backend/models/ActivityLogs.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const ActivitySchema = new Schema( 6 | { 7 | activity: { 8 | type: String, 9 | }, 10 | user: { 11 | type: String, 12 | }, 13 | }, 14 | { timestamps: true } 15 | ); 16 | 17 | module.exports = mongoose.model("ativity", ActivitySchema); 18 | -------------------------------------------------------------------------------- /frontend/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "CoreUI-React", 3 | "name": "CoreUI-React sample", 4 | "icons": [ 5 | { 6 | "src": "./assets/img/favicon.png", 7 | "sizes": "100x100", 8 | "type": "image/png" 9 | } 10 | ], 11 | "start_url": ".", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /frontend/src/store/index.js: -------------------------------------------------------------------------------- 1 | import { configureStore } from '@reduxjs/toolkit'; 2 | import userReducer from './slices/userSlice'; 3 | import appReducer from './slices/appSlice'; 4 | import schoolReducer from './slices/schoolSlice'; 5 | 6 | export default configureStore({ 7 | reducer: { 8 | user: userReducer, 9 | app: appReducer, 10 | school: schoolReducer 11 | }, 12 | }); 13 | -------------------------------------------------------------------------------- /backend/models/DivisionModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const DivisionSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | }, 10 | description: { 11 | type: String, 12 | }, 13 | }, 14 | { timestamps: true } 15 | ); 16 | 17 | module.exports = mongoose.model("division", DivisionSchema); 18 | -------------------------------------------------------------------------------- /backend/models/DepartmentsModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const DepartmentSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | }, 10 | description: { 11 | type: String, 12 | }, 13 | }, 14 | { timestamps: true } 15 | ); 16 | 17 | module.exports = mongoose.model("departments", DepartmentSchema); 18 | -------------------------------------------------------------------------------- /backend/middlewares/Nodemailer.js: -------------------------------------------------------------------------------- 1 | const nodemailer = require("nodemailer"); 2 | 3 | const transporter = nodemailer.createTransport({ 4 | host: "smtp.example.com", 5 | port: 587, 6 | secure: false, 7 | requireTLS: true, 8 | service: "gmail", 9 | auth: { 10 | user: process.env.EMAIL_ADDRESS, 11 | pass: process.env.EMAIL_PASSWORD, 12 | }, 13 | }); 14 | 15 | module.exports = transporter; 16 | -------------------------------------------------------------------------------- /backend/models/SectionModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const SectionSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | required: true, 10 | }, 11 | description: { 12 | type: String, 13 | }, 14 | }, 15 | { timestamps: true } 16 | ); 17 | 18 | module.exports = mongoose.model("sections", SectionSchema); 19 | -------------------------------------------------------------------------------- /frontend/src/setupTests.js: -------------------------------------------------------------------------------- 1 | import {configure} from 'enzyme'; 2 | import Adapter from '@wojtekmaj/enzyme-adapter-react-17'; 3 | 4 | configure({adapter: new Adapter()}); 5 | 6 | if (global.document) { 7 | document.createRange = () => ({ 8 | setStart: () => {}, 9 | setEnd: () => {}, 10 | commonAncestorContainer: { 11 | nodeName: 'BODY', 12 | ownerDocument: document, 13 | }, 14 | }); 15 | } 16 | -------------------------------------------------------------------------------- /backend/models/YearGroupModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const YearGroupSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | }, 10 | code: { 11 | type: String, 12 | }, 13 | year: { 14 | type: String, 15 | }, 16 | }, 17 | { timestamps: true } 18 | ); 19 | 20 | module.exports = mongoose.model("yeargroup", YearGroupSchema); 21 | -------------------------------------------------------------------------------- /frontend/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | package-lock.json 6 | 7 | # testing 8 | /coverage 9 | 10 | # production 11 | /build 12 | 13 | # misc 14 | .eslintcache 15 | .DS_Store 16 | .idea 17 | .env.local 18 | .env.development.local 19 | .env.test.local 20 | .env.production.local 21 | 22 | npm-debug.log* 23 | yarn-debug.log* 24 | yarn-error.log* 25 | -------------------------------------------------------------------------------- /backend/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | package-lock.json 6 | 7 | # testing 8 | /coverage 9 | 10 | # production 11 | /build 12 | 13 | # misc 14 | .eslintcache 15 | .DS_Store 16 | .idea 17 | .env 18 | .env.local 19 | .env.development.local 20 | .env.test.local 21 | .env.production.local 22 | 23 | npm-debug.log* 24 | yarn-debug.log* 25 | yarn-error.log* 26 | -------------------------------------------------------------------------------- /backend/models/DeductionsModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const DeductionsSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | }, 10 | amount: { 11 | type: String, 12 | }, 13 | staff: { 14 | type: Array, 15 | }, 16 | }, 17 | { timestamps: true } 18 | ); 19 | 20 | module.exports = mongoose.model("deductions", DeductionsSchema); 21 | -------------------------------------------------------------------------------- /backend/models/CampusesModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const CampusSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | required: true, 10 | }, 11 | location: { 12 | type: String, 13 | }, 14 | description: { 15 | type: String, 16 | }, 17 | }, 18 | { timestamps: true } 19 | ); 20 | 21 | module.exports = mongoose.model("campus", CampusSchema); 22 | -------------------------------------------------------------------------------- /backend/models/PayRow.Model.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const PayrowSchema = new Schema( 6 | { 7 | type: { 8 | type: String, 9 | default: "pay", 10 | }, 11 | name: String, 12 | code: String, 13 | salary: String, 14 | allowance: String, 15 | bonus: String, 16 | }, 17 | { timestamps: true } 18 | ); 19 | 20 | module.exports = mongoose.model("payrow", PayrowSchema); 21 | -------------------------------------------------------------------------------- /frontend/src/containers/TheFooter.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { CFooter } from "@coreui/react"; 3 | 4 | const TheFooter = () => { 5 | let year = new Date(); 6 | 7 | return ( 8 | 9 |

10 | © 2015 - {year.getFullYear()} Darrel Technologies Limited. All Rights 11 | Reserved. 12 |

13 |
14 | ); 15 | }; 16 | 17 | export default React.memo(TheFooter); 18 | -------------------------------------------------------------------------------- /backend/models/OptionsModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const OptionsModel = new Schema( 6 | { 7 | events: { 8 | type: [ 9 | { 10 | type: String, 11 | }, 12 | ], 13 | }, 14 | date: { 15 | type: Date, 16 | default: Date.now, 17 | }, 18 | }, 19 | { timestamps: true } 20 | ); 21 | 22 | module.exports = mongoose.model("optionsdata", OptionsModel); 23 | -------------------------------------------------------------------------------- /backend/models/DormitoriesModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const DormitoriesSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | required: true, 10 | }, 11 | campus: { 12 | type: String, 13 | }, 14 | description: { 15 | type: String, 16 | }, 17 | }, 18 | { timestamps: true } 19 | ); 20 | 21 | module.exports = mongoose.model("dormitories", DormitoriesSchema); 22 | -------------------------------------------------------------------------------- /backend/models/CurrentModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const AcademicYearSchema = new Schema( 6 | { 7 | currentYear: { 8 | type: String, 9 | }, 10 | currentTerm: { 11 | type: String, 12 | }, 13 | code: { 14 | type: String, 15 | default: "admin", 16 | }, 17 | }, 18 | { timestamps: true } 19 | ); 20 | 21 | module.exports = mongoose.model("academicYear", AcademicYearSchema); 22 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/shared/GoBack.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import ArrowForwardIosIcon from "@material-ui/icons/ArrowForwardIos"; 3 | import { Link } from "react-router-dom"; 4 | 5 | function GoBack({ link, name }) { 6 | return ( 7 |
8 | 9 | {name} 10 | 11 | 12 |
13 | ); 14 | } 15 | 16 | export default GoBack; 17 | -------------------------------------------------------------------------------- /frontend/src/scss/style.scss: -------------------------------------------------------------------------------- 1 | // If you want to override variables do it here 2 | @import "./variables"; 3 | 4 | // Import CoreUI styles 5 | @import "~@coreui/coreui/scss/coreui.scss"; 6 | 7 | @import "react-big-calendar/lib/sass/styles"; 8 | @import "react-big-calendar/lib/addons/dragAndDrop/styles"; 9 | 10 | // Some temp fixes 11 | @import "fixes"; 12 | 13 | // If you want to add something do it here 14 | @import "custom"; 15 | @import "./admin"; 16 | @import "./layouts"; 17 | @import "./students"; 18 | @import "./chat"; 19 | -------------------------------------------------------------------------------- /backend/models/TaskModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const TaskSchema = new Schema( 6 | { 7 | teacherID: String, 8 | courseID: String, 9 | classID: String, 10 | score: String, 11 | taskData: String, 12 | date: { 13 | type: Date, 14 | default: Date.now, 15 | }, 16 | deadline: { 17 | type: Date, 18 | }, 19 | }, 20 | { timestamps: true } 21 | ); 22 | 23 | module.exports = mongoose.model("tasks", TaskSchema); 24 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # School-management-System-MERN 2 | 3 | ### school management system for schools 4 | 5 | School Management System built on MERN stack (Mongo, React/Redux, Node). 6 | 7 | ##### http://demo.dtechghana.com/serp 8 | 9 | we need all features from above url 10 | 11 | ##### https://preview.themeforest.net/item/akkhor-school-management-admin-template/full_screen_preview/23687250?_ga=2.255758081.864210670.1612108516-299139616.1603134458 12 | 13 | and will use this template design 14 | 15 | live site: 16 | 17 | https://inovotek-sms.netlify.app/ 18 | -------------------------------------------------------------------------------- /frontend/src/components/messages/inbox/Message.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import {timeStamp} from '../../../utils' 3 | 4 | function Message({message, currentUser}) { 5 | return ( 6 |
7 |
8 | {message?.message} 9 |
10 |
{timeStamp(message.date)}
11 |
12 | ) 13 | } 14 | 15 | export default Message 16 | -------------------------------------------------------------------------------- /backend/models/UsersModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const UsersSchema = new Schema( 6 | { 7 | username: { 8 | type: String, 9 | }, 10 | password: { 11 | type: String, 12 | }, 13 | type: { 14 | type: String, 15 | }, 16 | lastlogin: { 17 | type: Date, 18 | }, 19 | restrictions: { 20 | type: Object, 21 | }, 22 | }, 23 | { timestamps: true } 24 | ); 25 | 26 | module.exports = mongoose.model("users", UsersSchema); 27 | -------------------------------------------------------------------------------- /backend/middlewares/utils.js: -------------------------------------------------------------------------------- 1 | const stringtoLowerCaseSpace = (string) => { 2 | if (string) { 3 | return string.toLowerCase().replace(/\s/g, ""); 4 | } else return 0; 5 | }; 6 | 7 | const stringtoLowerCase = (string) => { 8 | if (string) { 9 | return string.toLowerCase(); 10 | } else return 0; 11 | }; 12 | 13 | const stringSpace = (string) => { 14 | if (string) { 15 | return string.replace(/\s/g, ""); 16 | } else return 0; 17 | }; 18 | 19 | module.exports = { 20 | stringSpace, 21 | stringtoLowerCase, 22 | stringtoLowerCaseSpace, 23 | }; 24 | -------------------------------------------------------------------------------- /backend/models/ScholarshipsModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const ScholarshipsSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | required: true, 10 | }, 11 | percentage: { 12 | type: String, 13 | }, 14 | code: { 15 | type: String, 16 | required: true, 17 | }, 18 | types: { 19 | type: Object, 20 | }, 21 | }, 22 | { timestamps: true } 23 | ); 24 | 25 | module.exports = mongoose.model("scholarships", ScholarshipsSchema); 26 | -------------------------------------------------------------------------------- /frontend/src/components/userInfoTabs/GuadanceTab.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import GuadianCard from '../../AdminComponents/shared/GuadianCard' 3 | 4 | function GuadanceTab({user}) { 5 | console.log(user, "guadance tab") 6 | return ( 7 |
8 | {user?.length > 0 ? user.map(e => { 9 | return( 10 | 11 | ) 12 | }) :
No guadian info
} 13 |
14 | ) 15 | } 16 | 17 | export default GuadanceTab 18 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/academics/ClassDetails.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { useParams } from "react-router-dom"; 3 | import ClassDetails from "../../components/class/ClassDetails"; 4 | 5 | function AllClasses() { 6 | const { id } = useParams(); 7 | 8 | return ( 9 |
10 | {id ? ( 11 | 12 | ) : ( 13 |
14 | No Class Details yet{" "} 15 |
16 | )} 17 |
18 | ); 19 | } 20 | 21 | export default AllClasses; 22 | -------------------------------------------------------------------------------- /backend/models/PrefectsModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const PrefectsSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | required: true, 10 | }, 11 | position: { 12 | type: String, 13 | }, 14 | userID: { 15 | type: String, 16 | }, 17 | startYear: { 18 | type: String, 19 | }, 20 | endYear: { 21 | type: String, 22 | }, 23 | }, 24 | { timestamps: true } 25 | ); 26 | 27 | module.exports = mongoose.model("prefects", PrefectsSchema); 28 | -------------------------------------------------------------------------------- /backend/models/StoreItemsModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const StoreitemsSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | required: true, 10 | }, 11 | description: { 12 | type: String, 13 | }, 14 | quantity: { 15 | type: Number, 16 | }, 17 | unit: { 18 | type: String, 19 | }, 20 | price: { 21 | type: Number, 22 | }, 23 | }, 24 | { timestamps: true } 25 | ); 26 | 27 | module.exports = mongoose.model("storeitems", StoreitemsSchema); 28 | -------------------------------------------------------------------------------- /frontend/src/containers/index.js: -------------------------------------------------------------------------------- 1 | import TheContent from "./TheContent"; 2 | import TheFooter from "./TheFooter"; 3 | import TheHeader from "./TheHeader"; 4 | import TheHeaderDropdown from "./TheHeaderDropdown"; 5 | import TheHeaderDropdownMssg from "./TheHeaderDropdownMssg"; 6 | import TheHeaderDropdownNotif from "./TheHeaderDropdownNotif"; 7 | //import TheLayout from './TheLayout' 8 | import TheSidebar from "./TheSidebar"; 9 | 10 | export { 11 | TheContent, 12 | TheFooter, 13 | TheHeader, 14 | TheHeaderDropdown, 15 | TheHeaderDropdownMssg, 16 | TheHeaderDropdownNotif, 17 | TheSidebar, 18 | }; 19 | -------------------------------------------------------------------------------- /backend/models/NoticeModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const NotificationsSchema = new Schema( 6 | { 7 | date: { 8 | type: Date, 9 | default: Date.now, 10 | }, 11 | title: { 12 | type: String, 13 | }, 14 | description: { 15 | type: String, 16 | }, 17 | createdBy: { 18 | type: String, 19 | }, 20 | receiver: { 21 | type: [], 22 | default: "All", 23 | }, 24 | }, 25 | { timestamps: true } 26 | ); 27 | 28 | module.exports = mongoose.model("notices", NotificationsSchema); 29 | -------------------------------------------------------------------------------- /backend/models/NotificationMessageModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const NotificationsSchema = new Schema( 6 | { 7 | date: { 8 | type: Date, 9 | default: Date.now, 10 | }, 11 | sender: { 12 | type: String, 13 | }, 14 | isSend: { 15 | type: Boolean, 16 | default: false, 17 | }, 18 | messageID: { 19 | type: String, 20 | }, 21 | receiver: { 22 | type: String, 23 | }, 24 | }, 25 | { timestamps: true } 26 | ); 27 | 28 | module.exports = mongoose.model("newMessage", NotificationsSchema); 29 | -------------------------------------------------------------------------------- /frontend/src/App.test.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import { shallow } from 'enzyme/build' 3 | import App from './App' 4 | import ChartLineSimple from './views/charts/ChartLineSimple' 5 | import Dashboard from './views/dashboard/Dashboard.js' 6 | 7 | 8 | it('mounts App without crashing', () => { 9 | const wrapper = shallow() 10 | wrapper.unmount() 11 | }) 12 | 13 | it('mounts Dashboard without crashing', () => { 14 | const wrapper = shallow() 15 | wrapper.unmount() 16 | }) 17 | 18 | it('mounts Charts without crashing', () => { 19 | const wrapper = shallow( ) 20 | wrapper.unmount() 21 | }) 22 | -------------------------------------------------------------------------------- /frontend/src/ProtectedRoutes.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import {Route , Redirect} from 'react-router-dom' 3 | 4 | export const SignedInRoutes = ({Component, path, isAuth, exact, name}) => { 5 | if(!isAuth) { 6 | return 7 | } 8 | return } /> 13 | } 14 | 15 | export const SignedOutRoutes = ({component, path, isAuth, exact}) => { 16 | if(isAuth) { 17 | return 18 | } 19 | return 20 | } -------------------------------------------------------------------------------- /frontend/src/components/messages/inbox/Messaging.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { Switch, Route } from "react-router-dom"; 3 | import Sidebar from "./Sidebar"; 4 | import Message from "./MessageContainer"; 5 | import DefaultView from "./DefaultView"; 6 | 7 | function Messaging() { 8 | return ( 9 |
10 |
11 | 12 | 13 | 14 | 15 | 16 |
17 |
18 | ); 19 | } 20 | 21 | export default Messaging; 22 | -------------------------------------------------------------------------------- /frontend/src/components/settings/Settings.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import Logout from "./Logout"; 3 | import ChangePassword from "./ChangePassword"; 4 | import { useSelector, useDispatch } from "react-redux"; 5 | import { selectUser, logout } from "../../store/slices/userSlice"; 6 | 7 | function SettingsPage() { 8 | const user = useSelector(selectUser); 9 | const dispatch = useDispatch(); 10 | 11 | return ( 12 |
13 |

Account Settings

14 | 15 | 16 |
17 | ); 18 | } 19 | 20 | export default SettingsPage; 21 | -------------------------------------------------------------------------------- /frontend/src/Loading.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import Backdrop from "@material-ui/core/Backdrop"; 3 | import CircularProgress from "@material-ui/core/CircularProgress"; 4 | import { makeStyles } from "@material-ui/core/styles"; 5 | 6 | const useStyles = makeStyles((theme) => ({ 7 | backdrop: { 8 | zIndex: theme.zIndex.drawer + 1, 9 | color: "#fff", 10 | }, 11 | })); 12 | 13 | export default function SimpleBackdrop() { 14 | const classes = useStyles(); 15 | 16 | return ( 17 |
18 | 19 | 20 | 21 |
22 | ); 23 | } 24 | -------------------------------------------------------------------------------- /backend/models/AttendenceModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const AttendanceSchema = new Schema( 6 | { 7 | classID: { 8 | type: String, 9 | required: true, 10 | }, 11 | role: { 12 | type: String, 13 | }, 14 | user: String, 15 | users: { 16 | type: [ 17 | { 18 | userID: String, 19 | name: String, 20 | surname: String, 21 | status: Boolean, 22 | }, 23 | ], 24 | default: [], 25 | }, 26 | }, 27 | { timestamps: true } 28 | ); 29 | 30 | module.exports = mongoose.model("attendance", AttendanceSchema); 31 | -------------------------------------------------------------------------------- /backend/models/FilesModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const FilesSchema = new Schema( 6 | { 7 | topic: { 8 | type: String, 9 | }, 10 | date: { 11 | type: Date, 12 | default: Date.now, 13 | }, 14 | notes: { 15 | type: String, 16 | }, 17 | courseID: { 18 | type: String, 19 | }, 20 | classID: { 21 | type: String, 22 | }, 23 | senderID: { 24 | type: String, 25 | }, 26 | file: { 27 | type: String, 28 | }, 29 | }, 30 | { timestamps: true } 31 | ); 32 | 33 | module.exports = mongoose.model("notes", FilesSchema); 34 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/students/campuses/AddCampus.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import CampusForm from './CampusForm'; 3 | 4 | 5 | function AddCampus({name, location , setname, setlocation, onSubmit, loading}) { 6 | return ( 7 |
8 |

Add Campus

9 | 17 |
18 | ) 19 | } 20 | 21 | export default AddCampus 22 | -------------------------------------------------------------------------------- /backend/models/CalenderModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const CalendarSchema = new Schema( 6 | { 7 | title: { 8 | type: String, 9 | required: true, 10 | }, 11 | resource: { 12 | type: String, 13 | }, 14 | description: { 15 | type: String, 16 | }, 17 | start: { 18 | type: Date, 19 | }, 20 | end: { 21 | type: Date, 22 | }, 23 | allDay: { 24 | type: Boolean, 25 | }, 26 | day: { 27 | type: Date, 28 | default: Date.now, 29 | }, 30 | }, 31 | { timestamps: true } 32 | ); 33 | 34 | module.exports = mongoose.model("calendar", CalendarSchema); 35 | -------------------------------------------------------------------------------- /backend/config/mongodb.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("mongoose"); 2 | const dotenv = require("dotenv"); 3 | 4 | //LOCAL_DB_CONNECT -localhost database 5 | //DB_CONNECT -online database 6 | dotenv.config(); 7 | const connection_url = process.env.LOCAL_DB_CONNECT; 8 | 9 | mongoose.connect(connection_url, { 10 | useCreateIndex: true, 11 | useNewUrlParser: true, 12 | useUnifiedTopology: true, 13 | useFindAndModify: false, 14 | }); 15 | 16 | mongoose.connection.once("open", () => { 17 | console.log("db connnected localhost db"); 18 | // gfs = new mongoose.mongo.GridFSBucket(connect.db, { 19 | // bucketName: "uploads" 20 | // }) 21 | }); 22 | 23 | //export default mongoose; 24 | module.exports = mongoose; 25 | -------------------------------------------------------------------------------- /backend/models/NextofKinModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const NextofKinchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | }, 10 | surname: { 11 | type: String, 12 | }, 13 | address: { 14 | type: String, 15 | }, 16 | telephone: { 17 | type: String, 18 | }, 19 | occupation: { 20 | type: String, 21 | }, 22 | relationship: { 23 | String, 24 | }, 25 | gender: { 26 | type: String, 27 | }, 28 | email: { 29 | type: String, 30 | }, 31 | }, 32 | { timestamps: true } 33 | ); 34 | 35 | module.exports = mongoose.model("nextofkins", NextofKinchema); 36 | -------------------------------------------------------------------------------- /backend/models/CorrespondanceModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const CorrespondanceSchema = new Schema( 6 | { 7 | address: { 8 | type: String, 9 | required: true, 10 | }, 11 | salutation: { 12 | type: String, 13 | }, 14 | subject: { 15 | type: String, 16 | required: true, 17 | }, 18 | body: { 19 | type: String, 20 | }, 21 | closing: { 22 | type: String, 23 | }, 24 | signature: {}, 25 | date: { 26 | type: Date, 27 | default: Date.now, 28 | }, 29 | }, 30 | { timestamps: true } 31 | ); 32 | 33 | module.exports = mongoose.model("correspondance", CorrespondanceSchema); 34 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/message/Chat.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { Switch, Route } from "react-router-dom"; 3 | import Sidebar from "../../components/messages/inbox/Sidebar"; 4 | import Message from "../../components/messages/inbox/MessageContainer"; 5 | import DefaultView from "../../components/messages/inbox/DefaultView"; 6 | 7 | function Messaging() { 8 | return ( 9 |
10 |
11 | 12 | 13 | 14 | 15 | 16 |
17 |
18 | ); 19 | } 20 | 21 | export default Messaging; 22 | -------------------------------------------------------------------------------- /frontend/src/store/slices/appSlice.js: -------------------------------------------------------------------------------- 1 | import { createSlice } from "@reduxjs/toolkit"; 2 | 3 | export const appSlice = createSlice({ 4 | name: "app", 5 | initialState: { 6 | sidebarShow: "responsive", 7 | showLoading: false, 8 | }, 9 | reducers: { 10 | set: (state, action) => { 11 | state.sidebarShow = action.payload; 12 | }, 13 | setLoading: (state, action) => { 14 | console.log(action.payload); 15 | state.showLoading = action.payload; 16 | }, 17 | }, 18 | }); 19 | 20 | export const { set, setLoading } = appSlice.actions; 21 | export const selectSidebarShow = (state) => state.app.sidebarShow; 22 | export const selectShowLoading = (state) => state.app.showLoading; 23 | 24 | export default appSlice.reducer; 25 | -------------------------------------------------------------------------------- /backend/models/SchoolModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const SchoolSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | }, 10 | fullName: { 11 | type: String, 12 | }, 13 | motto: { 14 | type: String, 15 | }, 16 | role: { 17 | type: String, 18 | }, 19 | userID: { 20 | type: String, 21 | }, 22 | resetPassowrdToken: String, 23 | resetPasswordExpires: Date, 24 | logo: String, 25 | address: String, 26 | photoUrl: String, 27 | email: String, 28 | telephone: String, 29 | password: String, 30 | }, 31 | { timestamps: true } 32 | ); 33 | 34 | module.exports = mongoose.model("accounts", SchoolSchema); 35 | -------------------------------------------------------------------------------- /backend/models/NonBillModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const NonBillSchema = new Schema( 6 | { 7 | student: { 8 | type: String, 9 | }, 10 | term: { 11 | type: String, 12 | }, 13 | year: { 14 | type: String, 15 | }, 16 | amount: { 17 | type: String, 18 | }, 19 | remarks: { 20 | type: String, 21 | }, 22 | paymentType: { 23 | type: String, 24 | }, 25 | bank: { 26 | type: String, 27 | }, 28 | cheque: { 29 | type: String, 30 | }, 31 | date: { 32 | type: String, 33 | }, 34 | }, 35 | { timestamps: true } 36 | ); 37 | 38 | module.exports = mongoose.model("nonbillpayment", NonBillSchema); 39 | -------------------------------------------------------------------------------- /backend/models/SSNITModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const SBASchema = new Schema( 6 | { 7 | year: { 8 | type: String, 9 | }, 10 | month: { 11 | type: String, 12 | }, 13 | percentage: { 14 | type: Number, 15 | }, 16 | teachers: { 17 | type: [ 18 | { 19 | userID: String, 20 | name: String, 21 | SSNITNumber: String, 22 | position: String, 23 | salary: Number, 24 | contribution: Number, 25 | grade: String, 26 | interpretation: String, 27 | }, 28 | ], 29 | }, 30 | }, 31 | { timestamps: true } 32 | ); 33 | 34 | module.exports = mongoose.model("ssnit", SBASchema); 35 | -------------------------------------------------------------------------------- /backend/routes/Uploads.js: -------------------------------------------------------------------------------- 1 | const express = require("express"); 2 | const { cloudinary } = require("../middlewares/cloudinary"); 3 | 4 | const route = express.Router(); 5 | 6 | route.post("/", async (req, res) => { 7 | try { 8 | let timeStamp = new Date(); 9 | timeStamp = timeStamp.toJSON(); 10 | 11 | // Set folder for uploads 12 | let day = timeStamp.substring(0, 10); 13 | 14 | let promise = await cloudinary.v2.uploader.upload(req.body.dataUrl, { 15 | public_id: `${day}/files-${timeStamp}`, 16 | tags: "files", // tag 17 | }); 18 | console.log("finish loading", promise); 19 | return res.json(promise); 20 | } catch (err) { 21 | console.log("err", err); 22 | res.send({ error: err }); 23 | } 24 | }); 25 | 26 | module.exports = route; 27 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/Profile/FinanceCard.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { Link } from "react-router-dom"; 3 | import DescriptionIcon from "@material-ui/icons/Description"; 4 | 5 | function FinanceCard({ route, name, title }) { 6 | return ( 7 |
8 |
9 | 10 | {title && ( 11 |
12 |
{title}
13 |
14 | )} 15 | {name} 16 |
17 | 18 | 19 |
20 |
21 | ); 22 | } 23 | 24 | export default FinanceCard; 25 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/Profile/Profile.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import ProfileInfo from "./ProfileInfo"; 3 | import ProfileTabs from "./ProfileTabs"; 4 | import axios from "../../store/axios"; 5 | import { useSelector } from "react-redux"; 6 | import { selectUser } from "../../store/slices/userSlice"; 7 | 8 | function Profile() { 9 | const [admin, setadmin] = useState({}); 10 | const user = useSelector(selectUser); 11 | 12 | useEffect(() => { 13 | axios.get(`/school`).then((res) => { 14 | setadmin(res.data); 15 | }); 16 | }, [user]); 17 | 18 | return ( 19 |
20 | 21 | 22 |
23 | ); 24 | } 25 | 26 | export default Profile; 27 | -------------------------------------------------------------------------------- /frontend/src/components/tables/ExcelExport.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import ReactExport from "react-export-excel"; 3 | import moment from "moment"; 4 | 5 | const ExcelFile = ReactExport.ExcelFile; 6 | const ExcelSheet = ReactExport.ExcelFile.ExcelSheet; 7 | const ExcelColumn = ReactExport.ExcelFile.ExcelColumn; 8 | 9 | function ExcelExport({ data, btn, name, columns }) { 10 | return ( 11 | {btn || "Download"}} 13 | > 14 | 15 | {columns.map((col) => ( 16 | 17 | ))} 18 | 19 | 20 | ); 21 | } 22 | 23 | export default ExcelExport; 24 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/Profile/SummaryCard.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import Card from "@material-ui/core/Card"; 3 | 4 | function SummaryCard({ name, percentage, value }) { 5 | return ( 6 |
7 | 8 |
9 |
10 |
{name}
11 |
12 |
{percentage &&
%
}
13 |
14 |
15 |

{value}

16 |
{percentage}
17 |
18 |
19 |
20 | ); 21 | } 22 | 23 | export default SummaryCard; 24 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/messages/Chat.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { Switch, Route } from "react-router-dom"; 3 | import Sidebar from "../../components/messages/inbox/Sidebar"; 4 | import Message from "../../components/messages/inbox/MessageContainer"; 5 | import DefaultView from "../../components/messages/inbox/DefaultView"; 6 | 7 | function Messaging() { 8 | return ( 9 |
10 |
11 | 12 |
13 | 14 | 15 | 16 | 17 |
18 |
19 |
20 | ); 21 | } 22 | 23 | export default Messaging; 24 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/messages/Chat.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { Switch, Route } from "react-router-dom"; 3 | import Sidebar from "../../components/messages/inbox/Sidebar"; 4 | import Message from "../../components/messages/inbox/MessageContainer"; 5 | import DefaultView from "../../components/messages/inbox/DefaultView"; 6 | 7 | function Messaging() { 8 | return ( 9 |
10 |
11 | 12 |
13 | 14 | 15 | 16 | 17 |
18 |
19 |
20 | ); 21 | } 22 | 23 | export default Messaging; 24 | -------------------------------------------------------------------------------- /frontend/src/components/settings/Logout.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { useHistory } from "react-router-dom"; 3 | 4 | function Logout({ dispatch, loggout, user }) { 5 | const history = useHistory(); 6 | 7 | const handleDelete = () => { 8 | dispatch(loggout()); 9 | localStorage.clear(); 10 | history.push("/login"); 11 | }; 12 | 13 | return ( 14 |
15 |
16 |
17 | You are logged-in as {user?.id}- {user?.name}{" "} 18 | {user?.lastName ? user?.lastName : ""} 19 |
20 | 23 |
24 |
25 | ); 26 | } 27 | 28 | export default Logout; 29 | -------------------------------------------------------------------------------- /backend/models/PaymentPlanModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const PaymentSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | }, 10 | plans: { 11 | type: [ 12 | { 13 | name: String, 14 | plan: String, 15 | description: String, 16 | price: String, 17 | }, 18 | ], 19 | }, 20 | services: { 21 | type: [ 22 | { 23 | name: String, 24 | plan1: String, 25 | plan2: String, 26 | plan3: String, 27 | }, 28 | ], 29 | }, 30 | dataID: { 31 | type: String, 32 | default: "paymentPlan", 33 | }, 34 | }, 35 | { timestamps: true } 36 | ); 37 | 38 | module.exports = mongoose.model("canteenpayplan", PaymentSchema); 39 | -------------------------------------------------------------------------------- /backend/models/StoreSalesModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const StoreSalesSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | }, 10 | totalCost: { 11 | type: Number, 12 | }, 13 | amountPaid: { 14 | type: Number, 15 | }, 16 | seller: { 17 | type: String, 18 | }, 19 | items: { 20 | type: [ 21 | { 22 | name: { 23 | type: String, 24 | }, 25 | qty: { 26 | type: Number, 27 | }, 28 | rate: { 29 | type: Number, 30 | }, 31 | amount: { 32 | type: Number, 33 | }, 34 | }, 35 | ], 36 | }, 37 | }, 38 | { timestamps: true } 39 | ); 40 | 41 | module.exports = mongoose.model("storesales", StoreSalesSchema); 42 | -------------------------------------------------------------------------------- /backend/models/StaffPayModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const BankingSchema = new Schema( 6 | { 7 | useID: { 8 | type: String, 9 | required: true, 10 | }, 11 | basicSalary: { 12 | type: String, 13 | }, 14 | bank: { 15 | type: String, 16 | }, 17 | employeeSSF: { 18 | type: String, 19 | }, 20 | transactions: { 21 | type: [ 22 | { 23 | date: { 24 | type: Date, 25 | default: Date.now, 26 | }, 27 | allowance: String, 28 | grossIncome: String, 29 | deductions: String, 30 | tax: String, 31 | netSalary: String, 32 | }, 33 | ], 34 | }, 35 | }, 36 | { timestamps: true } 37 | ); 38 | 39 | module.exports = mongoose.model("staffpay", BankingSchema); 40 | -------------------------------------------------------------------------------- /frontend/src/store/slices/userSlice.js: -------------------------------------------------------------------------------- 1 | import { createSlice } from '@reduxjs/toolkit'; 2 | 3 | export const userSlice = createSlice({ 4 | name: 'user', 5 | initialState: { 6 | user: null 7 | }, 8 | reducers: { 9 | loggin: (state, action )=> { 10 | state.user = action.payload; 11 | }, 12 | logout: state => { 13 | console.log(state); 14 | state.user = null; 15 | }, 16 | update: (state, action) => { 17 | state.user = Object.assign({}, state.user, action.payload); 18 | } 19 | }, 20 | }); 21 | 22 | 23 | export const { loggin, logout, update } = userSlice.actions; 24 | 25 | export const selectUser = state => state.user.user; 26 | 27 | 28 | export const handleSignout = () => dispatch => { 29 | console.log('signed out') 30 | localStorage.clear(); 31 | dispatch(logout()); 32 | } 33 | export default userSlice.reducer; 34 | -------------------------------------------------------------------------------- /backend/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "backend", 3 | "version": "1.0.0", 4 | "description": "", 5 | "main": "server.js", 6 | "scripts": { 7 | "start": "node server.js", 8 | "dev": "nodemon start" 9 | }, 10 | "author": "", 11 | "license": "ISC", 12 | "dependencies": { 13 | "@hapi/joi": "^17.1.1", 14 | "bcrypt": "^5.0.0", 15 | "cloudinary": "^1.25.2", 16 | "cors": "^2.8.5", 17 | "crypto-js": "^4.0.0", 18 | "datauri": "^3.0.0", 19 | "dotenv": "^8.2.0", 20 | "express": "^4.17.1", 21 | "express-pino-logger": "^6.0.0", 22 | "method-override": "^3.0.0", 23 | "moment": "^2.29.1", 24 | "mongoose": "^5.11.13", 25 | "multer": "^1.4.2", 26 | "multer-gridfs-storage": "^4.2.0", 27 | "nodemailer": "^6.5.0", 28 | "nodemon": "^2.0.7", 29 | "pusher": "^4.0.2", 30 | "twilio": "^3.58.0", 31 | "uuid": "^8.3.2" 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/attendance/Attendance.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import AttendanceTable from "../../components/tables/AttendanceTable"; 3 | import axios from "../../store/axios"; 4 | import { useSelector } from "react-redux"; 5 | import { selectUser } from "../../store/slices/userSlice"; 6 | 7 | function Attendance() { 8 | const [attendanceData, setattendanceData] = useState([]); 9 | const user = useSelector(selectUser); 10 | 11 | useEffect(() => { 12 | axios.get(`/attendance/user/${user?.userID}`).then((res) => { 13 | console.log(res); 14 | setattendanceData(res.data); 15 | }); 16 | }, [user]); 17 | 18 | return ( 19 |
20 |

Attendance List

21 | 22 |
23 | ); 24 | } 25 | 26 | export default Attendance; 27 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/attendence/AttendancePage.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import AttendanceTable from "../../components/tables/AttendanceTable"; 3 | import axios from "../../store/axios"; 4 | import { useSelector } from "react-redux"; 5 | import { selectUser } from "../../store/slices/userSlice"; 6 | 7 | function Attendance() { 8 | const [attendanceData, setattendanceData] = useState([]); 9 | const user = useSelector(selectUser); 10 | 11 | useEffect(() => { 12 | axios.get(`/attendance/user/${user?.userID}`).then((res) => { 13 | console.log(res); 14 | setattendanceData(res.data); 15 | }); 16 | }, [user]); 17 | 18 | return ( 19 |
20 |

Attendance List

21 | 22 |
23 | ); 24 | } 25 | 26 | export default Attendance; 27 | -------------------------------------------------------------------------------- /backend/models/CoursesModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const CourserSchema = new Schema( 6 | { 7 | date: { 8 | type: Date, 9 | default: Date.now, 10 | }, 11 | name: { 12 | type: String, 13 | required: true, 14 | }, 15 | code: { 16 | type: String, 17 | required: true, 18 | }, 19 | classID: { 20 | type: String, 21 | }, 22 | classes: { 23 | type: [ 24 | { 25 | teacher: String, 26 | class: String, 27 | _id: String, 28 | }, 29 | ], 30 | }, 31 | department: { 32 | type: String, 33 | }, 34 | type: { 35 | type: String, 36 | }, 37 | teacher: { 38 | type: String, 39 | }, 40 | default: [], 41 | }, 42 | { timestamps: true } 43 | ); 44 | 45 | module.exports = mongoose.model("courses", CourserSchema); 46 | -------------------------------------------------------------------------------- /frontend/src/index.js: -------------------------------------------------------------------------------- 1 | import "react-app-polyfill/ie11"; // For IE 11 support 2 | import "react-app-polyfill/stable"; 3 | import "core-js"; 4 | import "./polyfill"; 5 | import React from "react"; 6 | import ReactDOM from "react-dom"; 7 | import App from "./App"; 8 | import * as serviceWorker from "./serviceWorker"; 9 | import { icons } from "./assets/icons"; 10 | import { Provider } from "react-redux"; 11 | import { initFunc } from "./store/apiCall"; 12 | import store from "./store/index"; 13 | initFunc(); 14 | React.icons = icons; 15 | 16 | ReactDOM.render( 17 | 18 | 19 | , 20 | document.getElementById("root") 21 | ); 22 | 23 | // If you want your app to work offline and load faster, you can change 24 | // unregister() to register() below. Note this comes with some pitfalls. 25 | // Learn more about service workers: http://bit.ly/CRA-PWA 26 | //serviceWorker.unregister(); 27 | serviceWorker.register(); 28 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/canteen/CanteenNav.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import {NavLink} from 'react-router-dom' 3 | 4 | function CanteenNav() { 5 | return ( 6 |
7 | Add Canteen Member 8 | All Members 9 | Payments Plan 10 | Make Payment 11 | All Payments 12 | 13 |
14 | ) 15 | } 16 | 17 | export default CanteenNav 18 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/staff/Attendence.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import AttendanceTable from '../shared/AttendanceTable' 3 | import SearchAttendance from './SearchAttendance'; 4 | 5 | function Attendence() { 6 | 7 | 8 | const attendanceData = [ 9 | { studentID: "BK2021",name:'Frozen', lastname:'yoghurt'}, 10 | { studentID: "BK2021",name:'Frozen', lastname:'yoghurt'}, 11 | { studentID: "BK2021",name:'Frozen', lastname:'yoghurt'}, 12 | { studentID: "BK2021",name:'Frozen', lastname:'yoghurt'}, 13 | { studentID: "BK2021",name:'Frozen', lastname:'yoghurt'}, 14 | { studentID: "BK2021",name:'Frozen', lastname:'yoghurt'}, 15 | { studentID: "BK2021",name:'Frozen', lastname:'yoghurt'}, 16 | ]; 17 | return ( 18 |
19 | 20 | 21 |
22 | ) 23 | } 24 | 25 | export default Attendence 26 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/academics/AllClasses.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import axios from "../../store/axios"; 3 | import { useSelector } from "react-redux"; 4 | import ClassCard from "./ClassCard"; 5 | import { selectUser } from "../../store/slices/userSlice"; 6 | 7 | function AllClasses() { 8 | const user = useSelector(selectUser); 9 | const [classes, setclasses] = useState([]); 10 | 11 | useEffect(() => { 12 | const getData = async () => { 13 | let classesData = await axios.get(`/classes/teacher/${user?.userID}`); 14 | setclasses(classesData.data.docs); 15 | }; 16 | getData(); 17 | }, [user]); 18 | 19 | return ( 20 |
21 |
22 | {classes?.length > 0 ? ( 23 | classes?.map((e) => ) 24 | ) : ( 25 | 26 | )} 27 |
28 |
29 | ); 30 | } 31 | 32 | export default AllClasses; 33 | -------------------------------------------------------------------------------- /backend/models/CanteenModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | const { Schema } = mongoose; 3 | 4 | const CanteenSchema = new Schema( 5 | { 6 | name: { 7 | type: String, 8 | required: true, 9 | }, 10 | classID: { 11 | type: String, 12 | }, 13 | memberID: { 14 | type: String, 15 | }, 16 | userID: { 17 | type: String, 18 | required: true, 19 | }, 20 | role: { 21 | type: String, 22 | }, 23 | paymentMethod: { 24 | type: String, 25 | }, 26 | payments: { 27 | type: [ 28 | { 29 | date: { 30 | type: Date, 31 | default: Date.now, 32 | }, 33 | receipt: String, 34 | amount: String, 35 | covers: String, 36 | }, 37 | ], 38 | }, 39 | date: { 40 | type: Date, 41 | default: Date.now, 42 | }, 43 | }, 44 | { timestamps: true } 45 | ); 46 | 47 | module.exports = mongoose.model("canteen", CanteenSchema); 48 | -------------------------------------------------------------------------------- /frontend/src/assets/icons/sygnet.js: -------------------------------------------------------------------------------- 1 | export const sygnet = ['160 160', ` 2 | coreui logo 3 | 4 | 5 | 6 | 7 | 8 | 9 | `] 10 | -------------------------------------------------------------------------------- /backend/models/ClassesModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const ClassesSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | required: true, 10 | }, 11 | teacherID: { 12 | type: String, 13 | }, 14 | classCode: { 15 | type: String, 16 | required: true, 17 | }, 18 | campusID: { 19 | type: String, 20 | }, 21 | division: { 22 | type: String, 23 | }, 24 | academic: { 25 | type: String, 26 | }, 27 | group: { 28 | type: String, 29 | }, 30 | prefect: { 31 | type: String, 32 | }, 33 | sba: { 34 | type: Boolean, 35 | }, 36 | sbaStaff: { 37 | type: String, 38 | }, 39 | date: { 40 | type: Date, 41 | default: Date.now, 42 | }, 43 | past: { 44 | type: Boolean, 45 | default: false, 46 | }, 47 | }, 48 | { timestamps: true } 49 | ); 50 | 51 | module.exports = mongoose.model("classes", ClassesSchema); 52 | -------------------------------------------------------------------------------- /frontend/src/polyfill.js: -------------------------------------------------------------------------------- 1 | 2 | (function () { 3 | 4 | if ( typeof window.CustomEvent === "function" ) return false 5 | 6 | function CustomEvent ( event, params ) { 7 | params = params || { bubbles: false, cancelable: false, detail: undefined } 8 | var evt = document.createEvent( 'CustomEvent' ) 9 | evt.initCustomEvent( event, params.bubbles, params.cancelable, params.detail ) 10 | return evt 11 | } 12 | 13 | CustomEvent.prototype = window.Event.prototype 14 | 15 | window.CustomEvent = CustomEvent 16 | })() 17 | 18 | if (!Element.prototype.matches) { 19 | Element.prototype.matches = 20 | Element.prototype.msMatchesSelector || 21 | Element.prototype.webkitMatchesSelector; 22 | } 23 | 24 | if (!Element.prototype.closest) { 25 | Element.prototype.closest = function(s) { 26 | var el = this; 27 | 28 | do { 29 | if (Element.prototype.matches.call(el, s)) return el; 30 | el = el.parentElement || el.parentNode; 31 | } while (el !== null && el.nodeType === 1); 32 | return null; 33 | }; 34 | } 35 | -------------------------------------------------------------------------------- /frontend/src/AppLoading.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import Backdrop from '@material-ui/core/Backdrop'; 3 | import CircularProgress from '@material-ui/core/CircularProgress'; 4 | import Button from '@material-ui/core/Button'; 5 | import { makeStyles } from '@material-ui/core/styles'; 6 | 7 | const useStyles = makeStyles((theme) => ({ 8 | backdrop: { 9 | zIndex: theme.zIndex.drawer + 1, 10 | color: '#fff', 11 | }, 12 | })); 13 | 14 | export default function SimpleBackdrop() { 15 | const classes = useStyles(); 16 | const [open, setOpen] = React.useState(false); 17 | const handleClose = () => { 18 | setOpen(false); 19 | }; 20 | const handleToggle = () => { 21 | setOpen(!open); 22 | }; 23 | 24 | return ( 25 |
26 | 29 | 30 | 31 | 32 |
33 | ); 34 | } 35 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/students/section/AddSection.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | 3 | function AddDormitories({ name, setname, loading, onSubmit }) { 4 | return ( 5 |
6 |
Add Section
7 |
8 |
9 | 10 |
11 | setname(e.target.value)} 14 | type="text" 15 | className="form-control" 16 | id="name" 17 | /> 18 |
19 |
20 |
21 | 28 |
29 |
30 |
31 | ); 32 | } 33 | 34 | export default AddDormitories; 35 | -------------------------------------------------------------------------------- /frontend/src/components/userInfoTabs/ContactInfo.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | 3 | function ContactInfo({user}) { 4 | return ( 5 |
6 |
7 |
Telephone Number:
8 |
{user?.telephone || "N/A"}
9 |
10 |
11 |
Mobile Number:
12 |
{user?.mobilenumber || "N/A"}
13 |
14 |
15 |
Area of Residence:
16 |
{user?.physicalAddress || "N/A"}
17 |
18 |
19 |
Postal Address
20 |
{user?.postalAddress || "N/A"}
21 |
22 |
23 | ) 24 | } 25 | 26 | export default ContactInfo 27 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/students/dormitories/AddDormitories.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | 3 | function AddDormitories({ name, setname, loading, onSubmit }) { 4 | return ( 5 |
6 |
Add Dormitory
7 |
8 |
9 | 10 |
11 | setname(e.target.value)} 14 | type="text" 15 | className="form-control" 16 | id="name" 17 | /> 18 |
19 |
20 |
21 | 28 |
29 |
30 |
31 | ); 32 | } 33 | 34 | export default AddDormitories; 35 | -------------------------------------------------------------------------------- /frontend/src/components/dashboard/Card.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { Link } from "react-router-dom"; 3 | import CountUp from "react-countup"; 4 | 5 | function Card({ icon, title, value, link, isPercentage, text, message }) { 6 | const colors = ["#2ad7c5", "#ffa201", "#f939a1"]; 7 | 8 | let bgColor = colors[Math.floor(Math.random() * colors.length)]; 9 | 10 | return ( 11 |
12 | 13 |
14 | {icon} 15 |
16 |
17 |
{title}
18 |
19 | 20 | {text ? value : } 21 | 22 | {isPercentage && "%"} 23 | 24 |
25 | {message ? message : ""} 26 |
27 | 28 |
29 | ); 30 | } 31 | 32 | export default Card; 33 | -------------------------------------------------------------------------------- /backend/models/SBAModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const SBASchema = new Schema( 6 | { 7 | class: { 8 | type: String, 9 | required: true, 10 | }, 11 | course: { 12 | type: String, 13 | }, 14 | academicYear: { 15 | type: String, 16 | }, 17 | term: { 18 | type: String, 19 | }, 20 | exam: { 21 | type: Number, 22 | }, 23 | examPercentage: { 24 | type: Number, 25 | }, 26 | classWork: { 27 | type: Number, 28 | }, 29 | classWorkPercentage: { 30 | type: Number, 31 | }, 32 | students: { 33 | type: [ 34 | { 35 | userID: String, 36 | name: String, 37 | position: String, 38 | examPercentage: Number, 39 | exam: Number, 40 | classWork: Number, 41 | classWorkPercentage: Number, 42 | total: Number, 43 | }, 44 | ], 45 | }, 46 | }, 47 | { timestamps: true } 48 | ); 49 | 50 | module.exports = mongoose.model("sba", SBASchema); 51 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/staff/SearchForm.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | 3 | function Search() { 4 | return ( 5 |
6 |
7 |
8 | 14 |
15 |
16 | 22 |
23 |
24 | 25 |
26 |
27 |
28 | ) 29 | } 30 | 31 | export default Search 32 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/shared/ProfilePicture.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import IconButton from "@material-ui/core/IconButton"; 3 | import PhotoCamera from "@material-ui/icons/PhotoCamera"; 4 | import Avatar from "@material-ui/core/Avatar"; 5 | import { getImgSrc } from "../../utils"; 6 | 7 | function Profile({ profileimg, setprofileUrl, profileUrl }) { 8 | return ( 9 |
10 |

Profile Photo

11 | 18 | 27 | 28 | 33 |
34 | ); 35 | } 36 | 37 | export default Profile; 38 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/students/upGrade/Upgrade.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { 3 | selectClasses, 4 | selectDormitories, 5 | selectCampuses, 6 | } from "../../../store/slices/schoolSlice"; 7 | import { useSelector } from "react-redux"; 8 | import PromotingStudent from "./PromotingStudent"; 9 | import PromotingClass from "./PromotingClass"; 10 | import PromotingDormitories from "./PromotingDormitories"; 11 | import PromotingCampus from "./PromotingCampus"; 12 | import PromotingPast from "./PromotingPast"; 13 | 14 | function Upgrade() { 15 | const classes = useSelector(selectClasses); 16 | const dormitories = useSelector(selectDormitories); 17 | const campuses = useSelector(selectCampuses); 18 | 19 | return ( 20 |
21 |

Students Promotions

22 | 23 | 24 | 25 | 26 | 27 |
28 | ); 29 | } 30 | 31 | export default Upgrade; 32 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/classes/CalendarPage.js: -------------------------------------------------------------------------------- 1 | import React, {useState, useEffect} from 'react'; 2 | import TableList from '../../AdminComponents/shared/ListTable'; 3 | import axios from '../../store/axios' 4 | 5 | 6 | const tableHeader = [ 7 | {id: "resourse", name: "Type"}, 8 | {id: "title", name: "Event"}, 9 | {id: "start", name: "Starts"}, 10 | {id: "end", name: "Ends"}, 11 | 12 | ] 13 | 14 | function ExamsPage() { 15 | const [loading, setloading] = useState(false); 16 | const [events, setevents] = useState([]); 17 | 18 | useEffect(() => { 19 | setloading(true) 20 | axios.get('/calendar') 21 | .then(res => { 22 | setloading(false) 23 | setevents(res.data) 24 | }) 25 | 26 | }, []) 27 | 28 | return ( 29 |
30 |

Upcoming School Events

31 | 36 |
37 | ) 38 | } 39 | 40 | export default ExamsPage 41 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/academics/ClassCard.js: -------------------------------------------------------------------------------- 1 | import React, { useEffect, useState } from "react"; 2 | import ImportContactsIcon from "@material-ui/icons/ImportContacts"; 3 | import { Link } from "react-router-dom"; 4 | import axios from "../../store/axios"; 5 | 6 | function ClassCard({ id }) { 7 | const [coursName, setcoursName] = useState([]); 8 | 9 | useEffect(() => { 10 | axios.get(`/classes/${id}`).then((res) => { 11 | setcoursName(res.data.docs); 12 | }); 13 | }, [id]); 14 | 15 | return ( 16 |
17 |
18 | {id ? ( 19 | 20 | 21 |
{coursName?.name}
22 | {id} 23 | 24 | ) : ( 25 |
26 | 27 |
Classes
28 | No classes yet 29 |
30 | )} 31 |
32 |
33 | ); 34 | } 35 | 36 | export default ClassCard; 37 | -------------------------------------------------------------------------------- /frontend/src/components/courses/ClassCard.js: -------------------------------------------------------------------------------- 1 | import React, { useEffect, useState } from "react"; 2 | import ImportContactsIcon from "@material-ui/icons/ImportContacts"; 3 | import { Link } from "react-router-dom"; 4 | import axios from "../../store/axios"; 5 | 6 | function ClassCard({ id, classID }) { 7 | const [coursName, setcoursName] = useState([]); 8 | 9 | useEffect(() => { 10 | axios.get(`/courses/courseCode/${id}`).then((res) => { 11 | setcoursName(res.data.docs); 12 | }); 13 | }, [id]); 14 | 15 | console.log(id); 16 | return ( 17 |
18 |
19 | {id ? ( 20 | 21 | 22 |
{coursName?.name}
23 | {classID} 24 | 25 | ) : ( 26 |
27 | 28 |
Courses
29 | No course yet 30 |
31 | )} 32 |
33 |
34 | ); 35 | } 36 | 37 | export default ClassCard; 38 | -------------------------------------------------------------------------------- /backend/models/BankingModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const BankingSchema = new Schema( 6 | { 7 | bankName: { 8 | type: String, 9 | required: true, 10 | }, 11 | accountNumber: { 12 | type: String, 13 | }, 14 | accountName: { 15 | type: String, 16 | }, 17 | transactions: { 18 | type: Array, 19 | // type: [ 20 | // { 21 | // date: { 22 | // type: Date, 23 | // default: Date.now, 24 | // }, 25 | // description: String, 26 | // payee: String, 27 | // transactionNumber: String, 28 | // credit: String, 29 | // debit: String, 30 | // type: String, 31 | // bankAcc: String, 32 | // issuedDate: { 33 | // type: Date, 34 | // default: Date.now, 35 | // }, 36 | // }, 37 | // ], 38 | }, 39 | date: { 40 | type: Date, 41 | default: Date.now, 42 | }, 43 | }, 44 | { timestamps: true }, 45 | { typeKey: "$type" } 46 | ); 47 | 48 | module.exports = mongoose.model("banking", BankingSchema); 49 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/Profile/ProfileInfo.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { getImgSrc } from "../../utils"; 3 | 4 | function ProfileInfo({ admin }) { 5 | return ( 6 |
7 |
8 | 9 |
10 |
11 |

{admin?.fullName}

12 |
{admin?.motto}
13 |
14 |
15 |
16 |
Email
17 |
18 | {admin?.email || "not set"}{" "} 19 |
20 |
21 |
22 |
Telephone
23 |
24 | {" "} 25 | {admin?.telephone || "not set"} 26 |
27 |
28 |
29 |
Address
30 |
31 | {admin?.address || "not set"}{" "} 32 |
33 |
34 |
35 |
36 | ); 37 | } 38 | 39 | export default ProfileInfo; 40 | -------------------------------------------------------------------------------- /frontend/src/components/userInfoTabs/UserInfo.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import {Avatar} from '@material-ui/core' 3 | import {Link} from 'react-router-dom' 4 | import {getCapitalize, getIntial, getImgSrc} from '../../utils' 5 | import {useSelector} from 'react-redux'; 6 | import {selectUser} from '../../store/slices/userSlice' 7 | 8 | 9 | 10 | function StudentInfo({id, name, surname, middleName, role , route, photoUrl}) { 11 | const user = useSelector(selectUser) 12 | return ( 13 |
14 | 15 |
{getCapitalize(name || "")} {middleName && getIntial(middleName)} {getCapitalize(surname || "")}
16 |
{id}
17 |
{role}
18 | {user?.role === "admin" && 19 | 22 | Edit 23 | 24 | } 25 | 26 |
27 | ) 28 | } 29 | 30 | export default StudentInfo 31 | -------------------------------------------------------------------------------- /backend/models/ChatModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const ChatSchema = new Schema( 6 | { 7 | userID: { 8 | type: String, 9 | }, 10 | message: { 11 | type: String, 12 | }, 13 | date: { 14 | type: Date, 15 | default: Date.now, 16 | }, 17 | parent: { 18 | type: String, 19 | }, 20 | isViewed: { 21 | type: Boolean, 22 | default: false, 23 | }, 24 | sender: { 25 | type: String, 26 | }, 27 | requestor_id: { 28 | type: String, 29 | }, 30 | acceptor_id: { 31 | type: String, 32 | }, 33 | messages: { 34 | type: [ 35 | { 36 | senderID: String, 37 | message: String, 38 | channelID: String, 39 | role: String, 40 | isViewed: { 41 | type: Boolean, 42 | default: false, 43 | }, 44 | date: { 45 | type: Date, 46 | default: Date.now, 47 | }, 48 | }, 49 | ], 50 | default: [], 51 | }, 52 | }, 53 | { timestamps: true } 54 | ); 55 | 56 | module.exports = mongoose.model("chats", ChatSchema); 57 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/finances/DuePayments.js: -------------------------------------------------------------------------------- 1 | import React, { useState } from "react"; 2 | import { Link } from "react-router-dom"; 3 | import ArrowForwardIosIcon from "@material-ui/icons/ArrowForwardIos"; 4 | import TableList from "../../AdminComponents/shared/ListTable"; 5 | import { currentCurrency } from "../../utils"; 6 | 7 | const tableHeader = [ 8 | { id: "due", name: "Due Date" }, 9 | { id: "payment", name: "payments" }, 10 | { id: "amount", name: `Amount (${currentCurrency()})` }, 11 | ]; 12 | 13 | function DuePayments() { 14 | const [payments, setpayments] = useState([]); 15 | const [loading, setloading] = useState(false); 16 | 17 | return ( 18 |
19 |
20 | 21 | Back {" "} 22 | 23 |
24 |
25 |

Due Payments

26 | 32 |
33 |
34 | ); 35 | } 36 | 37 | export default DuePayments; 38 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/classes/CoursesPage.js: -------------------------------------------------------------------------------- 1 | import React, { useEffect, useState } from "react"; 2 | import ClassCard from "../../components/courses/ClassCard"; 3 | import { selectUser } from "../../store/slices/userSlice"; 4 | import { useSelector } from "react-redux"; 5 | import axios from "../../store/axios"; 6 | 7 | function CoursesPage() { 8 | const [courses, setcourses] = useState([]); 9 | const user = useSelector(selectUser); 10 | 11 | useEffect(() => { 12 | const getdata = async () => { 13 | let data = await axios.get(`/students/student/${user?.userID}`); 14 | let classID = data.data.student?.classID; 15 | await axios.get(`/courses/class/${classID}`).then((res) => { 16 | if (res.data.success) { 17 | setcourses(res.data.docs); 18 | } 19 | }); 20 | }; 21 | getdata(); 22 | }, [user]); 23 | 24 | return ( 25 |
26 |

My Courses

27 |
28 | {courses.length > 0 ? ( 29 | courses.map((e) => ) 30 | ) : ( 31 | 32 | )} 33 |
34 |
35 | ); 36 | } 37 | 38 | export default CoursesPage; 39 | -------------------------------------------------------------------------------- /backend/models/NonTeacherModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const NonTeacherSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | required: true, 10 | }, 11 | surname: { 12 | type: String, 13 | required: true, 14 | }, 15 | email: { 16 | type: String, 17 | }, 18 | address: { 19 | type: String, 20 | }, 21 | class: { 22 | type: String, 23 | }, 24 | role: { 25 | type: String, 26 | default: "nonteacher", 27 | }, 28 | telephone: { 29 | type: String, 30 | }, 31 | position: { 32 | type: String, 33 | required: true, 34 | }, 35 | password: { 36 | type: String, 37 | required: true, 38 | }, 39 | nextofKin_ID: { 40 | type: String, 41 | }, 42 | gender: { 43 | type: String, 44 | required: true, 45 | }, 46 | profileUrl: String, 47 | userID: { 48 | type: String, 49 | }, 50 | date: { 51 | type: Date, 52 | default: Date.now, 53 | }, 54 | }, 55 | { timestamps: true } 56 | ); 57 | 58 | module.exports = mongoose.model("nonTeachers", NonTeacherSchema, "accounts"); 59 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/classes/Classes.js: -------------------------------------------------------------------------------- 1 | import React, { useEffect, useState } from "react"; 2 | import { selectUser } from "../../store/slices/userSlice"; 3 | import { useSelector } from "react-redux"; 4 | import axios from "../../store/axios"; 5 | import Loading from "../../Loading"; 6 | import ClassDetails from "../../components/class/ClassDetails"; 7 | 8 | function Classes() { 9 | const user = useSelector(selectUser); 10 | const [classID, setclassID] = useState(null); 11 | const [loading, setloading] = useState(false); 12 | 13 | useEffect(() => { 14 | const getData = async () => { 15 | setloading(true); 16 | let student = await axios.get(`/user/${user?.userID}`); 17 | 18 | let classData = student?.data?.user; 19 | console.log(classData?.classID); 20 | setclassID(classData?.classID); 21 | setloading(false); 22 | }; 23 | getData(); 24 | }, [user]); 25 | 26 | return ( 27 |
28 | {loading && } 29 |
30 | {classID ? ( 31 | 32 | ) : ( 33 |
No Class Details yet
34 | )} 35 |
36 |
37 | ); 38 | } 39 | 40 | export default Classes; 41 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/classes/ClassCard.js: -------------------------------------------------------------------------------- 1 | import React, { useEffect, useState } from "react"; 2 | import ImportContactsIcon from "@material-ui/icons/ImportContacts"; 3 | import { Link } from "react-router-dom"; 4 | import { selectUser } from "../../store/slices/userSlice"; 5 | import { useSelector } from "react-redux"; 6 | import axios from "../../store/axios"; 7 | 8 | function ClassCard({ id }) { 9 | const [courses, setcourses] = useState([]); 10 | const user = useSelector(selectUser); 11 | 12 | useEffect(() => { 13 | axios.get(`/students/student/${user?.userID}`).then((res) => { 14 | setcourses(res.data.docs); 15 | }); 16 | }, [user]); 17 | 18 | return ( 19 |
20 |
21 | {id ? ( 22 | 23 | 24 |
Course Name
25 | id 26 | 27 | ) : ( 28 |
29 | 30 |
Courses
31 | No course yet 32 |
33 | )} 34 |
35 |
36 | ); 37 | } 38 | 39 | export default ClassCard; 40 | -------------------------------------------------------------------------------- /frontend/src/containers/TheContent.js: -------------------------------------------------------------------------------- 1 | import React, { Suspense } from 'react' 2 | import { 3 | Route, 4 | Switch 5 | } from 'react-router-dom' 6 | import { CContainer, CFade } from '@coreui/react' 7 | 8 | // routes config 9 | //import routes from '../routes' 10 | 11 | const loading = ( 12 |
13 |
14 |
15 | ) 16 | 17 | const TheContent = ({routes, path}) => { 18 | return ( 19 |
20 | 21 | 22 | 23 | {routes.map((route, idx) => { 24 | return route.component && ( 25 | ( 31 | 32 | 33 | 34 | )} 35 | /> 36 | ) 37 | })} 38 | 39 | 40 | 41 |
42 | ) 43 | } 44 | 45 | export default React.memo(TheContent) 46 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/dashboard/RecentActivity.js: -------------------------------------------------------------------------------- 1 | import React, { useEffect, useState } from "react"; 2 | import axios from "../../store/axios"; 3 | import { timeStamp } from "../../utils"; 4 | 5 | function RecentActivity() { 6 | const [activities, setactivities] = useState([]); 7 | 8 | useEffect(() => { 9 | axios.get("/activitylog").then((res) => setactivities(res.data)); 10 | }, []); 11 | 12 | return ( 13 |
14 |

Recent Activities

15 |
16 | {activities.length > 0 ? ( 17 | activities.map((e) => ( 18 |
19 |
20 |
21 | {e?.user} 22 |
23 |
24 | 25 | {timeStamp(e.createdAt)} 26 | 27 |
28 |
29 |

{e?.activity}

30 |
31 |
32 | )) 33 | ) : ( 34 |
No activities yet
35 | )} 36 |
37 |
38 | ); 39 | } 40 | 41 | export default RecentActivity; 42 | -------------------------------------------------------------------------------- /backend/models/TransactionsModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const TransactionSchema = new Schema( 6 | { 7 | amount: { 8 | type: String, 9 | required: true, 10 | }, 11 | category: { 12 | type: String, 13 | }, 14 | type: { 15 | type: String, 16 | }, 17 | paymentMethod: { 18 | type: String, 19 | }, 20 | chequeNumber: { 21 | type: String, 22 | }, 23 | bank: { 24 | type: String, 25 | }, 26 | description: String, 27 | month: String, 28 | year: String, 29 | term: String, 30 | pay: { 31 | type: { 32 | accountNumber: String, 33 | bank: String, 34 | userID: String, 35 | position: String, 36 | month: String, 37 | year: String, 38 | salary: String, 39 | }, 40 | }, 41 | fees: { 42 | type: { 43 | userID: String, 44 | term: String, 45 | academicYear: String, 46 | applyTo: { 47 | all: Boolean, 48 | tuition: Boolean, 49 | examination: Boolean, 50 | }, 51 | }, 52 | }, 53 | date: { 54 | type: Date, 55 | default: Date.now, 56 | }, 57 | }, 58 | { timestamps: true } 59 | ); 60 | 61 | module.exports = mongoose.model("transactions", TransactionSchema); 62 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/academics/classGroups/AddClassGroup.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { useForm } from "react-hook-form"; 3 | 4 | export default function AddClassGroup({ name, setname, onSubmit, loading }) { 5 | const { register, handleSubmit, errors } = useForm(); 6 | 7 | return ( 8 |
9 |

Add New Class Group

10 |
11 | 12 | setname(e.target.value)} 17 | className="form-control" 18 | name="name" 19 | /> 20 | {errors.name && ( 21 | 22 | This field is required 23 | 24 | )} 25 |
26 |
27 | 37 |
38 |
39 | ); 40 | } 41 | -------------------------------------------------------------------------------- /frontend/src/scss/_students.scss: -------------------------------------------------------------------------------- 1 | .student__info { 2 | display: flex; 3 | flex-direction: column; 4 | align-items: center; 5 | justify-content: center; 6 | 7 | .avatar { 8 | font-size: 3em; 9 | font-weight: 800; 10 | height: 80px; 11 | width: 80px; 12 | } 13 | } 14 | 15 | .classCard { 16 | background-color: #fff !important; 17 | border-radius: 5px; 18 | padding: 10px; 19 | text-align: center; 20 | 21 | a { 22 | color: $darkBlue !important; 23 | &:hover { 24 | color: $orange !important; 25 | } 26 | } 27 | 28 | &:hover { 29 | transform: scale(1.009); 30 | } 31 | 32 | .icon { 33 | width: 80px !important; 34 | height: 80px !important; 35 | } 36 | } 37 | 38 | .selectBox { 39 | position: relative; 40 | } 41 | .showcheckboxes { 42 | display: block; 43 | border: 1px #dadada solid; 44 | } 45 | 46 | .profileContainer { 47 | position: relative; 48 | .profileIcon { 49 | position: absolute; 50 | color: $darkBlue; 51 | top: 20%; 52 | left: 50%; 53 | transform: translate(-50%); 54 | display: none; 55 | } 56 | } 57 | 58 | .profileContainer:hover .profileIcon { 59 | display: block; 60 | } 61 | 62 | .students__container { 63 | border: 1px solid #ccc; 64 | width: 100%; 65 | 66 | li { 67 | border-bottom: 1px solid #ccc; 68 | padding: 10px 0; 69 | cursor: pointer; 70 | } 71 | } 72 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/Profile/StaffTabs.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import Card from "./SummaryCard"; 3 | 4 | function StaffTabs({ count }) { 5 | return ( 6 |
7 |

Staff Overview

8 |
9 |

Staffs

10 |
11 | 19 | 27 | 28 |
29 |
30 |
31 | 32 | 36 | 40 |
41 |
42 | ); 43 | } 44 | 45 | export default StaffTabs; 46 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/dashboard/StaffPopulation.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import ComplexDonut from "react-svg-donuts/dist/complex"; 3 | import "react-svg-donuts/dist/index.css"; 4 | 5 | function Population({ maleStudents, femaleStudents }) { 6 | return ( 7 |
8 |

Staff

9 | 10 | 26 | 27 |
28 |
29 |
30 |
Female Staff
31 |
32 | {femaleStudents || 0} 33 |
34 |
35 |
36 |
37 |
Male Staff
38 |
39 | {maleStudents || 0} 40 |
41 |
42 |
43 |
44 | ); 45 | } 46 | 47 | export default Population; 48 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/dashboard/SchoolPopulation.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import ComplexDonut from "react-svg-donuts/dist/complex"; 3 | import "react-svg-donuts/dist/index.css"; 4 | 5 | function Population({ maleStudents, femaleStudents }) { 6 | return ( 7 |
8 |

Students

9 | 10 | 26 | 27 |
28 |
29 |
30 |
Female Students
31 |
32 | {femaleStudents || 0} 33 |
34 |
35 |
36 |
37 |
Male Students
38 |
39 | {maleStudents || 0} 40 |
41 |
42 |
43 |
44 | ); 45 | } 46 | 47 | export default Population; 48 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/shared/HandleDelete.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import Button from '@material-ui/core/Button'; 3 | import Dialog from '@material-ui/core/Dialog'; 4 | import DialogActions from '@material-ui/core/DialogActions'; 5 | import DialogContent from '@material-ui/core/DialogContent'; 6 | import DialogTitle from '@material-ui/core/DialogTitle'; 7 | import axios from '../../store/axios' 8 | 9 | 10 | export default function AlertDialog({id, open, setOpen}) { 11 | // const [open, setOpen] = React.useState(false); 12 | 13 | const handleClose = () => { 14 | setOpen(false); 15 | }; 16 | 17 | const handleDelete = () => { 18 | axios.delete(`/user/delete/${id}`).then(res => { 19 | 20 | }) 21 | } 22 | 23 | return ( 24 |
25 | 31 | {`Are you sure you want to delete user ${id}`} 32 | 33 | 34 | 35 | 38 | 41 | 42 | 43 |
44 | ); 45 | } 46 | -------------------------------------------------------------------------------- /frontend/src/containers/TheSidebar.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { useSelector, useDispatch } from "react-redux"; 3 | import { 4 | CCreateElement, 5 | CSidebar, 6 | CSidebarBrand, 7 | CSidebarNav, 8 | CSidebarNavDivider, 9 | CSidebarNavTitle, 10 | CSidebarMinimizer, 11 | CSidebarNavDropdown, 12 | CSidebarNavItem, 13 | } from "@coreui/react"; 14 | import { selectSidebarShow, set } from "../store/slices/appSlice"; 15 | import logo from "../assets/icons/logo.png"; 16 | 17 | const TheSidebar = ({ navs }) => { 18 | const dispatch = useDispatch(); 19 | const show = useSelector(selectSidebarShow); 20 | 21 | return ( 22 | dispatch(set(val))} 26 | > 27 | 28 | logo-negative 34 | 35 | 36 | 45 | 46 | 47 | 48 | ); 49 | }; 50 | 51 | export default React.memo(TheSidebar); 52 | -------------------------------------------------------------------------------- /frontend/src/pages/page404/Page404.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import { 3 | CButton, 4 | CCol, 5 | CContainer, 6 | CInput, 7 | CInputGroup, 8 | CInputGroupPrepend, 9 | CInputGroupAppend, 10 | CInputGroupText, 11 | CRow 12 | } from '@coreui/react' 13 | import CIcon from '@coreui/icons-react' 14 | 15 | const Page404 = () => { 16 | return ( 17 |
18 | 19 | 20 | 21 |
22 |

404

23 |

Oops! You{'\''}re lost.

24 |

The page you are looking for was not found.

25 |
26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | Search 35 | 36 | 37 |
38 |
39 |
40 |
41 | ) 42 | } 43 | 44 | export default Page404 45 | -------------------------------------------------------------------------------- /frontend/src/components/dashboard/SchoolCalender.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import { Calendar, momentLocalizer } from "react-big-calendar"; 3 | import moment from "moment"; 4 | import "react-big-calendar/lib/css/react-big-calendar.css"; 5 | import axios from "../../store/axios"; 6 | import { Link } from "react-router-dom"; 7 | import { useSelector } from "react-redux"; 8 | import { selectUser } from "../../store/slices/userSlice"; 9 | 10 | const localizer = momentLocalizer(moment); 11 | 12 | function SchoolCalender() { 13 | const [events, setevents] = useState([]); 14 | const user = useSelector(selectUser); 15 | 16 | useEffect(() => { 17 | axios.get("/calendar").then((res) => { 18 | setevents(res.data); 19 | }); 20 | }, []); 21 | 22 | return ( 23 |
24 |
25 |

School Event Calender

26 |
27 | {user?.role === "admin" && ( 28 | 29 | Add New Event 30 | 31 | )} 32 |
33 |
34 | 35 | 42 |
43 | ); 44 | } 45 | 46 | export default SchoolCalender; 47 | -------------------------------------------------------------------------------- /frontend/src/pages/page500/Page500.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import { 3 | CButton, 4 | CCol, 5 | CContainer, 6 | CInput, 7 | CInputGroup, 8 | CInputGroupAppend, 9 | CInputGroupPrepend, 10 | CInputGroupText, 11 | CRow 12 | } from '@coreui/react' 13 | import CIcon from '@coreui/icons-react' 14 | 15 | const Page500 = () => { 16 | return ( 17 |
18 | 19 | 20 | 21 | 22 |

500

23 |

Houston, we have a problem!

24 |

The page you are looking for is temporarily unavailable.

25 |
26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | Search 35 | 36 | 37 |
38 |
39 |
40 |
41 | ) 42 | } 43 | 44 | export default Page500 45 | -------------------------------------------------------------------------------- /backend/models/FeesModel.js: -------------------------------------------------------------------------------- 1 | const mongoose = require("../config/mongodb"); 2 | 3 | const { Schema } = mongoose; 4 | 5 | const FeesSchema = new Schema( 6 | { 7 | name: { 8 | type: String, 9 | }, 10 | code: { 11 | type: String, 12 | }, 13 | term: String, 14 | year: String, 15 | day: { 16 | type: { 17 | name: { 18 | type: String, 19 | default: "day", 20 | }, 21 | tution: String, 22 | facility: String, 23 | maintenance: String, 24 | exam: String, 25 | }, 26 | }, 27 | freshDay: { 28 | type: { 29 | name: { 30 | type: String, 31 | default: "freshDay", 32 | }, 33 | tution: String, 34 | facility: String, 35 | maintenance: String, 36 | exam: String, 37 | }, 38 | }, 39 | border: { 40 | type: { 41 | name: { 42 | type: String, 43 | default: "border", 44 | }, 45 | tution: String, 46 | facility: String, 47 | maintenance: String, 48 | exam: String, 49 | }, 50 | }, 51 | freshBorder: { 52 | type: { 53 | name: { 54 | type: String, 55 | default: "freshBorder", 56 | }, 57 | tution: String, 58 | facility: String, 59 | maintenance: String, 60 | exam: String, 61 | }, 62 | }, 63 | }, 64 | { timestamps: true } 65 | ); 66 | 67 | module.exports = mongoose.model("fees", FeesSchema); 68 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/Profile/FinancialTabs.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import Card from "./FinanceCard"; 3 | 4 | function FinancialTabs() { 5 | return ( 6 |
7 |

Financial Reports

8 |
9 |
10 | 11 |
12 |
13 | 17 |
18 | 19 |
20 | 21 |
22 |
23 | 27 |
28 | 29 |
30 | 34 |
35 |
36 | 37 |
38 | 39 |
40 | 41 |
42 |
43 |
44 | ); 45 | } 46 | 47 | export default FinancialTabs; 48 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/staff/PayrowPage.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import ListTable from '../shared/ListTable'; 3 | import Payrow from './SearchPayrow' 4 | 5 | function PayrowPage() { 6 | const data = [ 7 | {id: "123", name: "Rudo Mapfumba", role: "Teacher", bank: "Bank of China", accNum: "21294040392043205050", salary: "2500", status: "Paid"}, 8 | {id: "124", name: "Rudo Mapfumba", role: "Teacher", bank: "Bank of China", accNum: "21294040392043205050", salary: "2500", status: "Paid"}, 9 | {id: "125", name: "Rudo Mapfumba", role: "Teacher", bank: "Bank of China", accNum: "21294040392043205050", salary: "2500", status: "Paid"}, 10 | {id: "126", name: "Rudo Mapfumba", role: "Teacher", bank: "Bank of China", accNum: "21294040392043205050", salary: "2500", status: "Paid"}, 11 | {id: "127", name: "Rudo Mapfumba", role: "Teacher", bank: "Bank of China", accNum: "21294040392043205050", salary: "2500", status: "Paid"} 12 | ]; 13 | const tableHeadings = [ 14 | {id: "id", name: "Staff ID"}, 15 | {id: "name", name: "Name"}, 16 | {id: "role", name: "Staff Type"}, 17 | {id: "bank", name: "Bank"}, 18 | {id: "accNum", name: "Account Number"}, 19 | {id: "salary", name: "Salary"}, 20 | {id: "status", name: "Status"}, 21 | 22 | ]; 23 | 24 | return ( 25 |
26 | 27 | 28 |
29 | ) 30 | } 31 | 32 | export default PayrowPage 33 | -------------------------------------------------------------------------------- /backend/middlewares/multer.js: -------------------------------------------------------------------------------- 1 | const multer = require("multer"); 2 | const path = require("path"); 3 | const { v4 } = require("uuid"); 4 | const fs = require("fs/promises"); 5 | 6 | const UPLOAD_DIRECTORY = "./consumerPhotos"; 7 | 8 | const checkIfDirectoryExists = async () => { 9 | try { 10 | await fs.stat(UPLOAD_DIRECTORY); 11 | } catch (err) { 12 | if (err.code === "ENOENT") { 13 | await fs.mkdir(UPLOAD_DIRECTORY); 14 | } 15 | } 16 | }; 17 | 18 | const storage = multer.diskStorage({ 19 | async destination(req, file, callback) { 20 | //console.log(file) 21 | try { 22 | await checkIfDirectoryExists(); 23 | // console.log(file, "multer file") 24 | callback(null, UPLOAD_DIRECTORY); 25 | } catch (err) { 26 | callback(err); 27 | } 28 | }, 29 | 30 | async filename(req, file, callback) { 31 | const fileExtension = path.extname(file.originalname); 32 | const fileName = `${v4()}${fileExtension}`; 33 | // console.log(fileName, "filename") 34 | callback(null, fileName); 35 | }, 36 | }); 37 | 38 | const uploader = multer({ 39 | storage: storage, 40 | limits: { fileSize: 2000000 }, 41 | }); 42 | 43 | const getUploadedFiles = async () => { 44 | return await fs.readdir(UPLOAD_DIRECTORY); 45 | }; 46 | 47 | const findUploadedFile = async (fileName) => { 48 | const info = await fs.stat(path.resolve(UPLOAD_DIRECTORY, fileName)); 49 | console.log({ info }); 50 | return info; 51 | }; 52 | 53 | module.exports = { 54 | findUploadedFile, 55 | getUploadedFiles, 56 | uploader, 57 | UPLOAD_DIRECTORY, 58 | }; 59 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/finance/setfees/DeleteFeesModal.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import Button from '@material-ui/core/Button'; 3 | import Dialog from '@material-ui/core/Dialog'; 4 | import DialogActions from '@material-ui/core/DialogActions'; 5 | import DialogContent from '@material-ui/core/DialogContent'; 6 | import DialogContentText from '@material-ui/core/DialogContentText'; 7 | 8 | 9 | function DeleteFeesModal({ open , setOpen, handleDelete, loading}) { 10 | 11 | const handleClose = () => { 12 | setOpen(false); 13 | }; 14 | 15 | return ( 16 | 22 | 23 | 24 | Are you sure you want to delete 25 | 26 | 27 | 28 | 31 | 35 | 36 | 37 | ) 38 | } 39 | 40 | export default DeleteFeesModal 41 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/academics/AllCourses.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import ClassCard from "../../components/courses/ClassCard"; 3 | import { selectUser } from "../../store/slices/userSlice"; 4 | import { useSelector } from "react-redux"; 5 | import axios from "../../store/axios"; 6 | 7 | function AllCourses() { 8 | const [courses, setcourses] = useState([]); 9 | const user = useSelector(selectUser); 10 | 11 | useEffect(() => { 12 | axios.get(`/courses/teacher/${user?.id}`).then((res) => { 13 | console.log(res); 14 | if (res.data.success) { 15 | //let classesArr = [] 16 | let classes = res.data?.docs.map((e) => { 17 | let classesArr = []; 18 | e.classes.map((i) => { 19 | if (i.teacher === user?.id) { 20 | classesArr.push({ 21 | class: i.class, 22 | teacher: i.teacher, 23 | course: e.code, 24 | }); 25 | } 26 | }); 27 | return classesArr; 28 | }); 29 | console.log(classes.flat()); 30 | setcourses(classes.flat()); 31 | } 32 | }); 33 | }, [user]); 34 | 35 | return ( 36 |
37 |

My Tutorial Courses

38 |
39 | {courses?.length > 0 ? ( 40 | courses?.map((e, i) => ( 41 | 42 | )) 43 | ) : ( 44 | 45 | )} 46 |
47 |
48 | ); 49 | } 50 | 51 | export default AllCourses; 52 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/academics/combinedReports/CombinedReports.js: -------------------------------------------------------------------------------- 1 | import React, { useState } from "react"; 2 | import Search from "./Search"; 3 | import Table from "./Table"; 4 | import axios from "../../../store/axios"; 5 | import { errorAlert } from "../../../utils"; 6 | 7 | function CombinedReports() { 8 | const [data, setdata] = useState([]); 9 | const [term, setterm] = useState(""); 10 | const [year, setyear] = useState(""); 11 | const [classID, setclass] = useState(""); 12 | const [loading, setloading] = useState(false); 13 | const [show, setshow] = useState(false); 14 | 15 | const handleSearch = (e) => { 16 | setshow(false); 17 | e.preventDefault(); 18 | setloading(true); 19 | if (classID === "" || term === "" || year === "") { 20 | setloading(false); 21 | return errorAlert("Please select all fields"); 22 | } 23 | axios.get(`/sba/class/${classID}/${year}/${term}`).then((result) => { 24 | setloading(false); 25 | console.log(result); 26 | setdata(result.data.docs); 27 | setshow(true); 28 | }); 29 | }; 30 | 31 | return ( 32 |
33 |

Combined Reports

34 |
35 | 45 |
46 | {show && } 47 | 48 | ); 49 | } 50 | 51 | export default CombinedReports; 52 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/academics/progressReports/ProgressReports.js: -------------------------------------------------------------------------------- 1 | import React, { useState } from "react"; 2 | import Search from "./Search"; 3 | import Table from "./Table"; 4 | import axios from "../../../store/axios"; 5 | import { errorAlert } from "../../../utils"; 6 | 7 | function ProgressReports() { 8 | const [data, setdata] = useState([]); 9 | const [classID, setclassID] = useState(""); 10 | const [term, setterm] = useState(""); 11 | const [academicYear, setacademicYear] = useState(""); 12 | const [loading, setloading] = useState(false); 13 | 14 | const handleSearch = (e) => { 15 | e.preventDefault(); 16 | setloading(true); 17 | if (classID === "" || term === "" || academicYear === "") { 18 | setloading(false); 19 | return errorAlert("Please select all fields"); 20 | } 21 | axios.get(`/students/class/${classID}`).then((res) => { 22 | setloading(false); 23 | if (res.data.error) { 24 | return errorAlert(res.data.error); 25 | } 26 | setdata(res.data.users); 27 | }); 28 | }; 29 | 30 | return ( 31 |
32 |

Progress Reports

33 |
34 | 44 |
45 | {data.length > 0 &&
} 46 | 47 | ); 48 | } 49 | 50 | export default ProgressReports; 51 | -------------------------------------------------------------------------------- /frontend/src/components/userInfoTabs/StudentDetails.js: -------------------------------------------------------------------------------- 1 | import React, {useEffect, useState} from 'react'; 2 | import StudentInfo from './UserInfo'; 3 | import StudentTabs from './StudentTabs'; 4 | import axios from '../../../store/axios'; 5 | import { useParams} from 'react-router-dom' 6 | import {errorAlert} from '../../utils' 7 | 8 | function StudentDetails() { 9 | const [details, setdetails] = useState(null); 10 | 11 | const {id} =useParams() 12 | 13 | useEffect(() => { 14 | axios.get(`/students/student/${id}`).then(res => { 15 | if(res.data.error){ 16 | errorAlert(res.data.error) 17 | return 0 18 | } 19 | setdetails(res.data.student) 20 | }) 21 | 22 | }, [id]) 23 | 24 | 25 | 26 | return ( 27 |
28 |

Student Details

29 |
30 | {details ? <> 31 |
32 | 38 |
39 |
40 | 41 |
42 | :

Student not found

} 43 |
44 |
45 | ) 46 | } 47 | 48 | export default StudentDetails 49 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/dashboard/Profile.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import { Link } from "react-router-dom"; 3 | import InfoTabs from "../../components/userInfoTabs/StaffTabs"; 4 | import Profile from "../../components/profile/UpdateProfile"; 5 | import { useSelector } from "react-redux"; 6 | import { selectUser } from "../../store/slices/userSlice"; 7 | import { getCapitalize, getIntial } from "../../utils"; 8 | import axios from "../../store/axios"; 9 | 10 | function ProfilePage() { 11 | const user = useSelector(selectUser); 12 | const [userDetails, setuserDetails] = useState({}); 13 | 14 | useEffect(() => { 15 | axios.get(`/teachers/${user?.userID}`).then((res) => { 16 | setuserDetails(res.data.teacher); 17 | }); 18 | }, [user]); 19 | 20 | return ( 21 |
22 |

About Me

23 |
24 |
25 | 26 |
27 |
28 |

29 | {getCapitalize(user?.name)} {getIntial(user?.middleName || "")}{" "} 30 | {getCapitalize(user?.lastName)} 31 |

32 |
{user?.id}
33 |
Role
34 | 35 | Edit 36 | 37 |
38 |
39 |
40 | 41 |
42 |
43 | ); 44 | } 45 | 46 | export default ProfilePage; 47 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/profile/ProfilePage.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import { Link } from "react-router-dom"; 3 | import InfoTabs from "../../components/userInfoTabs/StudentTabs"; 4 | import Profile from "../../components/profile/UpdateProfile"; 5 | import { useSelector } from "react-redux"; 6 | import { selectUser } from "../../store/slices/userSlice"; 7 | import { getCapitalize, getIntial } from "../../utils"; 8 | import axios from "../../store/axios"; 9 | 10 | function ProfilePage() { 11 | const user = useSelector(selectUser); 12 | const [userDetails, setuserDetails] = useState({}); 13 | 14 | useEffect(() => { 15 | axios.get(`/students/student/${user?.userID}`).then((res) => { 16 | console.log(res.data); 17 | setuserDetails(res.data.student); 18 | }); 19 | }, [user]); 20 | 21 | return ( 22 |
23 |

About Me

24 |
25 |
26 | 27 |
28 |
29 |

30 | {getCapitalize(user?.name)} {getIntial(user?.middleName || "")}{" "} 31 | {getCapitalize(user?.lastName)} 32 |

33 |
{user?.id}
34 |
Role
35 | 36 | Edit 37 | 38 |
39 |
40 |
41 | 42 |
43 |
44 | ); 45 | } 46 | 47 | export default ProfilePage; 48 | -------------------------------------------------------------------------------- /frontend/src/scss/_admin.scss: -------------------------------------------------------------------------------- 1 | .dashboard__card { 2 | background-color: $white; 3 | padding: 20px; 4 | display: flex; 5 | margin-bottom: 30px; 6 | align-items: center; 7 | color: $black !important; 8 | //justify-content: space-between; 9 | 10 | .card__digits { 11 | font-weight: 800; 12 | font-size: 1.7em; 13 | } 14 | .card__details { 15 | margin-left: 10px; 16 | } 17 | h5 { 18 | opacity: 0.4; 19 | } 20 | .card__icon { 21 | background-color: lightblue; 22 | border-radius: 50%; 23 | padding: 20px; 24 | } 25 | &:hover { 26 | transform: scale(1.02); 27 | } 28 | } 29 | 30 | .activities__container { 31 | height: 500px; 32 | overflow-y: scroll; 33 | 34 | &::-webkit-scrollbar { 35 | display: hidden; 36 | } 37 | } 38 | .dashboard__attendance { 39 | height: 50vh; 40 | } 41 | .notices { 42 | max-height: 500; 43 | min-height: 100%; 44 | overflow: scroll; 45 | 46 | &::-webkit-scrollbar { 47 | display: none; 48 | } 49 | 50 | .notice { 51 | padding: 20px; 52 | 53 | .chip__date { 54 | background-color: $darkBlue; 55 | color: $white !important; 56 | } 57 | } 58 | } 59 | 60 | .attendances { 61 | .color__box { 62 | width: 100px; 63 | height: 20px; 64 | } 65 | .male__color { 66 | background: #051f3e !important; 67 | } 68 | .female__color { 69 | background-color: #ffa201; 70 | } 71 | } 72 | 73 | .fees { 74 | font-size: 1em; 75 | 76 | .icon { 77 | width: 0.8em; 78 | height: 0.8em; 79 | color: red; 80 | font-weight: 800; 81 | } 82 | } 83 | 84 | .form__sender { 85 | padding: 0 !important; 86 | 87 | .header { 88 | background-color: $darkBlue; 89 | padding: 10px; 90 | color: #ccc; 91 | margin-bottom: 10px; 92 | } 93 | } 94 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/message/Broadcast.js: -------------------------------------------------------------------------------- 1 | import React, { useState } from "react"; 2 | import SendForm from "../../components/messages/SendToForm"; 3 | import { useSelector } from "react-redux"; 4 | import { selectUser } from "../../store/slices/userSlice"; 5 | import axios from "../../store/axios"; 6 | import { errorAlert, successAlert } from "../../utils"; 7 | 8 | function MessageAdmin() { 9 | const [message, setmessage] = useState(""); 10 | const [recipient, setrecipient] = useState("admin"); 11 | const user = useSelector(selectUser); 12 | 13 | const recipientOptions = [ 14 | { 15 | id: "admin", 16 | name: "admin", 17 | }, 18 | ]; 19 | 20 | const onSend = (e) => { 21 | e.preventDefault(); 22 | if (message && recipient) { 23 | axios 24 | .post(`/chats`, { 25 | message, 26 | sender: user?.userID, 27 | userID: recipient, 28 | }) 29 | .then((res) => { 30 | if (res.data.error) { 31 | errorAlert(res.data.error); 32 | return 0; 33 | } 34 | successAlert("message send"); 35 | setmessage(""); 36 | }); 37 | } 38 | }; 39 | 40 | const searchOptions = () => { 41 | return recipientOptions.map((option) => ( 42 | 45 | )); 46 | }; 47 | 48 | return ( 49 |
50 | 60 |
61 | ); 62 | } 63 | 64 | export default MessageAdmin; 65 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/staff/SearchPayrow.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | 3 | function SearchPayrow() { 4 | return ( 5 | 6 |
7 |
8 | 14 |
15 |
16 | 22 |
23 |
24 | 30 |
31 |
32 | 38 |
39 |
40 | 41 |
42 |
43 | 44 | ) 45 | } 46 | 47 | export default SearchPayrow 48 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/classes/CoursePage.js: -------------------------------------------------------------------------------- 1 | import React, { useEffect, useState } from "react"; 2 | import { useParams } from "react-router-dom"; 3 | import axios from "../../store/axios"; 4 | 5 | function Course() { 6 | const [courseDetails, setcourseDetails] = useState({}); 7 | const [isClass, setisClass] = useState(null); 8 | const { id } = useParams(); 9 | 10 | useEffect(() => { 11 | axios.get(`/course/courseCode/${id}`).then((response) => { 12 | if (response.data.success) { 13 | setcourseDetails(response.data.docs); 14 | } else { 15 | setisClass(false); 16 | console.log("ERROR", response.data); 17 | } 18 | }); 19 | }, [id]); 20 | 21 | return ( 22 |
23 |
24 |

Course Details

25 | {isClass ? ( 26 | <> 27 |
28 |
Course
29 |
{courseDetails?.name || "N/A"}
30 |
31 |
32 |
Code
33 |
{courseDetails?.code || "N/A"}
34 |
35 |
36 |
Course Department
37 |
{courseDetails?.type || "N/A"}
38 |
39 |
40 |
Course Teacher
41 |
{courseDetails?.teacher || "N/A"}
42 |
43 | 44 | ) : ( 45 |
No Class Details yet
46 | )} 47 |
48 |
49 | ); 50 | } 51 | 52 | export default Course; 53 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/students/pastStudents/ViewOptions.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import IconButton from "@material-ui/core/IconButton"; 3 | import Menu from "@material-ui/core/Menu"; 4 | import MenuItem from "@material-ui/core/MenuItem"; 5 | import MoreHorizIcon from "@material-ui/icons/MoreHoriz"; 6 | import { useSelector } from "react-redux"; 7 | import { selectUser } from "../../../store/slices/userSlice"; 8 | 9 | export default function SimpleMenu({ 10 | id, 11 | route, 12 | history, 13 | handleDelete, 14 | handleWithdraw, 15 | }) { 16 | const [anchorEl, setAnchorEl] = React.useState(null); 17 | const user = useSelector(selectUser); 18 | 19 | const handleClick = (event) => { 20 | setAnchorEl(event.currentTarget); 21 | }; 22 | 23 | const handleClose = () => { 24 | setAnchorEl(null); 25 | }; 26 | 27 | return ( 28 |
29 | 34 | 35 | 36 | 43 | history.push(`/${route}/${id}`)}> 44 | View 45 | 46 | {user?.role === "admin" && ( 47 | { 49 | handleWithdraw(id); 50 | }} 51 | > 52 | Re-admit 53 | 54 | )} 55 | 56 | {user?.role === "admin" && ( 57 | { 59 | handleDelete(id); 60 | }} 61 | > 62 | Delete 63 | 64 | )} 65 | 66 |
67 | ); 68 | } 69 | -------------------------------------------------------------------------------- /frontend/src/components/dashboard/NoticeBoard.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import Notice from "./Notice"; 3 | import axios from "../../store/axios"; 4 | import { Link } from "react-router-dom"; 5 | import { getTrimString } from "../../utils"; 6 | 7 | function NoticeBoard({ user }) { 8 | const [notices, setnotices] = useState([]); 9 | 10 | useEffect(() => { 11 | axios.get("/notification").then((res) => { 12 | setnotices(res.data); 13 | }); 14 | }, []); 15 | 16 | let max = 5; 17 | let length = notices.length; 18 | 19 | return ( 20 |
21 |
22 |
23 |

Notice Board

24 |
25 |
26 | {user === "admin" && ( 27 | 28 | {" "} 29 | Add New Notice 30 | 31 | )} 32 |
33 |
34 | 35 | {notices.length > 0 ? ( 36 | <> 37 | {notices.slice(0, max).map((notice) => ( 38 |
39 | 47 |
48 |
49 | ))}{" "} 50 | {length > 5 && ( 51 | View More 52 | )} 53 | 54 | ) : ( 55 |
No Notice yet
56 | )} 57 |
58 | ); 59 | } 60 | 61 | export default NoticeBoard; 62 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/finance/banking/Banking.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import ListTable from "../../shared/ListTable"; 3 | import { useHistory, Link } from "react-router-dom"; 4 | import axios from "../../../store/axios"; 5 | import { errorAlert, successAlert } from "../../../utils"; 6 | 7 | function Banking() { 8 | const history = useHistory(); 9 | const [loading, setloading] = useState(false); 10 | const [banks, setbanks] = useState([]); 11 | 12 | useEffect(() => { 13 | axios.get("/banking").then((res) => { 14 | setbanks(res.data); 15 | }); 16 | }, []); 17 | 18 | const tableHeadings = [ 19 | { id: "bankName", name: "Bank" }, 20 | { id: "accountName", name: "Account Name" }, 21 | { id: "accountNumber", name: "Account Number" }, 22 | { id: "balance", name: "Balance" }, 23 | ]; 24 | 25 | const handleEdit = (id) => { 26 | history.push(`/finance/banking/transaction/${id}`); 27 | }; 28 | 29 | const handleDelete = (id) => { 30 | const ans = window.confirm( 31 | "are you sure you want to delete banking details" 32 | ); 33 | if (ans) { 34 | //delete 35 | axios.delete(`/banking/delete/${id}`).then((res) => { 36 | if (res.data.error) { 37 | errorAlert(res.data.error); 38 | return 0; 39 | } 40 | successAlert("Deleted"); 41 | setbanks(banks.filter((e) => e._id !== id)); 42 | }); 43 | } 44 | }; 45 | 46 | return ( 47 |
48 |
49 | Add New Bank 50 |
51 |

Banking Details

52 | 59 |
60 | ); 61 | } 62 | 63 | export default Banking; 64 | -------------------------------------------------------------------------------- /frontend/src/TeachersComponents/message/MessageAdmin.js: -------------------------------------------------------------------------------- 1 | import React, { useState } from "react"; 2 | import SendForm from "../../components/messages/SendToForm"; 3 | import { useSelector } from "react-redux"; 4 | import { selectUser } from "../../store/slices/userSlice"; 5 | import axios from "../../store/axios"; 6 | import { errorAlert, successAlert } from "../../utils"; 7 | 8 | function MessageAdmin() { 9 | const [message, setmessage] = useState(""); 10 | const [recipient, setrecipient] = useState(""); 11 | const recipientOptions = [{ id: "admin", name: "admin" }]; 12 | const user = useSelector(selectUser); 13 | const [loading, setloading] = useState(""); 14 | 15 | const onSend = (e) => { 16 | e.preventDefault(); 17 | if (message && recipient) { 18 | setloading(true); 19 | axios 20 | .post(`/chats/user`, { 21 | message, 22 | userID: recipient, 23 | sender: user?.userID, 24 | }) 25 | .then((res) => { 26 | setloading(false); 27 | if (res.data.error) { 28 | errorAlert(res.data.error); 29 | return 0; 30 | } 31 | successAlert("message send"); 32 | setmessage(""); 33 | }); 34 | } 35 | }; 36 | 37 | const searchOptions = () => { 38 | return recipientOptions.map((option) => ( 39 | 43 | )); 44 | }; 45 | 46 | return ( 47 |
48 | 60 |
61 | ); 62 | } 63 | 64 | export default MessageAdmin; 65 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/attendance/StaffAttendance/StaffAttendanceRegister.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import Table from "../../shared/RegisterAttendance"; 3 | import axios from "../../../store/axios"; 4 | import { errorAlert } from "../../../utils"; 5 | import moment from "moment"; 6 | 7 | function RegisterAttendance() { 8 | const [loading, setloading] = useState(false); 9 | const [staff, setstaff] = useState([]); 10 | 11 | useEffect(() => { 12 | axios.get(`/teachers`).then((res) => { 13 | let data = res.data.map((sta) => { 14 | return { 15 | userID: sta.userID, 16 | name: sta.name, 17 | surname: sta.surname, 18 | status: false, 19 | }; 20 | }); 21 | setstaff(data); 22 | }); 23 | }, []); 24 | 25 | const handleRegisterAttendance = () => { 26 | setloading(true); 27 | axios 28 | .post("/attendance/register", { 29 | users: staff, 30 | classID: "staff", 31 | role: "staff", 32 | }) 33 | .then((res) => { 34 | setloading(false); 35 | console.log(res); 36 | if (res.data.error) { 37 | errorAlert(res.data.error); 38 | return 0; 39 | } 40 | }) 41 | .catch((err) => { 42 | console.log(err); 43 | setloading(false); 44 | errorAlert("Sorry something when wrong"); 45 | }); 46 | }; 47 | 48 | return ( 49 |
50 |

Staff Attendance Register

51 |
52 |
53 | {moment().format("dddd D MMMM YYYY")} 54 |
55 |
56 |
63 | 64 | ); 65 | } 66 | 67 | export default RegisterAttendance; 68 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/canteen/Members.js: -------------------------------------------------------------------------------- 1 | import React, { useEffect, useState } from "react"; 2 | import ListTable from "../shared/ListTable"; 3 | import axios from "../../store/axios"; 4 | import { useHistory } from "react-router-dom"; 5 | import CanteenNav from "./CanteenNav"; 6 | import { errorAlert } from "../../utils"; 7 | 8 | function Members() { 9 | const [data, setdata] = useState([]); 10 | const [loading, setloading] = useState(false); 11 | const history = useHistory(); 12 | 13 | const tableHeader = [ 14 | { id: "memberID", name: " Member ID" }, 15 | { id: "userID", name: "School ID" }, 16 | { id: "name", name: "Name" }, 17 | { id: "role", name: "Type" }, 18 | { id: "paymentMethod", name: "Payment Method" }, 19 | ]; 20 | 21 | useEffect(() => { 22 | axios.get("/canteen").then((res) => { 23 | setdata(res.data); 24 | }); 25 | }, []); 26 | 27 | const handleEdit = (id) => { 28 | history.push(`/canteen/members/edit/${id}`); 29 | }; 30 | 31 | const handleDelete = (id) => { 32 | let ans = window.confirm("Are you sure you want to delete"); 33 | if (ans) { 34 | setloading(true); 35 | axios 36 | .delete(`/canteen/delete/${id}`) 37 | .then(() => { 38 | setloading(false); 39 | setdata(data.filter((res) => res.memberID !== id)); 40 | }) 41 | .catch((err) => { 42 | console.log(err); 43 | errorAlert("something went wrong"); 44 | setloading(false); 45 | }); 46 | } 47 | }; 48 | 49 | return ( 50 |
51 |
52 | 53 |
54 |

Canteen Members

55 | 63 |
64 | ); 65 | } 66 | 67 | export default Members; 68 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/Profile/StudentsTabs.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import Card from "./SummaryCard"; 3 | 4 | function StudentsTabs({ count }) { 5 | return ( 6 |
7 |

Students Overview

8 |
9 |

Students

10 |
11 | 19 | 27 | 28 |
29 |
30 |
31 |

Admissions

32 |
33 | 37 | 41 | 42 |
43 |
44 |
45 | 49 | 53 | 57 |
58 |
59 | ); 60 | } 61 | 62 | export default StudentsTabs; 63 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/attendance/StaffAttendance/EditStaffAttendance.js: -------------------------------------------------------------------------------- 1 | import React, {useState , useEffect} from 'react' 2 | import Table from '../../shared/RegisterAttendance'; 3 | import axios from '../../../store/axios'; 4 | import {errorAlert} from '../../../utils'; 5 | import {useParams} from 'react-router-dom' 6 | 7 | 8 | 9 | function RegisterAttendance() { 10 | const [loading, setloading] = useState(false); 11 | const { id } = useParams() 12 | const [staff, setstaff] = useState([]) 13 | 14 | 15 | useEffect(() => { 16 | if(id){ 17 | axios.get(`/attendance/attendance/${id}`).then(res => { 18 | console.log(res) 19 | setstaff(res.data.users) 20 | }) 21 | } 22 | }, [id]) 23 | 24 | 25 | const handleRegisterAttendance = () => { 26 | setloading(true) 27 | axios.put(`/attendance/update/${id}`, {users: staff}).then(res => { 28 | setloading(false) 29 | if(res.data.error){ 30 | errorAlert(res.data.error); 31 | return 0 32 | } 33 | }).catch(err => { 34 | console.log(err); 35 | setloading(false) 36 | errorAlert("Sorry something when wrong"); 37 | }) 38 | }; 39 | 40 | const handleResetAttendance = () => { 41 | axios.get(`/attendance/attendance/${id}`).then(res => { 42 | console.log(res) 43 | setstaff(res.data.users) 44 | }) 45 | }; 46 | 47 | 48 | return ( 49 |
50 |

51 | Edit Staff Attendance 52 |

53 |
61 | 62 | ) 63 | } 64 | 65 | export default RegisterAttendance 66 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/finance/banking/AddBank.js: -------------------------------------------------------------------------------- 1 | import React, { useState } from 'react' 2 | import BankForm from './BankForm'; 3 | import axios from '../../../store/axios'; 4 | import {errorAlert, successAlert} from '../../../utils'; 5 | import {Link} from 'react-router-dom'; 6 | import ArrowForwardIosIcon from '@material-ui/icons/ArrowForwardIos'; 7 | 8 | 9 | function AddBank() { 10 | const [name, setname] = useState(""); 11 | const [bank, setbank] = useState(""); 12 | const [number, setnumber] = useState(""); 13 | const [loading, setloading] = useState(false) 14 | 15 | 16 | const handleAdd = () => { 17 | setloading(true) 18 | axios.post('/banking/create', { 19 | bankName: bank, 20 | accountName: name, 21 | accountNumber: number 22 | }).then(res => { 23 | setloading(false) 24 | if(res.data.error){ 25 | errorAlert(res.data.error); 26 | return 0; 27 | } 28 | successAlert("successfully created."); 29 | setname(""); 30 | setbank(""); 31 | setnumber(""); 32 | }).catch(err => { 33 | setloading(false); 34 | errorAlert("something went wrong"); 35 | }) 36 | } 37 | 38 | return ( 39 |
40 |
41 | 42 | Back to Banks List 43 | 44 | 45 |
46 |

Add new Bank

47 | 57 | 58 |
59 | ) 60 | } 61 | 62 | export default AddBank 63 | -------------------------------------------------------------------------------- /frontend/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | School Dashboard 18 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 31 |
32 | 33 | 34 | 35 | 36 | 37 | -------------------------------------------------------------------------------- /backend/routes/DivisionRoutes.js: -------------------------------------------------------------------------------- 1 | const express = require("express"); 2 | const DivisionModel = require("../models/DivisionModel"); 3 | const { stringtoLowerCase } = require("../middlewares/utils"); 4 | const route = express.Router(); 5 | 6 | route.get("/", async (req, res) => { 7 | const data = await DivisionModel.find().sort({ 8 | createdAt: "desc", 9 | }); 10 | res.json(data); 11 | }); 12 | 13 | //create 14 | route.post("/create", async (req, res) => { 15 | let body = req.body; 16 | 17 | let code = stringtoLowerCase(body.name); 18 | 19 | const departExist = await DivisionModel.findOne({ 20 | code: code, 21 | }); 22 | if (departExist) { 23 | return res.json({ success: false, error: "Department already exist" }); 24 | } 25 | 26 | DivisionModel.create({ 27 | ...body, 28 | code: code, 29 | }) 30 | .then((doc) => { 31 | console.log(doc); 32 | res.json({ success: true, doc }); 33 | }) 34 | .catch((err) => { 35 | console.log(err); 36 | res.json({ success: false, message: "failed" }); 37 | }); 38 | }); 39 | 40 | //edit 41 | route.put("/update/:id", (req, res) => { 42 | if (!req.params.id) { 43 | return res.status(400).send("Missing URL parameter: username"); 44 | } 45 | DivisionModel.findOneAndUpdate( 46 | { 47 | _id: req.params.id, 48 | }, 49 | req.body, 50 | { 51 | new: true, 52 | } 53 | ) 54 | .then((doc) => { 55 | console.log(doc); 56 | if (!doc) { 57 | return res.json({ success: false, error: "doex not exists" }); 58 | } 59 | return res.json({ success: true, doc }); 60 | }) 61 | .catch((err) => { 62 | res.json({ success: false, message: err }); 63 | }); 64 | }); 65 | 66 | //delete 67 | route.delete("/delete/:id", (req, res) => { 68 | DivisionModel.findOneAndRemove({ 69 | _id: req.params.id, 70 | }) 71 | .then((doc) => { 72 | res.json(doc); 73 | }) 74 | .catch((err) => { 75 | res.status(500).json(err); 76 | }); 77 | }); 78 | 79 | module.exports = route; 80 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/attendance/StudentAttendance/EditAttendance.js: -------------------------------------------------------------------------------- 1 | import React, {useState , useEffect} from 'react' 2 | import Table from '../../shared/RegisterAttendance'; 3 | import axios from '../../../store/axios'; 4 | import {errorAlert} from '../../../utils'; 5 | import {useParams} from 'react-router-dom' 6 | 7 | 8 | 9 | function RegisterAttendance() { 10 | const [loading, setloading] = useState(false); 11 | const {classID, id } = useParams() 12 | const [students, setstudents] = useState([]) 13 | 14 | 15 | useEffect(() => { 16 | if(id){ 17 | axios.get(`/attendance/attendance/${id}`).then(res => { 18 | console.log(res) 19 | setstudents(res.data.users) 20 | }) 21 | } 22 | }, [id]) 23 | 24 | 25 | const handleRegisterAttendance = () => { 26 | setloading(true) 27 | axios.put(`/attendance/update/${id}`, {users: students}).then(res => { 28 | setloading(false) 29 | if(res.data.error){ 30 | errorAlert(res.data.error); 31 | return 0 32 | } 33 | }).catch(err => { 34 | console.log(err); 35 | setloading(false) 36 | errorAlert("Sorry something when wrong"); 37 | }) 38 | } 39 | 40 | const handleResetAttendance = () => { 41 | axios.get(`/attendance/students/${id}`).then(res => { 42 | console.log(res) 43 | setstudents(res.data.users) 44 | }) 45 | } 46 | 47 | 48 | return ( 49 |
50 |

51 | Edit {classID} Attendance 52 |

53 | {classID && 54 |
} 61 | 62 | ) 63 | } 64 | 65 | export default RegisterAttendance 66 | -------------------------------------------------------------------------------- /frontend/src/components/userInfoTabs/EmploymentTab.js: -------------------------------------------------------------------------------- 1 | import moment from "moment"; 2 | import React, { useState, useEffect } from "react"; 3 | import axios from "../../store/axios"; 4 | 5 | function EmploymentTab({ user }) { 6 | const [campus, setcampus] = useState(""); 7 | 8 | useEffect(() => { 9 | if (user?.campusID) { 10 | axios.get(`/campuses/${user?.campusID}`).then((res) => { 11 | setcampus(res.data.docs.name); 12 | }); 13 | } 14 | }, [user]); 15 | 16 | return ( 17 |
18 |
19 |
Position Role:
20 |
{user?.position || "N/A"}
21 |
22 |
23 |
Department:
24 |
{user?.department || "N/A"}
25 |
26 |
27 |
Campus:
28 |
{campus || "N/A"}
29 |
30 |
31 |
Employment Date
32 |
33 | {moment(user?.employmentDate).format("DD MMMM YYYY") || "N/A"}{" "} 34 |
35 |
36 |
37 |
Qualification:
38 |
{user?.qualifications || "N/A"}
39 |
40 |
41 |
Years of Experience:
42 |
{user?.years || "N/A"}
43 |
44 |
45 |
Bank:
46 |
{user?.bank || "N/A"}
47 |
48 |
49 |
Account Number:
50 |
{user?.accountNumber || "N/A"}
51 |
52 |
53 | ); 54 | } 55 | 56 | export default EmploymentTab; 57 | -------------------------------------------------------------------------------- /frontend/src/components/dashboard/Notice.js: -------------------------------------------------------------------------------- 1 | import React, { useState } from "react"; 2 | import moment from "moment"; 3 | import Chip from "@material-ui/core/Chip"; 4 | import { IconButton } from "@material-ui/core"; 5 | import OpenInNewIcon from "@material-ui/icons/OpenInNew"; 6 | import Edit from "./EditNotice"; 7 | 8 | function Notice({ 9 | description, 10 | createdBy, 11 | date, 12 | title, 13 | createdAt, 14 | isEdit, 15 | id, 16 | open, 17 | setOpen, 18 | editData, 19 | handleDelete, 20 | }) { 21 | const colors = ["#2ad7c5", "#ffa201", "#f939a1"]; 22 | 23 | const handleOpenEdit = () => { 24 | setOpen(true); 25 | editData?.setdate(date); 26 | editData?.settitle(title); 27 | editData?.setcreatedby(createdBy); 28 | editData?.setdescription(description); 29 | editData?.seteditID(id); 30 | }; 31 | 32 | let bgColor = colors[Math.floor(Math.random() * colors.length)]; 33 | 34 | return ( 35 |
36 |
37 |

38 | {title} 39 |

40 | 45 |

46 | {description} 47 |

48 |
49 |
50 | {createdBy} /{" "} 51 | {moment(createdAt).fromNow()} 52 |
53 |
54 |
55 | {isEdit && ( 56 | <> 57 |
58 | handleOpenEdit()}> 59 | 60 | 61 |
62 | 68 | 69 | )} 70 |
71 | ); 72 | } 73 | 74 | export default Notice; 75 | -------------------------------------------------------------------------------- /backend/routes/YeargroupRoutes.js: -------------------------------------------------------------------------------- 1 | const express = require("express"); 2 | const YearGroupModel = require("../models/YearGroupModel"); 3 | const { stringtoLowerCase } = require("../middlewares/utils"); 4 | const route = express.Router(); 5 | 6 | route.get("/", async (req, res) => { 7 | const data = await YearGroupModel.find().sort({ 8 | createdAt: "desc", 9 | }); 10 | res.json(data); 11 | }); 12 | 13 | //create 14 | route.post("/create", async (req, res) => { 15 | let body = req.body; 16 | 17 | let code = stringtoLowerCase(body.name); 18 | 19 | const departExist = await YearGroupModel.findOne({ 20 | code: code, 21 | year: body.year, 22 | }); 23 | if (departExist) { 24 | return res.json({ success: false, error: "Year Group already exist" }); 25 | } 26 | 27 | YearGroupModel.create({ 28 | ...body, 29 | code: code, 30 | }) 31 | .then((doc) => { 32 | console.log(doc); 33 | res.json({ success: true, doc }); 34 | }) 35 | .catch((err) => { 36 | console.log(err); 37 | res.json({ success: false, message: "failed" }); 38 | }); 39 | }); 40 | 41 | //edit 42 | route.put("/update/:id", (req, res) => { 43 | if (!req.params.id) { 44 | return res.status(400).send("Missing URL parameter: username"); 45 | } 46 | YearGroupModel.findOneAndUpdate( 47 | { 48 | _id: req.params.id, 49 | }, 50 | req.body, 51 | { 52 | new: true, 53 | } 54 | ) 55 | .then((doc) => { 56 | console.log(doc); 57 | if (!doc) { 58 | return res.json({ success: false, error: "does not exists" }); 59 | } 60 | return res.json({ success: true, doc }); 61 | }) 62 | .catch((err) => { 63 | res.json({ success: false, message: err }); 64 | }); 65 | }); 66 | 67 | //delete 68 | route.delete("/delete/:id", (req, res) => { 69 | YearGroupModel.findOneAndRemove({ 70 | _id: req.params.id, 71 | }) 72 | .then((doc) => { 73 | res.json(doc); 74 | }) 75 | .catch((err) => { 76 | res.status(500).json(err); 77 | }); 78 | }); 79 | 80 | module.exports = route; 81 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/shared/ViewOptions.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import IconButton from "@material-ui/core/IconButton"; 3 | import Menu from "@material-ui/core/Menu"; 4 | import MenuItem from "@material-ui/core/MenuItem"; 5 | import MoreHorizIcon from "@material-ui/icons/MoreHoriz"; 6 | import { useSelector } from "react-redux"; 7 | import { selectUser } from "../../store/slices/userSlice"; 8 | 9 | export default function SimpleMenu({ 10 | id, 11 | route, 12 | history, 13 | isWithdraw, 14 | handleDelete, 15 | handleWithdraw, 16 | }) { 17 | const [anchorEl, setAnchorEl] = React.useState(null); 18 | const user = useSelector(selectUser); 19 | 20 | const handleClick = (event) => { 21 | setAnchorEl(event.currentTarget); 22 | }; 23 | 24 | const handleClose = () => { 25 | setAnchorEl(null); 26 | }; 27 | 28 | return ( 29 |
30 | 35 | 36 | 37 | 44 | history.push(`/${route}/${id}`)}> 45 | View 46 | 47 | {user?.role === "admin" && ( 48 | history.push(`/${route}/edit/${id}`)}> 49 | Edit 50 | 51 | )} 52 | {user?.role === "admin" && ( 53 | { 55 | handleWithdraw(id); 56 | }} 57 | > 58 | {isWithdraw ? "UnWithdraw" : "Withdraw"} 59 | 60 | )} 61 | {user?.role === "admin" && ( 62 | { 64 | handleDelete(id); 65 | }} 66 | > 67 | Delete 68 | 69 | )} 70 | 71 |
72 | ); 73 | } 74 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/staff/StaffDetails.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import Info from "../../components/userInfoTabs/UserInfo"; 3 | import StaffTabs from "../../components/userInfoTabs/StaffTabs"; 4 | import axios from "../../store/axios"; 5 | import { errorAlert } from "../../utils"; 6 | import { useParams, useHistory } from "react-router-dom"; 7 | 8 | function StaffDetails() { 9 | const [details, setdetails] = useState({}); 10 | const { id } = useParams(); 11 | const [loading, setloading] = useState(false); 12 | const history = useHistory(); 13 | 14 | useEffect(() => { 15 | setloading(true); 16 | axios 17 | .get(`/teachers/${id}`) 18 | .then((res) => { 19 | setloading(false); 20 | if (res.data.error) { 21 | history.push("/staff"); 22 | // errorAlert(res.data.error); 23 | return 0; 24 | } 25 | setdetails(res.data.teacher); 26 | }) 27 | .catch((err) => { 28 | console.log(err); 29 | setloading(false); 30 | }); 31 | }, [id, history]); 32 | 33 | console.log(details); 34 | 35 | return ( 36 |
37 | {!loading && ( 38 | <> 39 |

Staff Details

40 | {!details ? ( 41 |

Staff Member not found

42 | ) : ( 43 |
44 |
45 | 54 |
55 |
56 | 57 |
58 |
59 | )} 60 | 61 | )} 62 |
63 | ); 64 | } 65 | 66 | export default StaffDetails; 67 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/dashboard/Attendance.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | //import { Chart } from "react-chartjs-2"; 3 | import { Bar } from "@reactchartjs/react-chart.js"; 4 | import moment from "moment"; 5 | import axios from "../../store/axios"; 6 | 7 | const date = new Date(); 8 | const month = date.getMonth(); 9 | var year = date.getFullYear(); 10 | var day = date.getDate(); 11 | var weekday = date.getDay(); 12 | var start = new Date(year, month, day - weekday); 13 | var end = moment(start).add(7, "day").format("dddd D MMMM YYYY"); 14 | 15 | function AttendanceTabs() { 16 | const [dates, setdates] = useState([]); 17 | const [datas, setdatas] = useState([]); 18 | 19 | useEffect(() => { 20 | let arr = []; 21 | let d = []; 22 | for (var i = 0; i < 7; i++) { 23 | arr.push(moment(start).add(i, "day").format("dd")); 24 | d.push(Math.floor(Math.random() * Math.floor(100))); 25 | } 26 | setdates(arr); 27 | //setdatas(d); 28 | }, []); 29 | 30 | useEffect(() => { 31 | let d = moment(start).format("DD-MM-YYYY"); 32 | console.log(d); 33 | axios.get(`/count/attendance/week/${d}`).then((res) => { 34 | setdatas(res.data.map((e) => e.value)); 35 | }); 36 | }, []); 37 | 38 | const data = { 39 | labels: dates, 40 | datasets: [ 41 | { 42 | label: "Attendance", 43 | data: datas, 44 | backgroundColor: "#051f3e", 45 | borderColor: "#051f3e", 46 | borderWidth: 1, 47 | }, 48 | ], 49 | }; 50 | 51 | const options = { 52 | scales: { 53 | yAxes: [ 54 | { 55 | ticks: { 56 | beginAtZero: true, 57 | }, 58 | }, 59 | ], 60 | }, 61 | }; 62 | 63 | return ( 64 |
65 |
66 | Attendance Report from {moment(start).format(" D MMMM YYYY")} to{" "} 67 | {moment(end).format(" D MMMM YYYY")} 68 |
69 | 70 |
71 | ); 72 | } 73 | 74 | export default AttendanceTabs; 75 | -------------------------------------------------------------------------------- /frontend/src/StudentComponents/messages/MessageAdmin.js: -------------------------------------------------------------------------------- 1 | import React, { useState } from "react"; 2 | import SendForm from "../../components/messages/SendToForm"; 3 | import { useSelector } from "react-redux"; 4 | import { selectUser } from "../../store/slices/userSlice"; 5 | import axios from "../../store/axios"; 6 | import { errorAlert, successAlert } from "../../utils"; 7 | 8 | function MessageAdmin() { 9 | const [message, setmessage] = useState(""); 10 | const [recipient, setrecipient] = useState("admin"); 11 | const user = useSelector(selectUser); 12 | const [loading, setloading] = useState(false); 13 | 14 | const recipientOptions = [ 15 | { 16 | id: "admin", 17 | name: "admin", 18 | }, 19 | ]; 20 | 21 | const onSend = (e) => { 22 | e.preventDefault(); 23 | if (message && recipient) { 24 | setloading(true); 25 | axios 26 | .post(`/chats/user`, { 27 | message, 28 | sender: user?.id, 29 | userID: recipient, 30 | telephone: "", 31 | }) 32 | .then((res) => { 33 | console.log(res); 34 | setloading(false); 35 | if (res.data.error) { 36 | errorAlert(res.data.error); 37 | return 0; 38 | } 39 | successAlert("message send"); 40 | setmessage(""); 41 | }) 42 | .catch((err) => { 43 | console.log(err); 44 | setloading(false); 45 | }); 46 | } 47 | }; 48 | 49 | const searchOptions = () => { 50 | return recipientOptions.map((option) => ( 51 | 54 | )); 55 | }; 56 | 57 | return ( 58 |
59 | 70 |
71 | ); 72 | } 73 | 74 | export default MessageAdmin; 75 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/finance/expenditure/ViewPayment.js: -------------------------------------------------------------------------------- 1 | import React, { useState, useEffect } from "react"; 2 | import ListTable from "../../shared/ListTable"; 3 | import { Link } from "react-router-dom"; 4 | import axios from "../../../store/axios"; 5 | import { getTrimString, errorAlert, currentCurrency } from "../../../utils"; 6 | 7 | const tableHeader = [ 8 | { id: "date", name: "Date" }, 9 | { id: "category", name: "Category" }, 10 | { id: "type", name: "Type" }, 11 | { id: "description", name: "Description" }, 12 | { id: "amount", name: `Amount (${currentCurrency()})` }, 13 | { id: "paymentMethod", name: "Payment Type" }, 14 | ]; 15 | 16 | function ViewPayment() { 17 | const [expenditures, setexpenditures] = useState([]); 18 | 19 | useEffect(() => { 20 | axios.get("/transactions").then((res) => { 21 | let data = res.data.map((e) => { 22 | return { 23 | ...e, 24 | description: getTrimString(e.description, 50), 25 | }; 26 | }); 27 | setexpenditures(data); 28 | }); 29 | }, []); 30 | 31 | const handleEdit = (id) => {}; 32 | 33 | const handleDelete = (id) => { 34 | axios.delete(`/transactions/delete/${id}`).then((res) => { 35 | if (res.data.error) { 36 | errorAlert(res.data.error); 37 | } 38 | setexpenditures(expenditures.filter((e) => e._id !== id)); 39 | }); 40 | }; 41 | 42 | return ( 43 |
44 |

Transactions

45 |
46 | 47 | Record An Income 48 | 49 | 50 | Make a Payment 51 | 52 |
53 |
54 | 61 |
62 |
63 | ); 64 | } 65 | 66 | export default ViewPayment; 67 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/academics/yearGroups/AddYearGroup.js: -------------------------------------------------------------------------------- 1 | import React from "react"; 2 | import { useForm } from "react-hook-form"; 3 | import { getYearsList } from "../../../utils"; 4 | 5 | export default function AddClassGroup({ 6 | name, 7 | setname, 8 | onSubmit, 9 | loading, 10 | year, 11 | setyear, 12 | }) { 13 | const { register, handleSubmit, errors } = useForm(); 14 | const yearOptions = getYearsList(10); 15 | return ( 16 | 17 |

Add Year Group

18 |
19 | 20 | setname(e.target.value)} 26 | className="form-control" 27 | name="name" 28 | /> 29 | {errors.name && ( 30 | 31 | This field is required 32 | 33 | )} 34 |
35 |
36 | 37 | 53 |
54 |
55 | 65 |
66 | 67 | ); 68 | } 69 | -------------------------------------------------------------------------------- /frontend/src/AdminComponents/staff/SearchAttendance.js: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | 3 | function SearchAttendance() { 4 | return ( 5 | 6 |

Staff Attendance

7 |
8 |
9 | 10 | 16 |
17 |
18 | 19 | 25 |
26 |
27 | 28 | 34 |
35 |
36 |
37 | 38 | 39 |
40 | 41 | ) 42 | } 43 | 44 | export default SearchAttendance 45 | -------------------------------------------------------------------------------- /backend/routes/DepartmentRoutes.js: -------------------------------------------------------------------------------- 1 | const express = require("express"); 2 | const DepartmentsModel = require("../models/DepartmentsModel"); 3 | const { stringtoLowerCase } = require("../middlewares/utils"); 4 | const route = express.Router(); 5 | 6 | route.get("/", async (req, res) => { 7 | const data = await DepartmentsModel.find().sort({ 8 | createdAt: "desc", 9 | }); 10 | res.json(data); 11 | }); 12 | 13 | //create 14 | route.post("/create", async (req, res) => { 15 | let body = req.body; 16 | 17 | let code = stringtoLowerCase(body.name); 18 | 19 | const departExist = await DepartmentsModel.findOne({ 20 | code: code, 21 | }); 22 | if (departExist) { 23 | return res.json({ success: false, error: "Department already exist" }); 24 | } 25 | 26 | DepartmentsModel.create({ 27 | ...body, 28 | code: code, 29 | }) 30 | .then((doc) => { 31 | console.log(doc); 32 | res.json({ success: true, doc }); 33 | }) 34 | .catch((err) => { 35 | console.log(err); 36 | res.json({ success: false, message: "failed" }); 37 | }); 38 | }); 39 | 40 | //edit 41 | route.put("/update/:id", (req, res) => { 42 | if (!req.params.id) { 43 | return res.status(400).send("Missing URL parameter: username"); 44 | } 45 | DepartmentsModel.findOneAndUpdate( 46 | { 47 | _id: req.params.id, 48 | }, 49 | req.body, 50 | { 51 | new: true, 52 | } 53 | ) 54 | .then((doc) => { 55 | console.log(doc); 56 | if (!doc) { 57 | return res.json({ success: false, error: "doex not exists" }); 58 | } 59 | return res.json({ success: true, doc }); 60 | }) 61 | .catch((err) => { 62 | res.json({ success: false, message: err }); 63 | }); 64 | }); 65 | 66 | //delete 67 | route.delete("/delete/:id", (req, res) => { 68 | if (!req.params.id) { 69 | return res.status(400).send("Missing URL parameter: username"); 70 | } 71 | DepartmentsModel.findOneAndRemove({ 72 | _id: req.params.id, 73 | }) 74 | .then((doc) => { 75 | res.json(doc); 76 | }) 77 | .catch((err) => { 78 | res.status(500).json(err); 79 | }); 80 | }); 81 | 82 | module.exports = route; 83 | --------------------------------------------------------------------------------