Skip to content

Commit

Permalink
Add resource management endpoints and validation for categories
Browse files Browse the repository at this point in the history
  • Loading branch information
guillecro committed Feb 13, 2025
1 parent 55b78e0 commit bce294d
Show file tree
Hide file tree
Showing 2 changed files with 300 additions and 4 deletions.
214 changes: 212 additions & 2 deletions controllers/resourceController.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,21 +7,34 @@ exports.fetch = async (req, res) => {
// get from query params page and limit (if not provided, default to 1 and 10)
const page = parseInt(req.query.page) || 1;
const limit = parseInt(req.query.limit) || 10;
const category = req.query.category || null;

// calculateOffset
const offset = (page - 1) * limit;

const where = {}

if(category) {
where.categoryId = category;
}

// query the database

const query = {
limit: limit,
offset: offset,
where: where
where: where,
include: [
{
model: models.ResourceCategory,
as: 'category',
attributes: ['id', 'name'],
},
],
order: [['updatedAt', 'DESC']],
}

const entries = await models.Resource.findAndCountAll(query)
const entries = await models.ResourceEntry.findAndCountAll(query)

// return the entries
return res.status(200).json(entries);
Expand All @@ -30,4 +43,201 @@ exports.fetch = async (req, res) => {
console.error(error);
return res.status(500).json({ message: msg.error.default });
}
}

exports.fetchOne = async (req, res) => {
try {
const id = req.params.id || null;

const entry = await models.ResourceEntry.findByPk(id, {
include: [
{
model: models.ResourceCategory,
as: 'category',
attributes: ['id', 'name'],
},
],
})

if(!entry) {
return res.status(400).json({ message: msg.error.default });
}

return res.status(200).json(entry);
} catch (error) {
console.error(error);
return res.status(500).json({ message: msg.error.default });
}
}

exports.create = async (req, res) => {
try {
const { title, description, url, categoryId } = req.body;

// check the category id exists

const category = await models.ResourceCategory.findByPk(categoryId)

if(!category) {
return res.status(400).json({ message: msg.error.default });
}

const entry = await models.ResourceEntry.create({
title,
categoryId,
description: description || null,
url
})

return res.status(200).json(entry);
} catch (error) {
console.error(error);
return res.status(500).json({ message: msg.error.default });
}
}

exports.update = async (req, res) => {
try {
const id = req.params.id || null;
const { title, description, url, categoryId } = req.body;

const category = await models.ResourceCategory.findByPk(categoryId)

if(!category) {
return res.status(400).json({ message: msg.error.default });
}

const entry = await models.ResourceEntry.findByPk(id)

if(!entry) {
return res.status(400).json({ message: msg.error.default });
}


entry.title = title;
entry.categoryId = categoryId;
entry.description = description;
entry.url = url;
await entry.save()

return res.status(200).json(entry);
} catch (error) {
console.error(error);
return res.status(500).json({ message: msg.error.default });
}
}

exports.delete = async (req, res) => {
try {
const id = req.params.id || null;

const entry = await models.ResourceEntry.findByPk(id)

if(!entry) {
return res.status(400).json({ message: msg.error.default });
}

await entry.destroy();

return res.status(200).send()
} catch (error) {
console.error(error);
return res.status(500).json({ message: msg.error.default });
}
}

exports.fetchCategories = async (req, res) => {
try {
const categories = await models.ResourceCategory.findAll({
attributes: ['id', 'name'],
});

return res.status(200).json(categories);
} catch (error) {
console.error(error);
return res.status(500).json({ message: msg.error.default });
}
}


exports.createCategory = async (req, res) => {
try {
// get all categories
const { name } = req.body;



const category = await models.ResourceCategory.create({
name
})

return res.status(200).json(category);

} catch (error) {
console.error(error);
res.status(500).json({ message: msg.error.default });
}
}

exports.updateCategory = async (req, res) => {
try {

const id = req.params.id || null;

// get all categories
const { name } = req.body;

const category = await models.ResourceCategory.findByPk(id)

if(!category) {
return res.status(400).json({ message: msg.error.default });
}

category.name = name;
await category.save()

return res.status(200).json(category);

} catch (error) {
console.error(error);
res.status(500).json({ message: msg.error.default });
}
}

exports.deleteCategory = async (req, res) => {
try {

const id = req.params.id || null;

// get all categories
const { categoryId } = req.body;

const category = await models.ResourceCategory.findByPk(id)

if(!category) {
return res.status(400).json({ message: msg.error.default });
}

const categoryToMigrate = await models.ResourceCategory.findByPk(categoryId)

if(!categoryToMigrate) {
return res.status(400).json({ message: msg.error.default });
}

await models.ResourceEntry.update({
categoryId: categoryToMigrate.id
}, {
where: {
categoryId: category.id
}
})

await category.destroy();

return res.status(200).send()

} catch (error) {
console.error(error);
res.status(500).json({ message: msg.error.default });
}
}
90 changes: 88 additions & 2 deletions routes/resource.js
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
const express = require('express');
const { check, query } = require('express-validator');
const { check, query, body, param } = require('express-validator');

const validate = require('../middlewares/validate');
const authorize = require('../middlewares/authorize');
const requiresAnon = require('../middlewares/requiresAnon');
const constants = require('../services/constants');
const ResourceController = require('../controllers/memberController');
const ResourceController = require('../controllers/resourceController');
const msg = require('../utils/messages');
const uploader = require('../middlewares/s3');

Expand All @@ -21,6 +21,92 @@ const router = express.Router();
// PUT /:id
// DELETE /:id
// -----------------------------------------------
router.get('/',
[
query('page').optional().isInt().withMessage(msg.validationError.integer),
query('limit').optional().isInt().withMessage(msg.validationError.integer),
query('category').optional().isInt().withMessage(msg.validationError.integer),
],
validate,
ResourceController.fetch
)

router.post('/',
authorize(constants.ROLES.ADMINISTRATOR),
[
check('title').isString().withMessage("TODO"),
check('categoryId').isInt().withMessage("TODO"),
check('description').optional().isString().withMessage("TODO"),
check('url').isURL().withMessage("Debe ser una URL válida"),
],
validate,
ResourceController.create
)


router.get('/category',
ResourceController.fetchCategories
)

router.post('/category',
authorize(constants.ROLES.ADMINISTRATOR),
[
body('name').isString().withMessage("El nuevo nombre es requerido"),
],
validate,
ResourceController.createCategory
)

router.put('/category/:id',
authorize(constants.ROLES.ADMINISTRATOR),
[
param('id').not().isEmpty().withMessage('id is required'),
body('name').isString().withMessage("El nuevo nombre es requerido"),
],
validate,
ResourceController.updateCategory
)

router.delete('/category/:id',
authorize(constants.ROLES.ADMINISTRATOR),
[
param('id').not().isEmpty().withMessage('id is required'),
body('categoryId').isInt().withMessage("El nuevo nombre es requerido"),
],
validate,
ResourceController.deleteCategory
)

router.get('/:id',
[
check('id').isInt().withMessage(msg.validationError.integer),
],
validate,
ResourceController.fetchOne
);


router.put('/:id',
authorize(constants.ROLES.ADMINISTRATOR),
[
check('title').isString().withMessage("TODO"),
check('categoryId').isInt().withMessage("TODO"),
check('description').optional().isString().withMessage("TODO"),
check('url').isURL().withMessage("Debe ser una URL válida"),
],
validate,
ResourceController.update
);

router.delete('/:id',
authorize(constants.ROLES.ADMINISTRATOR),
[
check('id').isInt().withMessage(msg.validationError.integer),
],
validate,
ResourceController.delete
);


// -----------------------------------------------

Expand Down

0 comments on commit bce294d

Please sign in to comment.