UNPKG

@comodinx/query-parser

Version:

@comodinx/query-parser is a module for parser query parameters on ORM object (sequelize).

225 lines (224 loc) 8.1 kB
"use strict"; var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) { if (k2 === undefined) k2 = k; var desc = Object.getOwnPropertyDescriptor(m, k); if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) { desc = { enumerable: true, get: function() { return m[k]; } }; } Object.defineProperty(o, k2, desc); }) : (function(o, m, k, k2) { if (k2 === undefined) k2 = k; o[k2] = m[k]; })); var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) { Object.defineProperty(o, "default", { enumerable: true, value: v }); }) : function(o, v) { o["default"] = v; }); var __importStar = (this && this.__importStar) || (function () { var ownKeys = function(o) { ownKeys = Object.getOwnPropertyNames || function (o) { var ar = []; for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k; return ar; }; return ownKeys(o); }; return function (mod) { if (mod && mod.__esModule) return mod; var result = {}; if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]); __setModuleDefault(result, mod); return result; }; })(); Object.defineProperty(exports, "__esModule", { value: true }); exports.parseProperties = void 0; const lodash_1 = require("lodash"); const constants = __importStar(require("./constants")); // // helpers // const getDefaultSeparator = (type, query, options) => { return (((0, lodash_1.isObject)(query) ? query[`${type}Separator`] : undefined) || ((0, lodash_1.isObject)(options) ? options[`${type}Separator`] : undefined) || constants.propertiesSeparator); }; const getDefaultConcatenator = (type, query, options) => { return (((0, lodash_1.isObject)(query) ? query[`${type}Concatenator`] : undefined) || ((0, lodash_1.isObject)(options) ? options[`${type}Concatenator`] : undefined) || constants.propertiesConcatenator); }; /** * Indicate if property is remote property * * r-person * \/ -> This is the remote prefix. Then, return true * * person * \____/ -> This is the normal property. Then, return false */ const isRemoteProperty = (property) => property.startsWith(constants.propertiesRemotePrefix); /** * Normalize remote property if necesary * * r-person * \______/ -> This is the remote prefix. Then, return "person" * * person * \____/ -> This is the normal property. Then, return "person" */ const normalizeRemoteProperty = (property) => property.replace(constants.propertiesRemotePrefix, ""); /** * Indicate if property is extra property * * e-person * \/ -> This is the extra prefix. Then, return true * * person * \____/ -> This is the normal property. Then, return false */ const isExtraProperty = (property) => property.startsWith(constants.propertiesExtraPrefix); /** * Normalize extra property if necesary * * e-person * \______/ -> This is the extra prefix. Then, return "person" * * person * \____/ -> This is the normal property. Then, return "person" */ const normalizeExtraProperty = (property) => property.replace(constants.propertiesExtraPrefix, ""); /** * Normalize remote or extra property if necesary * * r-person * \______/ -> This is the remote prefix. Then, return "person" * e-person * \______/ -> This is the extra prefix. Then, return "person" * * person * \____/ -> This is the normal property. Then, return "person" */ const normalizeRemoteExtraProperty = (property) => normalizeExtraProperty(normalizeRemoteProperty(property)); /** * Save related property in correct location * * r-person * \______/ -> This is the remote prefix. Then, save in opts.remotes * * person * \____/ -> This is the normal property. Then, save in carry */ const resolveProperty = (opts, property, carry) => { // Check if property is remote property // // r-person // \/ -> This is the remote prefix // if (isRemoteProperty(property)) { const rawProperty = normalizeRemoteProperty(property); opts.remotes = opts.remotes || []; if (!opts.remotes.includes(rawProperty)) { opts.remotes.push(rawProperty); } } // Check if property is extra property // // e-person // \/ -> This is the extra prefix // else if (isExtraProperty(property)) { const rawProperty = normalizeExtraProperty(property); opts.extras = opts.extras || []; if (!opts.extras.includes(rawProperty)) { opts.extras.push(rawProperty); } } // Handle simple property // // user // \__/ -> This is the simple property // else if (!carry.includes(property)) { carry.push(property); } }; const resolveRelationship = (context, type, property) => { type = constants.propertiesMapTypes[type] || type; if (!isRemoteProperty(property) && !isExtraProperty(property)) { context[type] = context[type] || []; } resolveProperty(context, property, context[type]); }; // // source code // const parseProperties = (query, type, options = {}) => { if (!query || !query[type] || ((0, lodash_1.isString)(query[type]) && !query[type].trim())) { return; } const concatenator = getDefaultConcatenator(type, query, options); const separator = getDefaultSeparator(type, query, options); const properties = (0, lodash_1.isString)(query[type]) ? query[type].trim().split(separator) : query[type]; const opts = { [type]: [] }; opts[type] = (0, lodash_1.reduce)(properties, (carry, property) => { let isFirstLevelProperty = true; let parentPropertyName; let parentPropertyOpts; // Check if property is complex. // // user.status // | -> This is the concatenator // if (property.includes(concatenator)) { property.split(concatenator).forEach((partOfProperty) => { const rawProperty = normalizeRemoteExtraProperty(partOfProperty); // Check if is initial part of property. // // user.status // \__/ -> This part // if (isFirstLevelProperty) { isFirstLevelProperty = false; if (!options.skipFirstLevelProperty) { resolveProperty(opts, partOfProperty, carry); } } else { // prepare relations options parentPropertyOpts.relations = parentPropertyOpts.relations || {}; parentPropertyOpts.relations[parentPropertyName] = parentPropertyOpts.relations[parentPropertyName] || {}; // Resolve no first parts of property. // // user.status... // \_____________ -> This parts // resolveRelationship(parentPropertyOpts.relations[parentPropertyName], type, partOfProperty); } // save previous property options parentPropertyOpts = (parentPropertyOpts && parentPropertyOpts.relations && parentPropertyOpts.relations[parentPropertyName || rawProperty]) || opts; // save previous property name parentPropertyName = normalizeRemoteExtraProperty(partOfProperty); }); } // Handle single property // // status // | -> Property without concatenator // else { resolveProperty(opts, property, carry); } return carry; }, opts[type]); return opts; }; exports.parseProperties = parseProperties;