UNPKG

feathers-solr-node

Version:

Solr Adapter for Feathersjs. Base on Solr-client, so can also used as a Solr-client

243 lines (213 loc) 5.68 kB
const _ = require('./util'); const errors = require('@feathersjs/errors'); class QueryParser { constructor(options) { this.mapKey = { $select: 'fields', $search: 'query', $limit: 'limit', $skip: 'offset', $sort: 'sort', $facet: 'facet', $params: 'params' //$qf: "qf" //'$or':'filter' }; this.METHODS = ['$or']; this.setDefaultQuery(options); } setDefaultQuery(options) { this.defaultQuery = { query: '*:*', // TODO: score //filter: [], // sort: '', fields: _.get(options, 'query.$select') || '*', limit: _.get(options, 'paginate.default') || _.get(options, 'paginate.max') || 10, offset: 0 }; this.rowsMax = _.get(options, 'paginate.max'); } getDefaultQuery() { return this.defaultQuery; } parseQuery(query) { let queryObj = Object.assign({}, this.getDefaultQuery()); queryObj.filter = []; let keys = Object.keys(query); for (let item of keys) { if (this.mapKey[item]) { let value = this[item](item, query[item]); queryObj[this.mapKey[item]] = value; } else { let $filter = this.filterBuilder(item, query[item]); if ($filter) { queryObj.filter.push(...$filter); } else { return new errors.BadRequest(`undefined field ${item}`); } } } return queryObj; } filterBuilder(item, param) { if (item === '$or') { let value = this[item](item, param,true); return [value]; } if (item[0] === '$') { return false; } return this.filter(item, param); } filter(field, param) { let $filter = []; if (_.isObject(param)) { Object.keys(param).forEach(f => { if (f[0] === '$' && typeof this[f] !== 'undefined') { let condition = this[f](field, param[f]); $filter.push(condition); } else { $filter.push(...this.filter(f, param[f])); } }); } else if (Array.isArray(param)) { param = '(' + param.join(' OR ') + ')'; $filter.push(field + ':' + param); } else { $filter.push(field + ':' + param); } return $filter; } $search(field, param) { return param; } $limit(field, param) { return parseInt(param) > this.rowsMax ? this.rowsMax : param; } $skip(field, param) { return param; } $sort(field, param) { let order = []; Object.keys(param).forEach(name => { order.push(name + (parseInt(param[name]) === 1 ? ' asc' : ' desc')); }); return order.join(','); } $select(field, param) { if (Array.isArray(param)) { param = param.join(','); } return param; } $in(field, param) { if (Array.isArray(param)) { param = param.join('" OR "'); } return field + ':("' + param + '")'; } $nin(field, param) { if (Array.isArray(param)) { param = param.join('" OR "'); } return '!' + field + ':("' + param + '")'; } $between(field, param) { if (Array.isArray(param)) { param = param.join('" TO "'); } return field + ':["' + param + '"]'; } $lt(field, param) { return field + ':[* TO ' + param + '}'; } $lte(field, param) { return field + ':[* TO ' + param + ']'; } $gt(field, param) { return field + ':{' + param + ' TO *]'; } $gte(field, param) { return field + ':[' + param + ' TO *]'; } $ne(field, param) { if (Array.isArray(param)) { param = param.join('" OR "'); } return '!' + field + ':"' + param + '"'; } $or(field, param, root) { let operator = 'OR'; var $filter = []; if (Array.isArray(param)) { param.forEach(item => { let fq = this.filter(field, item); if(fq.length>1){ fq = '(' +fq.join(' AND ') +')'; } $filter.push(fq); // var f = Object.keys(item)[0]; // if (f[0] === '$' && typeof this[f] !== 'undefined') { // let condition = this[f](f, item[f]); // $filter.push(condition); // } else { // $filter.push(...this.filter(f, item[f])); // } }); } else { Object.keys(param).forEach(item => { if (item[0] === '$' && typeof param[item] !== 'undefined') { let condition = this[item](item, param[item]); $filter.push(condition); } else { $filter.push(...this.filter(item, param[item])); } }); } if(root && $filter.length || $filter.length==1){ return $filter.join(` ${operator} `); } else if ($filter.length > 1) { return '('+ $filter.join(` ${operator} `) + ')'; } return []; } // $or(field, param) { // return this['$andor']('or', param); // } $and(field, param) { return this['$andor']('or', param); } $qf(field, params) { return Object.assign({}, this.query.params || {}, { qf: params }); } $facet(field, params) { return params; } $params(field, params) { //return Object.assign(this.query.params || {}, params); return params; } parseDelete(id, params) { if (id === '*' || id === '*:*') { return { delete: { query: '*:*' } }; } else if (id) { return { delete: { id: id } }; } else if (_.isObject(params)) { let query = []; Object.keys(params).forEach(field => { let filter = this.filterBuilder(field, params[field]); query.push(...filter); }); return { delete: { query: query.join(' AND ') } }; } return { delete: { query: '*:*' } }; } } module.exports = QueryParser;