Skip to content

Commit e702c80

Browse files
committed
feat(request comments): request comments
- setup controller for user to comment on requests - setup route for user to comment on requests - setup unit test for user to comment on requests route [Delivers #167750066]
1 parent 3b53b80 commit e702c80

File tree

12 files changed

+604
-3
lines changed

12 files changed

+604
-3
lines changed

src/controllers/commentsController.js

Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
import models from '../models';
2+
import { successResponse, errorResponse, status } from '../utils';
3+
4+
const { Comments, Requests } = models;
5+
6+
/**
7+
* @class CommentsController
8+
* @description Controllers for handling travel requests comments
9+
* @exports CommentsController
10+
*/
11+
class CommentsController {
12+
/**
13+
* @method addComment
14+
* @description Method to add comment to requests
15+
* @param {object} req - The Request Object
16+
* @param {object} res - The Response Object
17+
* @returns {object} Newly added request comment
18+
*/
19+
static async addComment(req, res) {
20+
const { userId } = req.user;
21+
const { requestId } = req.params;
22+
const { comment } = req.body;
23+
try {
24+
const existingRequest = await Requests.findOne({
25+
where: { id: requestId }
26+
});
27+
if (!existingRequest) {
28+
return errorResponse(res, status.notfound, 'Request does not exist');
29+
}
30+
const commentAdded = await Comments.create({ comment, userId, requestId });
31+
const response = commentAdded.toJSON();
32+
return successResponse(res, status.created, 'Comment added successfully', response);
33+
} catch (error) {
34+
return errorResponse(res, status.error, 'Error adding comment');
35+
}
36+
}
37+
38+
/**
39+
* @method getSingleComment
40+
* @description Method to get a comment
41+
* @param {object} req - The Request Object
42+
* @param {object} res - The Response Object
43+
* @returns {object} retrieved comment details
44+
*/
45+
static async getCommentById(req, res) {
46+
const { commentId } = req.params;
47+
try {
48+
const getComment = await Comments.findByPk(commentId);
49+
if (!getComment) {
50+
return errorResponse(res, status.notfound, 'Comment not found');
51+
}
52+
const response = getComment.toJSON();
53+
return successResponse(res, status.success, 'Comment retrieved successfully', response);
54+
} catch (error) {
55+
return errorResponse(res, status.error, 'Error retrieving comment');
56+
}
57+
}
58+
59+
/**
60+
* @method updateComment
61+
* @description Method to update comment
62+
* @param {object} req - The Request Object
63+
* @param {object} res - The Response Object
64+
* @returns {object} updated comment details
65+
*/
66+
static async updateCommentById(req, res) {
67+
const { commentId } = req.params;
68+
const { comment } = req.body;
69+
try {
70+
const getComment = await Comments.findOne({ where: { id: commentId } });
71+
if (!getComment) {
72+
return errorResponse(res, status.notfound, 'Comment not found');
73+
}
74+
await Comments.update({ comment }, { where: { id: commentId } });
75+
return successResponse(res, status.success, 'Comment updated successfully');
76+
} catch (error) {
77+
return errorResponse(res, status.error, 'Error updating comment');
78+
}
79+
}
80+
81+
/**
82+
* @method deleteComment
83+
* @description Method to delete comment
84+
* @param {object} req - The Request Object
85+
* @param {object} res - The Response Object
86+
* @returns {object} deleted comment details
87+
*/
88+
static async deleteCommentById(req, res) {
89+
const { commentId } = req.params;
90+
try {
91+
const getComment = await Comments.findByPk(commentId);
92+
if (!getComment) {
93+
return errorResponse(res, status.notfound, 'Comment not found');
94+
}
95+
await Comments.destroy({ where: { id: commentId } });
96+
return successResponse(res, status.success, 'Comment deleted successfully');
97+
} catch (error) {
98+
return errorResponse(res, status.error, 'Error deleting comment');
99+
}
100+
}
101+
102+
/**
103+
* @method getAllCommentsOnRequest
104+
* @description Method to get all comments on requests
105+
* @param {object} req - The Request Object
106+
* @param {object} res - The Response Object
107+
* @returns {object} retrieved comments details
108+
*/
109+
static async getAllCommentsOnRequest(req, res) {
110+
const { requestId } = req.params;
111+
try {
112+
const existingRequest = await Requests.findOne({ where: { id: requestId } });
113+
if (!existingRequest) {
114+
return errorResponse(res, status.notfound, 'Request not found');
115+
}
116+
const response = await Comments.findAll({ where: { requestId } });
117+
return successResponse(res, status.success, 'Comments retrieved successfully', response);
118+
} catch (error) {
119+
return errorResponse(res, status.error, 'Error retrieving comments');
120+
}
121+
}
122+
}
123+
124+
export default CommentsController;

src/controllers/index.js

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,9 @@ import UsersController from './users';
22
import ResetPasswordController from './resetPassword';
33
import AccommodationController from './accommodationController';
44
import RoomController from './roomController';
5+
import CommentsController from './commentsController';
56

67
export {
78
UsersController, ResetPasswordController,
8-
AccommodationController, RoomController
9+
AccommodationController, RoomController, CommentsController
910
};
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
export default {
2+
up: queryInterface => queryInterface.bulkInsert(
3+
'Requests',
4+
[
5+
{
6+
id: '2b770fbc-76e6-4b5a-afab-882759fd1f06',
7+
status: 'pending',
8+
accommodationId: '2b770fbc-76e6-4b5a-afab-882759fd1f06',
9+
userId: 'e71c28fd-73d8-4d92-9125-ab3d022093b9'
10+
},
11+
{
12+
id: 'b356097c-c6d0-4a3d-85f6-33bc2595c974',
13+
status: 'rejected',
14+
accommodationId: '2b770fbc-76e6-4b5a-afab-882759fd1f06',
15+
userId: 'e71c28fd-73d8-4d92-9125-ab3d022093b0'
16+
},
17+
{
18+
id: '777f640e-a2ff-45ee-9ce1-bf37645c42d6',
19+
status: 'approved',
20+
accommodationId: '2b770fbc-76e6-4b5a-afab-882759fd1f06',
21+
userId: '7aa38d4e-7fbf-4067-8821-9c27d2fb6e3a'
22+
},
23+
],
24+
{}
25+
),
26+
27+
down: queryInterface => queryInterface.bulkDelete('Requests', null, {})
28+
};
29+
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
export default {
2+
up: queryInterface => queryInterface.bulkInsert(
3+
'Comments',
4+
[
5+
{
6+
id: '2b770fbc-76e6-4b5a-afab-882759fd1f06',
7+
comment: 'my added comment',
8+
userId: 'e71c28fd-73d8-4d92-9125-ab3d022093b9',
9+
requestId: '2b770fbc-76e6-4b5a-afab-882759fd1f06'
10+
},
11+
{
12+
id: 'b356097c-c6d0-4a3d-85f6-33bc2595c974',
13+
comment: 'my added comment',
14+
userId: 'e71c28fd-73d8-4d92-9125-ab3d022093b0',
15+
requestId: '2b770fbc-76e6-4b5a-afab-882759fd1f06'
16+
},
17+
{
18+
id: '777f640e-a2ff-45ee-9ce1-bf37645c42d6',
19+
comment: 'mu added comment',
20+
userId: '7aa38d4e-7fbf-4067-8821-9c27d2fb6e3a',
21+
requestId: '2b770fbc-76e6-4b5a-afab-882759fd1f06',
22+
},
23+
],
24+
{}
25+
),
26+
27+
down: queryInterface => queryInterface.bulkDelete('Comments', null, {})
28+
};
29+

src/models/Comment.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ export default (sequelize, DataTypes) => {
77
}, {});
88
Comment.associate = (models) => {
99
Comment.belongsTo(models.Users, { as: 'theComment', foreignKey: 'userId' });
10+
Comment.belongsTo(models.Requests, { as: 'theRequest', foreignKey: 'requestId' });
1011
};
1112
return Comment;
1213
};

src/models/Request.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ export default (sequelize, DataTypes) => {
77
},
88
}, {});
99
Request.associate = (models) => {
10-
Request.hasMany(models.Comments, { as: 'requestComments', foreignKey: 'reqId' });
10+
Request.hasMany(models.Comments, { as: 'requestComments', foreignKey: 'requestId' });
1111
Request.hasMany(models.Trips, { as: 'requestTrips', foreignKey: 'reqId' });
1212
};
1313
return Request;

src/routes/api/comments.js

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
import { Router } from 'express';
2+
import { CommentsController } from '../../controllers';
3+
import middlewares from '../../middlewares';
4+
5+
const router = new Router();
6+
7+
const { validate, Authenticate } = middlewares;
8+
const { verifyToken } = Authenticate;
9+
10+
const {
11+
addComment, getCommentById, deleteCommentById, updateCommentById, getAllCommentsOnRequest
12+
} = CommentsController;
13+
14+
router.post('/requests/:requestId/comments', verifyToken, validate('addComment'), addComment);
15+
router.get('/comments/:commentId', verifyToken, getCommentById);
16+
router.patch('/comments/:commentId', verifyToken, validate('addComment'), updateCommentById);
17+
router.delete('/comments/:commentId', verifyToken, deleteCommentById);
18+
router.get('/requests/:requestId/comments', verifyToken, getAllCommentsOnRequest);
19+
20+
21+
export default router;

src/routes/index.js

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@ import authRoutes from './api/auth';
44
import resetPasswordRoute from './api/resetPassword';
55
import accommodationRoute from './api/accommodation';
66
import roomRoute from './api/room';
7+
import commentsRoute from './api/comments';
8+
79

810
const router = express.Router();
911

@@ -12,5 +14,7 @@ router.use('/users', userRoute);
1214
router.use('/', resetPasswordRoute);
1315
router.use('/', accommodationRoute);
1416
router.use('/', roomRoute);
17+
router.use('/', commentsRoute);
18+
1519

1620
export default router;

0 commit comments

Comments
 (0)