From c9012f7c89e3d96c138f0dc902ca42e5976cf0a0 Mon Sep 17 00:00:00 2001 From: Judy Date: Thu, 24 Nov 2022 11:59:28 +0000 Subject: [PATCH 1/5] chore(assignment crud):add crud endpoints for assignments --- src/api/controllers/assignmentsController.js | 110 +++++++++++++++++++ src/api/db/models/assignment.js | 8 -- src/api/db/models/class.js | 4 - src/api/db/models/classteacher.js | 5 - src/api/db/models/user.js | 5 - src/api/routers/assignmentRouter.js | 12 ++ src/api/services/assignmentService.js | 68 ++++++++++++ src/index.js | 2 + 8 files changed, 192 insertions(+), 22 deletions(-) create mode 100644 src/api/controllers/assignmentsController.js create mode 100644 src/api/routers/assignmentRouter.js create mode 100644 src/api/services/assignmentService.js diff --git a/src/api/controllers/assignmentsController.js b/src/api/controllers/assignmentsController.js new file mode 100644 index 0000000..45bd09c --- /dev/null +++ b/src/api/controllers/assignmentsController.js @@ -0,0 +1,110 @@ +import AssignmentService from '../services/AssignmentService.js'; +import Util from '../utils/Utils.js'; + +const util = new Util(); + +class AssignmentController { + static async home(req, res) { + res.send(`

Welcome to the assignment Route

`) + } + + static async getAllAssignments(req, res) { + try { + const allAssignments = await AssignmentService.getAllAssignments(); + if (allAssignments.length > 0) { + util.setSuccess(200, 'Assignments retrieved', allAssignments); + } else { + util.setSuccess(200, 'No Assignment found in the database'); + } + return util.send(res); + } catch (error) { + util.setError(400, error); + return util.send(res); + } + } + + static async addAssignment(req, res) { + if (!req.body.Assignment || !req.body.senderId || !req.body.receiverId) { + util.setError(400, 'Please provide complete details of the Assignment'); + return util.send(res); + } + const newAssignment = req.body; + try { + const createdAssignment = await AssignmentService.addAssignment(newAssignment); + util.setSuccess(201, 'Assignment Added Successfully!', createdAssignment); + return util.send(res); + } catch (error) { + util.setError(400, error.Assignment); + return util.send(res); + } + } + + static async updatedAssignment(req, res) { + const alteredAssignment = req.body; + const { id } = req.params; + if (!Number(id)) { + util.setError(400, 'Please input a valid numeric value'); + return util.send(res); + } + try { + const updateAssignment = await AssignmentService.updateAssignment(id, alteredAssignment); + if (!updateAssignment) { + util.setError(404, `Cannot find a Assignment with the id: ${id}`); + } else { + util.setSuccess(200, 'Assignment updated', updateAssignment); + } + return util.send(res); + } catch (error) { + util.setError(404, error); + return util.send(res); + } + } + + static async getAAssignment(req, res) { + const { id } = req.params; + + if (!Number(id)) { + util.setError(400, 'Please input a valid numeric value'); + return util.send(res); + } + + try { + const theAssignment = await AssignmentService.getAAssignment(id); + + if (!theAssignment) { + util.setError(404, `Cannot find a Assignment with the id ${id}`); + } else { + util.setSuccess(200, 'Found Assignment', theAssignment); + } + return util.send(res); + } catch (error) { + util.setError(404, error); + return util.send(res); + } + } + + static async deleteAssignment(req, res) { + const { id } = req.params; + + if (!Number(id)) { + util.setError(400, 'Please provide a numeric value'); + return util.send(res); + } + + try { + const AssignmentToDelete = await AssignmentService.deleteAssignment(id); + + if (AssignmentToDelete) { + util.setSuccess(200, `Assignment with ${id} deleted`); + } else { + util.setError(404, `Assignment with the id ${id} cannot be found`); + } + return util.send(res); + } catch (error) { + util.setError(400, error); + return util.send(res); + } + } +} + +export default AssignmentController; \ No newline at end of file diff --git a/src/api/db/models/assignment.js b/src/api/db/models/assignment.js index 55de16d..0c12c0b 100644 --- a/src/api/db/models/assignment.js +++ b/src/api/db/models/assignment.js @@ -11,11 +11,7 @@ module.exports = (sequelize, DataTypes) => { */ static associate(models) { // define association here -<<<<<<< HEAD - Assignment.belongsTo(models.User, {foreignKey: 'teacherId', as: 'teacher'}); -======= // Assignment.belongsTo(models.User, {foreignKey: 'teacherId', as: 'teacher'}); ->>>>>>> 8f085e4edb2023272ebca0171aabbffe9a8178dd Assignment.belongsTo(models.User, {foreignKey: 'studentId', as: 'student'}); Assignment.belongsTo(models.Class, {foreignKey: 'classId', as: 'class'}); } @@ -37,12 +33,8 @@ module.exports = (sequelize, DataTypes) => { }, teacherId:{ type: DataTypes.UUID, -<<<<<<< HEAD - allowNull:false -======= allowNull:false, foreignKey:true ->>>>>>> 8f085e4edb2023272ebca0171aabbffe9a8178dd }, studentId:{ type: DataTypes.UUID, diff --git a/src/api/db/models/class.js b/src/api/db/models/class.js index 59df36a..8cc2e45 100644 --- a/src/api/db/models/class.js +++ b/src/api/db/models/class.js @@ -11,11 +11,7 @@ module.exports = (sequelize, DataTypes) => { */ static associate(models) { // define association here -<<<<<<< HEAD - Class.hasMany(models.ClassStudent, {as: 'student'}); -======= // Class.hasMany(models.ClassStudent, {as: 'student'}); ->>>>>>> 8f085e4edb2023272ebca0171aabbffe9a8178dd Class.hasMany(models.User, {as: 'teacher'}); } diff --git a/src/api/db/models/classteacher.js b/src/api/db/models/classteacher.js index 5fafe7d..49d0dae 100644 --- a/src/api/db/models/classteacher.js +++ b/src/api/db/models/classteacher.js @@ -10,13 +10,8 @@ module.exports = (sequelize, DataTypes) => { * The `models/index` file will call this method automatically. */ static associate(models) { -<<<<<<< HEAD - Class.belongsTo(models.Class, {foreignKey: 'classId', as: 'class'}); - Class.belongsTo(models.User, {foreignKey: 'teacherId', as: 'teacher'}); -======= ClassTeacher.belongsTo(models.Class, {foreignKey: 'classId', as: 'class'}); ClassTeacher.belongsTo(models.User, {foreignKey: 'teacherId', as: 'teacher'}); ->>>>>>> 8f085e4edb2023272ebca0171aabbffe9a8178dd } } ClassTeacher.init({ diff --git a/src/api/db/models/user.js b/src/api/db/models/user.js index 4fa0ac0..a43fd4e 100644 --- a/src/api/db/models/user.js +++ b/src/api/db/models/user.js @@ -14,13 +14,8 @@ module.exports = (sequelize, DataTypes) => { // define association here User.hasMany(models.Assignment, {foreignKey: 'assignmentId', as: 'assignment'}) User.hasMany(models.AssignmentScore, {foreignKey: 'assignmentScoreId', as: 'assignmentScore'}) -<<<<<<< HEAD - User.belongsTo(models.Message, {foreignKey: 'sender', as: 'sender'}); - User.belongsTo(models.Message, {foreignKey: 'receiver', as: 'receiver'}); -======= User.hasMany(models.Message, {foreignKey: 'senderId', as: 'sender'}); User.hasMany(models.Message, {foreignKey: 'receiverId', as: 'receiver'}); ->>>>>>> 8f085e4edb2023272ebca0171aabbffe9a8178dd User.belongsTo(models.Role, {foreignKey: 'roleId', as: 'role'}) } } diff --git a/src/api/routers/assignmentRouter.js b/src/api/routers/assignmentRouter.js new file mode 100644 index 0000000..d4b7d2a --- /dev/null +++ b/src/api/routers/assignmentRouter.js @@ -0,0 +1,12 @@ +import { Router } from "express"; +const assignmentRouter = Router(); +import AssignmentController from '../controllers/assignmentsController.js'; + +assignmentRouter.get('/home', AssignmentController.home); +assignmentRouter.get('/', AssignmentController.getAllAssignments); +assignmentRouter.post('/', AssignmentController.addAssignment); +assignmentRouter.get('/:id', AssignmentController.getAAssignment); +assignmentRouter.put('/:id', AssignmentController.updatedAssignment); +assignmentRouter.delete('/:id', AssignmentController.deleteAssignment); + +export { assignmentRouter }; \ No newline at end of file diff --git a/src/api/services/assignmentService.js b/src/api/services/assignmentService.js new file mode 100644 index 0000000..409fe23 --- /dev/null +++ b/src/api/services/assignmentService.js @@ -0,0 +1,68 @@ +import database from '../db/models/index.js'; + +class AssignmentService { + static async getAllAssignments() { + try { + const result = await database.Assignment.findAll(); + return result; + } catch (error) { + throw error; + } + } + + static async addAssignment(newAssignment) { + try { + const result = await database.Assignment.create(newAssignment); + return result; + } catch (error) { + throw error; + } + } + + static async updateAssignment(id, updateAssignment) { + try { + const AssignmentToUpdate = await database.Assignment.findOne({ + where: { id: Number(id) } + }); + + if (AssignmentToUpdate) { + await database.Assignment.update(updateAssignment, { where: { id: Number(id) } }); + + return updateAssignment; + } + return null; + } catch (error) { + throw error; + } + } + + static async getAAssignment(id) { + try { + const aAssignment = await database.Assignment.findOne({ + where: { id: Number(id) } + }); + + return aAssignment; + } catch (error) { + throw error; + } + } + + static async deleteAssignment(id) { + try { + const AssignmentToDelete = await database.Assignment.findOne({ where: { id: Number(id) } }); + + if (AssignmentToDelete) { + const deletedAssignment = await database.Assignment.destroy({ + where: { id: Number(id) } + }); + return deletedAssignment; + } + return null; + } catch (error) { + throw error; + } + } +} + +export default AssignmentService; diff --git a/src/index.js b/src/index.js index 6cd8823..861c24c 100644 --- a/src/index.js +++ b/src/index.js @@ -2,6 +2,7 @@ import express from "express"; import dotenv from "dotenv"; import messageRouter from "./api/routers/MessageRouter.js"; import { studentRouter } from './api/routers/studentsRoutes.js'; +import { assignmentRouter } from './api/routers/assignmentRouter.js'; const app = express(); dotenv.config(); @@ -10,6 +11,7 @@ app.use(express.json()); app.use(express.urlencoded()); app.use('/api/message', messageRouter); app.use('/api/students', studentRouter); +app.use('/api/assignment', assignmentRouter); app.get('/', (req, res) => { From 5b034654ad7a70e158cfa9a7b2d90f657377e0e1 Mon Sep 17 00:00:00 2001 From: Judy Date: Mon, 28 Nov 2022 17:50:02 +0000 Subject: [PATCH 2/5] feat(README.md restructure):restructure the README.md file --- README.md | 70 +++++++++++++++++++++++++++++++++++++++++++++---------- 1 file changed, 58 insertions(+), 12 deletions(-) diff --git a/README.md b/README.md index f7d562c..c54cd67 100644 --- a/README.md +++ b/README.md @@ -1,13 +1,59 @@ # Class Manager -### Introduction - More information coming soon ... - -### Installation Guide -* Clone this repository [here](https://github.com/devcareer/class-manager.git). -* The main branch is the most stable branch at any given time, ensure you're working from it. -* Run npm install to install all dependencies -* Create an .env file in your project root folder and add your variables. See .env.example for assistance. -### Usage -* Run npm watch:dev to start the application. -### License -This project is available for use under the MIT License. \ No newline at end of file + +### The technologies used in creating this project are: +Node.js, ExpressJs, Sequelize ORM, and PostgreSQL + +### :rocket: How to get started +- Make sure to have Git and Node.js installed on your computer +- Clone the project by running: `git clone https://https://github.com/devcareer/class-manager` +- cd into the project and run `npm install` +- create a `config.js` file in the root folder and copy the content in the config.example.js`into it. +- run `sequelize db:migrate` to migrate to the database. +- run `npm start` to start the project. + +These are the HTTP response codes used in this project: +| Status Codes | Indication | +| --- | --- | +| `200` | This `OK` status code indicates that a request has succeeded | +| `400` | This `bad request error` status code indicates that the request sent to the server is incorrect | +| `500` | This `internal server error` status code indicates that something has gone wrong on the web server | + +
+ +The routes featured in this project: +| API routes(url) | Method | Description | +| --- | --- | --- | +| / | `GET` | Api home page | +| /messages | `GET` | Get all messages | +| /messages | `POST` | Create a message | +| /messages/id | `GET` | Get a message by id | +| /messages/id | `PUT` | Update message| +| /messages/id | `DELETE` | Delete message | +| /students | `GET` | Get all students | +| /students | `POST` | Create a student | +| /students/id | `GET` | Get a student by id | +| /students/id | `PUT` | Update student | +| /students/id | `DELETE` | Delete student | +| /teacher | `GET` | Get all teachers | +| /teacher | `POST` | Create a teacher | +| /teacher/id | `GET` | Get a teacher by id | +| /teacher/id | `PUT` | Update teacher | +| /teacher/id | `DELETE` | Delete teacher | +| /assignment | `GET` | Get all assignment | +| /assignment/id | `GET` | Get a assignment with id | +| /assignment/id | `PUT` | Update assignment | +| /assignment/id | `DELETE` | Delete assignment | + +
+ + +👤 **Authors**: + +| Github | Linkedin | +| ------------- | ------------- | +| [@bellogo](https://github.com/bellogo) | [Ufuoma Ogodo](https://ng.linkedin.com/in/ufuoma-ogodo) | +| [@judyseyram](https://github.com/JudySeyram) | [Judith Amegbe](https://gh.linkedin.com/in/amegbe-judith-5b881811a) | +| [@hazeem01](https://github.com/Hazeem01) | [Adenekan Abdulhazeem](https://www.linkedin.com/in/abdulhazeem-adenekan) | +| [@talktonok](https://github.com/talktonok) | [Mansur Ibrahim Nok](https://www.linkedin.com/in/mansuribrahimnok) | +| [@TijanAyo](https://github.com/TijanAyo) | [Tijani Ayomide](https://www.linkedin.com/in/tijanayo) | +| [@Ekemiben](https://github.com/ekemiben) | [Ekemini Ben](https://www.linkedin.com/in/ekemini-ben) | \ No newline at end of file From 68ec1b7508e80e58ce5702ced805e53c60c43549 Mon Sep 17 00:00:00 2001 From: Judy Date: Thu, 1 Dec 2022 10:38:27 +0000 Subject: [PATCH 3/5] edit README.md --- .env.example | 7 ++++++- README.md | 7 +++++-- 2 files changed, 11 insertions(+), 3 deletions(-) diff --git a/.env.example b/.env.example index 0b33b40..98db207 100644 --- a/.env.example +++ b/.env.example @@ -1 +1,6 @@ -PORT = \ No newline at end of file +PORT = 3000 +DBNAME = databaseName +DBUSER = databaseUser +DBPASSWORD = databasePassword +DBHOST = 127.0.0.1 +DBDIALECT = postgres \ No newline at end of file diff --git a/README.md b/README.md index c54cd67..2da1500 100644 --- a/README.md +++ b/README.md @@ -7,8 +7,10 @@ Node.js, ExpressJs, Sequelize ORM, and PostgreSQL - Make sure to have Git and Node.js installed on your computer - Clone the project by running: `git clone https://https://github.com/devcareer/class-manager` - cd into the project and run `npm install` -- create a `config.js` file in the root folder and copy the content in the config.example.js`into it. -- run `sequelize db:migrate` to migrate to the database. +- create a `.env` file in the root folder and copy the content in the `.env.example`into it. +- run `npm run migrate` to migrate to the database. +- run `npm run migrate:undo` to undo migration. +- run `npm run seed` to seed the database. - run `npm start` to start the project. These are the HTTP response codes used in this project: @@ -16,6 +18,7 @@ These are the HTTP response codes used in this project: | --- | --- | | `200` | This `OK` status code indicates that a request has succeeded | | `400` | This `bad request error` status code indicates that the request sent to the server is incorrect | +| `404` | This `not found error` status code indicates that the resource is not found. | | `500` | This `internal server error` status code indicates that something has gone wrong on the web server |
From 07d64b9b08e8f4dc9193b736ca035f6c3c148063 Mon Sep 17 00:00:00 2001 From: Judy Date: Thu, 1 Dec 2022 11:35:36 +0000 Subject: [PATCH 4/5] initial commit --- src/controllers/scoreController.js | 106 +++++++++++++++++++++++++++++ src/index.js | 2 + src/routers/scoreRouter.js | 11 +++ src/services/scoreService.js | 68 ++++++++++++++++++ 4 files changed, 187 insertions(+) create mode 100644 src/controllers/scoreController.js create mode 100644 src/routers/scoreRouter.js create mode 100644 src/services/scoreService.js diff --git a/src/controllers/scoreController.js b/src/controllers/scoreController.js new file mode 100644 index 0000000..c829003 --- /dev/null +++ b/src/controllers/scoreController.js @@ -0,0 +1,106 @@ +import ScoreService from '../services/ScoreService.js'; +import Util from '../utils/Utils.js'; + +const util = new Util(); + +class ScoreController { + static async getAllScore(req, res) { + try { + const allScore = await ScoreService.getAllScores(); + if (allScores.length > 0) { + util.setSuccess(200, 'Scores retrieved', allScores); + } else { + util.setSuccess(200, 'No Score found'); + } + return util.send(res); + } catch (error) { + util.setError(400, error); + return util.send(res); + } + } + + static async addScore(req, res) { + if (!req.body.Score || !req.body.senderId || !req.body.receiverId) { + util.setError(400, 'Please provide complete details'); + return util.send(res); + } + const newScore = req.body; + try { + const createdScore = await ScoreService.addScore(newScore); + util.setSuccess(201, 'Score Added!', createdScore); + return util.send(res); + } catch (error) { + util.setError(400, error.Score); + return util.send(res); + } + } + + static async updatedScore(req, res) { + const alteredScore = req.body; + const { id } = req.params; + if (!Number(id)) { + util.setError(400, 'Please input a valid numeric value'); + return util.send(res); + } + try { + const updateScore = await ScoreService.updateScore(id, alteredScore); + if (!updateScore) { + util.setError(404, `Cannot find Score with the id: ${id}`); + } else { + util.setSuccess(200, 'Score updated', updateScore); + } + return util.send(res); + } catch (error) { + util.setError(404, error); + return util.send(res); + } + } + + static async getAScore(req, res) { + const { id } = req.params; + + if (!Number(id)) { + util.setError(400, 'Please input a valid numeric value'); + return util.send(res); + } + + try { + const theScore = await ScoreService.getAScore(id); + + if (!theScore) { + util.setError(404, `Cannot find Score with the id ${id}`); + } else { + util.setSuccess(200, 'Found Score', theScore); + } + return util.send(res); + } catch (error) { + util.setError(404, error); + return util.send(res); + } + } + + static async deleteScore(req, res) { + const { id } = req.params; + + if (!Number(id)) { + util.setError(400, 'Please provide a numeric value'); + return util.send(res); + } + + try { + const ScoreToDelete = await ScoreService.deleteScore(id); + + if (ScoreToDelete) { + util.setSuccess(200, 'Score deleted'); + } else { + util.setError(404, `Score with the id ${id} cannot be found`); + } + return util.send(res); + } catch (error) { + util.setError(400, error); + return util.send(res); + } + } +} + +export default ScoreController; \ No newline at end of file diff --git a/src/index.js b/src/index.js index 37930d1..26ec4f8 100644 --- a/src/index.js +++ b/src/index.js @@ -3,6 +3,7 @@ import dotenv from "dotenv"; import { assignmentRouter } from './api/routers/assignmentRouter.js'; import messageRouter from "./routers/MessageRouter.js"; import { studentRouter } from './routers/studentsRoutes.js'; +import { scoreRouter } from './routers/scoreRoutes.js'; const app = express(); dotenv.config(); @@ -12,6 +13,7 @@ app.use(express.urlencoded({ extended: true })); app.use('/api/message', messageRouter); app.use('/api/students', studentRouter); app.use('/api/assignment', assignmentRouter); +app.use('/api/score', scoreRouter); app.get('/', (req, res) => { diff --git a/src/routers/scoreRouter.js b/src/routers/scoreRouter.js new file mode 100644 index 0000000..aeda73b --- /dev/null +++ b/src/routers/scoreRouter.js @@ -0,0 +1,11 @@ +import { Router } from 'express'; +import scoreController from '../controllers/scoreController.js'; + +const scoreRouter = Router(); + + +scoreRouter.post('/', scoreController.addScore); +scoreRouter.put('/:id', scoreController.updatedScore); +scoreRouter.delete('/:id', scoreController.deleteScore); + +export default scoreRouter; \ No newline at end of file diff --git a/src/services/scoreService.js b/src/services/scoreService.js new file mode 100644 index 0000000..c551164 --- /dev/null +++ b/src/services/scoreService.js @@ -0,0 +1,68 @@ +import database from '../db/models/index.js'; + +class ScoreService { + static async getAllScores() { + try { + const result = await database.Score.findAll(); + return result; + } catch (error) { + throw error; + } + } + + static async addScore(newScore) { + try { + const result = await database.Score.create(newScore); + return result; + } catch (error) { + throw error; + } + } + + static async updateScore(id, updateScore) { + try { + const ScoreToUpdate = await database.Score.findOne({ + where: { id: Number(id) } + }); + + if (ScoreToUpdate) { + await database.Score.update(updateScore, { where: { id: Number(id) } }); + + return updateScore; + } + return null; + } catch (error) { + throw error; + } + } + + static async getScore(id) { + try { + const Score = await database.Score.findOne({ + where: { id: Number(id) } + }); + + return Score; + } catch (error) { + throw error; + } + } + + static async deleteScore(id) { + try { + const ScoreToDelete = await database.Score.findOne({ where: { id: Number(id) } }); + + if (ScoreToDelete) { + const deletedScore = await database.Score.destroy({ + where: { id: Number(id) } + }); + return deletedScore; + } + return null; + } catch (error) { + throw error; + } + } +} + +export default ScoreService; From 944e4aaae9e23b770832eafece40ef314929b027 Mon Sep 17 00:00:00 2001 From: Hazeem Date: Mon, 5 Dec 2022 15:22:32 +0100 Subject: [PATCH 5/5] chore(upload assignment):add route for student assignment upload --- package-lock.json | 52 ++++++++++++++++++++++++ package.json | 1 + src/controllers/assignmentsController.js | 18 ++++++++ src/index.js | 4 +- src/routers/assignmentRouter.js | 2 + src/services/assignmentService.js | 20 +++++++++ src/services/scoreService.js | 14 +++---- 7 files changed, 102 insertions(+), 9 deletions(-) diff --git a/package-lock.json b/package-lock.json index b964439..a258a0f 100644 --- a/package-lock.json +++ b/package-lock.json @@ -11,6 +11,7 @@ "body-parser": "^1.20.1", "dotenv": "^16.0.3", "express": "^4.18.2", + "express-fileupload": "^1.4.0", "pg": "^8.8.0", "pg-hstore": "^2.3.4", "sequelize": "^6.25.3" @@ -2971,6 +2972,17 @@ "node": ">=4" } }, + "node_modules/busboy": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/busboy/-/busboy-1.6.0.tgz", + "integrity": "sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA==", + "dependencies": { + "streamsearch": "^1.1.0" + }, + "engines": { + "node": ">=10.16.0" + } + }, "node_modules/bytes": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", @@ -4171,6 +4183,17 @@ "node": ">= 0.10.0" } }, + "node_modules/express-fileupload": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/express-fileupload/-/express-fileupload-1.4.0.tgz", + "integrity": "sha512-RjzLCHxkv3umDeZKeFeMg8w7qe0V09w3B7oGZprr/oO2H/ISCgNzuqzn7gV3HRWb37GjRk429CCpSLS2KNTqMQ==", + "dependencies": { + "busboy": "^1.6.0" + }, + "engines": { + "node": ">=12.0.0" + } + }, "node_modules/extend": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", @@ -7538,6 +7561,14 @@ "node": ">= 0.8" } }, + "node_modules/streamsearch": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/streamsearch/-/streamsearch-1.1.0.tgz", + "integrity": "sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg==", + "engines": { + "node": ">=10.0.0" + } + }, "node_modules/string_decoder": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", @@ -10596,6 +10627,14 @@ "resolved": "https://registry.npmjs.org/buffer-writer/-/buffer-writer-2.0.0.tgz", "integrity": "sha512-a7ZpuTZU1TRtnwyCNW3I5dc0wWNC3VR9S++Ewyk2HHZdrO3CQJqSpd+95Us590V6AL7JqUAH2IwZ/398PmNFgw==" }, + "busboy": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/busboy/-/busboy-1.6.0.tgz", + "integrity": "sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA==", + "requires": { + "streamsearch": "^1.1.0" + } + }, "bytes": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", @@ -11495,6 +11534,14 @@ "vary": "~1.1.2" } }, + "express-fileupload": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/express-fileupload/-/express-fileupload-1.4.0.tgz", + "integrity": "sha512-RjzLCHxkv3umDeZKeFeMg8w7qe0V09w3B7oGZprr/oO2H/ISCgNzuqzn7gV3HRWb37GjRk429CCpSLS2KNTqMQ==", + "requires": { + "busboy": "^1.6.0" + } + }, "extend": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", @@ -13938,6 +13985,11 @@ "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==" }, + "streamsearch": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/streamsearch/-/streamsearch-1.1.0.tgz", + "integrity": "sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg==" + }, "string_decoder": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", diff --git a/package.json b/package.json index 1499ac3..572d8fa 100644 --- a/package.json +++ b/package.json @@ -20,6 +20,7 @@ "body-parser": "^1.20.1", "dotenv": "^16.0.3", "express": "^4.18.2", + "express-fileupload": "^1.4.0", "pg": "^8.8.0", "pg-hstore": "^2.3.4", "sequelize": "^6.25.3" diff --git a/src/controllers/assignmentsController.js b/src/controllers/assignmentsController.js index 45bd09c..9d62b7e 100644 --- a/src/controllers/assignmentsController.js +++ b/src/controllers/assignmentsController.js @@ -105,6 +105,24 @@ class AssignmentController { return util.send(res); } } + + static async uploadAssignment(req, res) { + const { id } = req.params; + if (!req.files) { + util.setError(400, 'Please select a file for upload'); + return util.send(res); + } + const newUpload = req.files; + try { + await AssignmentService.uploadAssignment(newUpload, id); + util.setSuccess(201, 'Assignment Uploaded Successfully!'); + return util.send(res); + } catch (error) { + util.setError(400, error.Assignment); + return util.send(res); + } + } + } export default AssignmentController; \ No newline at end of file diff --git a/src/index.js b/src/index.js index 26ec4f8..2a9dc97 100644 --- a/src/index.js +++ b/src/index.js @@ -1,9 +1,9 @@ import express from "express"; import dotenv from "dotenv"; -import { assignmentRouter } from './api/routers/assignmentRouter.js'; +import { assignmentRouter } from './routers/assignmentRouter.js'; import messageRouter from "./routers/MessageRouter.js"; import { studentRouter } from './routers/studentsRoutes.js'; -import { scoreRouter } from './routers/scoreRoutes.js'; +import scoreRouter from './routers/scoreRouter.js'; const app = express(); dotenv.config(); diff --git a/src/routers/assignmentRouter.js b/src/routers/assignmentRouter.js index d4b7d2a..8b63f4c 100644 --- a/src/routers/assignmentRouter.js +++ b/src/routers/assignmentRouter.js @@ -1,4 +1,5 @@ import { Router } from "express"; +import fileUpload from "express-fileupload" const assignmentRouter = Router(); import AssignmentController from '../controllers/assignmentsController.js'; @@ -8,5 +9,6 @@ assignmentRouter.post('/', AssignmentController.addAssignment); assignmentRouter.get('/:id', AssignmentController.getAAssignment); assignmentRouter.put('/:id', AssignmentController.updatedAssignment); assignmentRouter.delete('/:id', AssignmentController.deleteAssignment); +assignmentRouter.post('/upload/:id', fileUpload({createParentPath: true}), AssignmentController.uploadAssignment); export { assignmentRouter }; \ No newline at end of file diff --git a/src/services/assignmentService.js b/src/services/assignmentService.js index 409fe23..ba7dcbd 100644 --- a/src/services/assignmentService.js +++ b/src/services/assignmentService.js @@ -1,4 +1,5 @@ import database from '../db/models/index.js'; +import path from 'path'; class AssignmentService { static async getAllAssignments() { @@ -63,6 +64,25 @@ class AssignmentService { throw error; } } + + static async uploadAssignment(files, id) { + // const validator = await database.Message.findOne({ + // where: { id: Number(id) } + // }) + // if(!validator){ + // util.setError(400, 'Please select a file for upload'); + // return util.send(res); + // } + try { + Object.keys(files).forEach(key => { + const filePath = path.join('./', 'files/assignmentSubmissions', `${id}`, files[key].name) + files[key].mv(filePath) + }) + } catch (error) { + throw error; + } + } + } export default AssignmentService; diff --git a/src/services/scoreService.js b/src/services/scoreService.js index c551164..2d0dd54 100644 --- a/src/services/scoreService.js +++ b/src/services/scoreService.js @@ -3,7 +3,7 @@ import database from '../db/models/index.js'; class ScoreService { static async getAllScores() { try { - const result = await database.Score.findAll(); + const result = await database.AssignmentScore.findAll(); return result; } catch (error) { throw error; @@ -12,7 +12,7 @@ class ScoreService { static async addScore(newScore) { try { - const result = await database.Score.create(newScore); + const result = await database.AssignmentScore.create(newScore); return result; } catch (error) { throw error; @@ -21,12 +21,12 @@ class ScoreService { static async updateScore(id, updateScore) { try { - const ScoreToUpdate = await database.Score.findOne({ + const ScoreToUpdate = await database.AssignmentScore.findOne({ where: { id: Number(id) } }); if (ScoreToUpdate) { - await database.Score.update(updateScore, { where: { id: Number(id) } }); + await database.AssignmentScore.update(updateScore, { where: { id: Number(id) } }); return updateScore; } @@ -38,7 +38,7 @@ class ScoreService { static async getScore(id) { try { - const Score = await database.Score.findOne({ + const Score = await database.AssignmentScore.findOne({ where: { id: Number(id) } }); @@ -50,10 +50,10 @@ class ScoreService { static async deleteScore(id) { try { - const ScoreToDelete = await database.Score.findOne({ where: { id: Number(id) } }); + const ScoreToDelete = await database.AssignmentScore.findOne({ where: { id: Number(id) } }); if (ScoreToDelete) { - const deletedScore = await database.Score.destroy({ + const deletedScore = await database.AssignmentScore.destroy({ where: { id: Number(id) } }); return deletedScore;