UNPKG

@nodeswork/sbase

Version:

Basic REST api foundation from Nodeswork.

134 lines (132 loc) 4.29 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); require("../mongoose/model-config"); const _ = require("underscore"); const debug_1 = require("debug"); const object_path_1 = require("object-path"); const d = debug_1.default('sbase:overrides'); /** * Generate an overrides middleware to help build mongoose queries. * * 1. Fetch query params to override query: * overrides('request.query.status->query.status') * overrides('request.body.status->query.status') * * 2. Set object to override query: * overrides(['constValue', 'query.status']) * * 3. Extract object from ctx: * overrides([(ctx) => * moment(ctx.request.query.date).startOf('month').toDate(), * 'query.date', * ]) * * 4. Append to array target: * overrides(['constValue', 'query.$or.[].status']) */ function overrides(...rules) { const rs = []; for (const rule of rules) { if (_.isString(rule)) { const [os, odWithFormat] = rule.split('->'); const [od, format, ...args] = odWithFormat.split(':'); if (!od) { throw new Error(`Rule ${rule} is not correct`); } if (format != null && format !== 'regex' && format !== 'date' && format !== 'string' && format !== 'seconds') { throw new Error(`Unknown format ${format}`); } rs.push({ src: split(os), dst: split(od), format: format, args, }); } else { const [os, odWithFormat, format1, ...args1] = rule; const [od, format, ...args] = odWithFormat.split(':'); rs.push({ src: _.isFunction(os) ? os : () => os, dst: split(od), format: (format || format1), args: args.concat(args1), }); } } d('Prepared overrides: %O', rs); return async (ctx, next) => { for (const { src, dst, format, args } of rs) { let value; if (_.isArray(src)) { value = object_path_1.withInheritedProps.get(ctx, src); } else if (_.isFunction(src)) { value = src(ctx); if (value && value.then) { value = await value; } } switch (format) { case 'regex': value = new RegExp(value, ...args); break; case 'date': value = new Date(value); break; case 'string': value = value.toString(); break; case 'seconds': value = new Date(value).getTime() / 1000; break; } if (value !== undefined) { setValue(ctx, ['overrides'].concat(dst), value); d('Set overrides %O with value %O, result: %O', dst, value, ctx.overrides); } } await next(); }; } exports.overrides = overrides; function clearOverrides() { return async (ctx, next) => { ctx.overrides = { query: {}, doc: {}, }; await next(); }; } exports.clearOverrides = clearOverrides; function setValue(target, keys, value) { const parts = []; keys = _.map(keys, (key) => { if (key === '[]') { if (!object_path_1.withInheritedProps.has(target, parts)) { object_path_1.withInheritedProps.set(target, parts, []); } key = object_path_1.withInheritedProps.get(target, parts).length.toString(); } parts.push(key); return key; }); object_path_1.withInheritedProps.set(target, keys, value); } function split(str) { const strs = str.split('.'); for (let i = strs.length - 1; i >= 1; i--) { if (strs[i - 1].endsWith('\\')) { strs[i - 1] = strs[i - 1].substring(0, strs[i - 1].length - 1) + '.' + strs[i]; strs[i] = ''; } } return _.filter(strs, (x) => !!x); } //# sourceMappingURL=overrides.js.map