const _find = require("./find"); const httpStatus = require("http-status"); const { extractParamsFromRequest, handleErrorResponse, handleResultResponse, } = require("../../helpers/controller.helper"); function buildContext(req, config) { return { user: req.user, scopes: [], ...config, }; } const defaultOptions = { MODULE_NAME: "default", params: { find: { includeAll: false }, findOne: { includeAll: false, paginate: { limit: 1, page: 1 } }, count: {}, create: {}, update: {}, delete: {}, }, }; const generateControllers = (service, extraControllers = {}, options = {}) => { const _options = { ...defaultOptions, ...options, }; const defaultControllers = { find: (config) => { return async (req, res, next) => { config = config || { scopes: [], }; const params = extractParamsFromRequest(req, res, _options.params.find); try { const result = await service.fetchAll(params, buildContext(req, config)); return handleResultResponse(result.rows, result.count, params, res); } catch (error) { return handleErrorResponse(_options.MODULE_NAME, "find", error, res); } }; }, findOne: (config) => { return async (req, res, next) => { const params = extractParamsFromRequest(req, res, _options.params.findOne); try { let result = await service.fetchOne(params, buildContext(req, config)); result = _options.findOneCallback !== undefined ? _options.findOneCallback(result) : result; return handleResultResponse( result, null, params, res, result === null ? httpStatus.NOT_FOUND : httpStatus.OK ); } catch (error) { console.log(error); return handleErrorResponse(_options.MODULE_NAME, "findOne", error, res); } }; }, count: (config) => { return async (req, res, next) => { const params = extractParamsFromRequest(req, res, _options.params.count); try { const result = await service.count(params, buildContext(req, config)); return handleResultResponse(result, null, params, res); } catch (error) { return handleErrorResponse(_options.MODULE_NAME, "count", error, res); } }; }, create: (config) => { return async (req, res, next) => { const params = extractParamsFromRequest(req, res, _options.params.count); try { //Asignamos el usuario que crea el elemento si viene req.body.userId = req.user ? req.user.id : null; //Añadimos los parametros que vienen por url y en el body let values = Object.assign({}, params.params, req.body); //Quitamos el campo id si viniera, para que no de un conflicto con el id autoinc if (values.id) delete values.id; console.log(">> SERVICE CREATE ->", values); const result = await service.create(values, buildContext(req, config)); return handleResultResponse(result, null, null, res, httpStatus.CREATED); } catch (error) { return handleErrorResponse(_options.MODULE_NAME, "create", error, res); } }; }, update: (config) => { return async (req, res, next) => { try { const params = extractParamsFromRequest(req, res, _options.params.update); console.log("SERVICE UPDATE ->", params, req.body); const response = await service.update(params, req.body, buildContext(req, config)); // https://sequelize.org/master/class/lib/model.js~Model.html#static-method-update // Update devuelve un array de un elemento con el número de filas afectadas // por la operación. Por comodidad, devuelvo el valor, no el array. let result = response[0]; let status = httpStatus.OK; if (result < 1) { status = httpStatus.NOT_FOUND; } // Express no puede devolver números porque los confunde con el 'status'. // Convertimos a cadena. result = result.toString(); return handleResultResponse(result, null, req.params, res, status); } catch (error) { return handleErrorResponse(_options.MODULE_NAME, "update", error, res); } }; }, delete: (config) => { return async (req, res, next) => { try { const params = extractParamsFromRequest(req, res, _options.params.delete); console.log("SERVICE DELETE ->", params); const result = await service.delete(params, buildContext(req, config)); return handleResultResponse(result, null, req.params, res, httpStatus.NO_CONTENT); } catch (error) { return handleErrorResponse(_options.MODULE_NAME, "delete", error, res); } }; }, }; //const associationControllers = generateAssociationControllers(model, options); //console.log(associationControllers); return { ...defaultControllers, //...associationControllers ...extraControllers, }; }; module.exports = generateControllers; module.exports.buildContext = buildContext;