UNPKG

webgme-engine

Version:

WebGME server and Client API without a GUI

241 lines (203 loc) 8.42 kB
/*globals define*/ /*eslint-env node, browser*/ /** * @author kecso / https://github.com/kecso */ define([ 'common/core/CoreAssert' ], function (ASSERT) { 'use strict'; var MetaQueryCore = function (innerCore, options) { ASSERT(typeof options === 'object'); ASSERT(typeof options.globConf === 'object'); ASSERT(typeof options.logger !== 'undefined'); var logger = options.logger, self = this, key; for (key in innerCore) { this[key] = innerCore[key]; } logger.debug('initialized MetaQueryCore'); //<editor-fold=Helper Functions> function sensitiveFilter(validNodes) { var i; i = validNodes.length; while (i--) { if (self.isConnection(validNodes[i]) || self.isAbstract(validNodes[i])) { validNodes.splice(i, 1); } } } //</editor-fold> //<editor-fold=Modified Methods> //</editor-fold> //<editor-fold=Added Methods> this.isAbstract = function (node) { return self.getRegistry(node, 'isAbstract') === true; }; this.isConnection = function (node) { var validPtrNames = innerCore.getValidPointerNames(node); return validPtrNames.indexOf('dst') !== -1 && validPtrNames.indexOf('src') !== -1; }; this.getValidChildrenMetaNodes = function (parameters) { var validNodes = [], node = parameters.node, metaNodes = self.getAllMetaNodes(node), keys = Object.keys(metaNodes || {}), validChildren = innerCore.getValidChildrenPaths(node), i, j, typeCounters = {}, children = parameters.children || [], cache = parameters.cache || {}, rules, inAspect; rules = innerCore.getChildrenMeta(node) || {}; for (i = 0; i < keys.length; i += 1) { for (j = 0; j < validChildren.length; j += 1) { if (innerCore.isTypeOf(metaNodes[keys[i]], validChildren[j], cache)) { validNodes.push(metaNodes[keys[i]]); } } } //before every next step we check if we still have potential nodes if (validNodes.length === 0) { return validNodes; } if (parameters.sensitive === true) { sensitiveFilter(validNodes); } //before every next step we check if we still have potential nodes if (validNodes.length === 0) { return validNodes; } if (parameters.multiplicity === true) { if (rules.max && rules.max > -1 && innerCore.getChildrenRelids(node).length >= rules.max) { validNodes = []; return validNodes; } if (children.length === 0) { return validNodes; //we cannot check type-multiplicity without children } delete rules.max; delete rules.min; keys = Object.keys(rules); for (i = 0; i < children.length; i += 1) { for (j = 0; j < keys.length; j += 1) { if (innerCore.isTypeOf(children[i], keys[j])) { if (!typeCounters[keys[j]]) { typeCounters[keys[j]] = 0; } typeCounters[keys[j]] += 1; } } } i = validNodes.length; keys = Object.keys(typeCounters); while (i--) { for (j = 0; j < keys.length; j += 1) { if (rules[keys[j]].max && rules[keys[j]].max > -1 && rules[keys[j]].max <= typeCounters[keys[j]] && innerCore.isTypeOf(validNodes[i], keys[j])) { validNodes.splice(i, 1); //FIXME slow, use only push instead break; } } } } //before every next step we check if we still have potential nodes if (validNodes.length === 0) { return validNodes; } if (parameters.aspect) { keys = innerCore.getAspectMeta(node, parameters.aspect) || []; i = validNodes.length; while (i--) { inAspect = false; for (j = 0; j < keys.length; j += 1) { if (innerCore.isTypeOf(validNodes[i], keys[j])) { inAspect = true; break; } } if (!inAspect) { validNodes.splice(i, 1); } } } return validNodes; }; this.getValidSetElementsMetaNodes = function (parameters) { var validNodes = [], node = parameters.node, name = parameters.name, metaNodes = self.getAllMetaNodes(node), keys = Object.keys(metaNodes || {}), i, j, typeCounters = {}, members = parameters.members || [], rules = self.getPointerMeta(node, name) || {}; for (i = 0; i < keys.length; i += 1) { if (metaNodes[keys[i]] && self.isValidTargetOf(metaNodes[keys[i]], node, name)) { validNodes.push(metaNodes[keys[i]]); } } //before every next step we check if we still have potential nodes if (validNodes.length === 0) { return validNodes; } if (parameters.sensitive === true) { sensitiveFilter(validNodes); } //before every next step we check if we still have potential nodes if (validNodes.length === 0) { return validNodes; } if (parameters.multiplicity === true) { if (rules.max && rules.max > -1 && innerCore.getMemberPaths(node).length >= rules.max) { validNodes = []; return validNodes; } if (members.length === 0) { return validNodes; //we cannot check type-multiplicity without children } delete rules.max; delete rules.min; //we need to clear nodes that are not on the meta sheet // and we have to initialize the counters keys = Object.keys(rules); for (i = 0; i < keys.length; i += 1) { if (!metaNodes[keys[i]]) { delete rules[keys[i]]; } else { typeCounters[keys[i]] = 0; } } keys = Object.keys(rules); for (i = 0; i < members.length; i += 1) { for (j = 0; j < keys.length; j += 1) { if (innerCore.isTypeOf(members[i], keys[j])) { typeCounters[keys[j]] += 1; } } } i = validNodes.length; keys = Object.keys(typeCounters); while (i--) { for (j = 0; j < keys.length; j += 1) { if (rules[keys[j]].max && rules[keys[j]].max > -1 && rules[keys[j]].max <= typeCounters[keys[j]] && innerCore.isTypeOf(validNodes[i], keys[j])) { validNodes.splice(i, 1); //FIXME slow, use only push instead break; } } } } return validNodes; }; //</editor-fold> }; return MetaQueryCore; });