UNPKG

jaydata

Version:

Cross-platform HTML5 data-management, JavaScript Language Query (JSLQ) support for OData, SQLite, WebSQL, IndexedDB, YQL and Facebook (packaged for Node.JS)

447 lines (425 loc) 26.6 kB
'use strict'; Object.defineProperty(exports, "__esModule", { value: true }); var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol ? "symbol" : typeof obj; }; var _index = require('../TypeSystem/index.js'); var _index2 = _interopRequireDefault(_index); function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } _index2.default.Class.define('$data.ModelBinder', null, null, { constructor: function constructor(context) { this.context = context; this.providerName = null; if (this.context.storageProvider && typeof this.context.storageProvider.getType === 'function') { this.references = !(this.context.storageProvider.providerConfiguration.modelBinderOptimization || false); this.providerName = this.context.storageProvider.providerName; if (!this.providerName) { for (var i in _index2.default.RegisteredStorageProviders) { if (_index2.default.RegisteredStorageProviders[i] === this.context.storageProvider.getType()) { this.providerName = i; break; } } } } }, _deepExtend: function _deepExtend(o, r) { if (o === null || o === undefined) { return r; } for (var i in r) { if (o.hasOwnProperty(i)) { if (_typeof(r[i]) === 'object') { if (Array.isArray(r[i])) { for (var j = 0; j < r[i].length; j++) { if (o[i].indexOf(r[i][j]) < 0) { o[i].push(r[i][j]); } } } else this._deepExtend(o[i], r[i]); } } else { o[i] = r[i]; } } return this._finalize(o); }, _finalize: function _finalize(o) { if (o instanceof _index2.default.Entity) { o.changedProperties = undefined; o.storeToken = this.context.storeToken; } return o; }, _buildSelector: function _buildSelector(meta, context) { if (meta.$selector) { if (!Array.isArray(meta.$selector)) { meta.$selector = [meta.$selector]; } for (var i = 0; i < meta.$selector.length; i++) { var selector = meta.$selector[i].replace('json:', ''); context.src += 'if('; var path = selector.split('.'); for (var j = 0; j < path.length; j++) { context.src += 'di["' + path.slice(0, j + 1).join('"]["') + '"]' + (j < path.length - 1 ? ' && ' : ' !== undefined && typeof di.' + selector + ' === "object"'); } context.src += '){di = di["' + path.join('"]["') + '"];}' + (i < meta.$selector.length - 1 ? 'else ' : ''); } context.src += 'if (di === null){'; if (context.iter) context.src += context.iter + ' = null;'; context.src += 'return null;'; context.src += '}'; } }, _buildKey: function _buildKey(name, type, keys, context, data) { if (keys) { var type = _index.Container.resolveType(type); var typeIndex = _index.Container.getIndex(type); type = type.fullName || type.name; context.src += 'var ' + name + 'Fn = function(di){'; if (!Array.isArray(keys) || keys.length == 1) { if (typeof keys !== 'string') keys = keys[0]; context.src += 'if (typeof di["' + keys + '"] === "undefined") return undefined;'; context.src += 'if (di["' + keys + '"] === null) return null;'; context.src += 'var key = ("' + type + '_' + typeIndex + '_' + keys + '#" + di["' + keys + '"]);'; } else { context.src += 'var key = "";'; for (var i = 0; i < keys.length; i++) { var id = _typeof(keys[i]) !== 'object' ? keys[i] : keys[i].$source; context.src += 'if (typeof di["' + id + '"] === "undefined") return undefined;'; context.src += 'if (di["' + id + '"] === null) return null;'; context.src += 'key += ("' + type + '_' + typeIndex + '_' + id + '#" + di["' + id + '"]);'; } } context.src += 'return key;};'; } context.src += 'var ' + name + ' = ' + (keys ? name + 'Fn(' + (data || 'di') + ')' : 'undefined') + ';'; }, build: function build(meta, context) { if (meta.$selector) { if (!Array.isArray(meta.$selector)) meta.$selector = [meta.$selector]; for (var i = 0; i < meta.$selector.length; i++) { meta.$selector[i] = meta.$selector[i].replace('json:', ''); } } if (meta.$value) { if (typeof meta.$value === 'function') { context.src += 'var di = di || data;'; context.src += 'var fn = function(){ return meta' + (context.meta.length ? '.' + context.meta.join('.') : '') + '.$value.call(self, meta' + (context.meta.length ? '.' + context.meta.join('.') : '') + ', di); };'; if (meta.$type) { var type = _index.Container.resolveName(_index.Container.resolveType(meta.$type)); var typeIndex = _index.Container.getIndex(_index.Container.resolveType(meta.$type)); var converter = this.context.storageProvider.fieldConverter.fromDb[type]; if (converter) { context.item = 'self.context.storageProvider.fieldConverter.fromDb["' + type + '"](fn())'; } else { context.item = 'new (Container.resolveByIndex(' + typeIndex + '))(fn())'; } } else context.item = 'fn()'; } else if (meta.$type) { var type = _index.Container.resolveName(_index.Container.resolveType(meta.$type)); var typeIndex = _index.Container.getIndex(_index.Container.resolveType(meta.$type)); var converter = this.context.storageProvider.fieldConverter.fromDb[type]; if (converter) { context.item = 'self.context.storageProvider.fieldConverter.fromDb["' + type + '"](' + meta.$value + ')'; } else { context.item = 'new (Container.resolveByIndex(' + typeIndex + '))(' + meta.$value + ')'; } } else context.item = meta.$value; } else if (meta.$source) { var type = _index.Container.resolveName(_index.Container.resolveType(meta.$type)); var typeIndex = _index.Container.getIndex(_index.Container.resolveType(meta.$type)); var converter = this.context.storageProvider.fieldConverter.fromDb[type]; var item = '_' + type.replace(/\./gi, '_') + '_'; if (!context.forEach) context.src += 'var di = data;'; context.item = item; this._buildSelector(meta, context); if (converter) { context.src += 'var ' + item + ' = self.context.storageProvider.fieldConverter.fromDb["' + type + '"](di["' + meta.$source + '"]);'; } else { context.src += 'var ' + item + ' = new (Container.resolveByIndex(' + typeIndex + '))(di["' + meta.$source + '"]);'; } context.src += 'var ' + item + '_inheritance;'; } else if (meta.$item) { context.meta.push('$item'); var iter = context.item && context.current ? context.item + '.' + context.current : context.item ? context.item : 'result'; context.iter = iter; if (iter.indexOf('.') < 0) { context.src += 'var ' + iter + ';'; context.src += 'var ' + iter + '_inheritance;'; } context.src += 'var fn = function(di){'; if (meta.$selector) { context.src += 'if (typeof di !== "undefined" && !(Array.isArray(di))){'; this._buildSelector(meta, context); context.src += '}'; } if (this.references && meta.$keys) this._buildKey('forKey', meta.$type, meta.$keys, context); context.src += iter + ' = typeof ' + iter + ' == "undefined" ? [] : ' + iter + ';'; if (this.references && meta.$item.$keys) { var keycacheName = 'keycache_' + iter.replace(/\./gi, '_'); context.src += 'var ' + keycacheName + ';'; context.src += 'var kci = keycacheIter.indexOf(' + iter + ');'; context.src += 'if (kci < 0){'; context.src += keycacheName + ' = [];'; context.src += 'keycache.push(' + keycacheName + ');'; context.src += 'keycacheIter.push(' + iter + ');'; context.src += '}else{'; context.src += keycacheName + ' = keycache[kci];'; context.src += '}'; } context.iter = undefined; context.forEach = true; var itemForKey = 'itemForKey_' + iter.replace(/\./gi, '_'); context.src += 'var forEachFn = function(di, i){'; context.src += 'var diBackup = di;'; if (this.providerName == "sqLite" && this.references && meta.$item.$keys) this._buildKey(itemForKey, meta.$type, meta.$item.$keys, context); var item = context.item || 'iter'; context.item = item; if (!meta.$item.$source) { this._buildSelector(meta.$item, context); } this.build(meta.$item, context); if (this.references && meta.$keys) { context.src += 'if (forKey){'; context.src += 'if (cache[forKey]){'; context.src += iter + ' = cache[forKey];'; context.src += 'if (' + iter + '.indexOf(' /*+ (context.item || item) + '_inheritance || '*/ + (context.item || item) + ') < 0){'; context.src += iter + '.push(' /*+ (context.item || item) + '_inheritance || '*/ + (context.item || item) + ');'; context.src += '}}else{'; context.src += 'cache[forKey] = ' + iter + ';'; context.src += iter + '.push(' /*+ (context.item || item) + '_inheritance || '*/ + (context.item || item) + ');'; context.src += '}}else{'; if (this.references && meta.$item.$keys) this._buildKey('cacheKey', meta.$type, meta.$item.$keys, context, 'diBackup'); context.src += 'if (typeof cacheKey != "undefined" && cacheKey !== null){'; context.src += 'if (keycache_' + iter.replace(/\./gi, '_') + ' && cacheKey){'; context.src += 'if (keycache_' + iter.replace(/\./gi, '_') + '.indexOf(cacheKey) < 0){'; context.src += iter + '.push(' /*+ (context.item || item) + '_inheritance || '*/ + (context.item || item) + ');'; context.src += 'keycache_' + iter.replace(/\./gi, '_') + '.push(cacheKey);'; context.src += '}'; context.src += '}else{'; context.src += iter + '.push(' /*+ (context.item || item) + '_inheritance || '*/ + (context.item || item) + ');'; context.src += '}'; context.src += '}'; context.src += '}'; } else { if (this.references && meta.$item.$keys) { context.src += 'if (typeof ' + itemForKey + ' !== "undefined" && ' + itemForKey + ' !== null){'; context.src += 'if (typeof keycache_' + iter.replace(/\./gi, '_') + ' !== "undefined" && ' + itemForKey + '){'; context.src += 'if (keycache_' + iter.replace(/\./gi, '_') + '.indexOf(' + itemForKey + ') < 0){'; context.src += iter + '.push(' /*+ (context.item || item) + '_inheritance || '*/ + (context.item || item) + ');'; context.src += 'keycache_' + iter.replace(/\./gi, '_') + '.push(' + itemForKey + ');'; context.src += '}}else{'; context.src += iter + '.push(' /*+ (context.item || item) + '_inheritance || '*/ + (context.item || item) + ');'; context.src += '}}else{'; context.src += iter + '.push(' /*+ (context.item || item) + '_inheritance || '*/ + (context.item || item) + ');'; context.src += '}'; } else { context.src += iter + '.push(' /*+ (context.item || item) + '_inheritance || '*/ + (context.item || item) + ');'; } } context.src += '};'; context.src += 'if (Array.isArray(di)) di.forEach(forEachFn);'; context.src += 'else forEachFn(di, 0);'; context.forEach = false; context.item = null; context.src += '};fn(typeof di === "undefined" ? data : di);'; context.meta.pop(); } else if (meta.$type) { if (!context.forEach) { context.src += 'if (typeof di === "undefined"){'; context.src += 'var di = data;'; this._buildSelector(meta, context); context.src += '}'; } var resolvedType = _index.Container.resolveType(meta.$type); var type = _index.Container.resolveName(resolvedType); var typeIndex = _index.Container.getIndex(resolvedType); var isEntityType = resolvedType.isAssignableTo && resolvedType.isAssignableTo(_index2.default.Entity); var item = '_' + type.replace(/\./gi, '_') + '_'; if (context.item == item) item += 'new_'; context.item = item; var isPrimitive = false; if (!meta.$source && !meta.$value && resolvedType !== _index2.default.Array && resolvedType !== _index2.default.Object && !resolvedType.isAssignableTo) isPrimitive = true; if (resolvedType === _index2.default.Object || resolvedType === _index2.default.Array) { var keys = Object.keys(meta); if (keys.length == 1 || keys.length == 2 && meta.$selector) isPrimitive = true; } if (isPrimitive) { var converter = this.context.storageProvider.fieldConverter.fromDb[type]; if (converter) { context.src += 'var ' + item + ' = di != undefined ? self.context.storageProvider.fieldConverter.fromDb["' + type + '"](di) : di;'; } else { context.src += 'var ' + item + ' = di;'; } context.src += 'var ' + item + '_inheritance;'; } else { if (this.references && meta.$keys) { this._buildKey('itemKey', meta.$type, meta.$keys, context); context.src += 'if (itemKey === null) return null;'; context.src += 'var ' + item + ';'; context.src += 'var ' + item + '_inheritance;'; context.src += 'if (itemKey && cache[itemKey]){'; context.src += item + ' = cache[itemKey];'; context.src += '}else{'; if (resolvedType.inheritedTo) { context.src += 'if (di && di["@odata.type"]){'; context.src += 'var odataTypeName = di["@odata.type"].split("#")[1];'; context.src += 'var odataType = Container.resolveType(odataTypeName);'; context.src += 'if (odataType){'; context.src += item + '_inheritance = new odataType(undefined, { setDefaultValues: false });'; //di);'; context.src += '}'; context.src += '}else{'; } if (isEntityType) { context.src += item + ' = new (Container.resolveByIndex(' + typeIndex + '))(undefined, { setDefaultValues: false });'; } else { context.src += item + ' = new (Container.resolveByIndex(' + typeIndex + '))();'; } if (resolvedType.inheritedTo) { context.src += '}'; } context.src += 'if (itemKey){'; context.src += 'cache[itemKey] = ' + item + ' || ' + item + '_inheritance;'; context.src += '}'; context.src += '}'; } else { var isEnum = resolvedType.isAssignableTo && resolvedType.isAssignableTo(_index2.default.Enum); context.src += 'var ' + item + ';'; context.src += 'var ' + item + '_inheritance;'; if (resolvedType.inheritedTo) { context.src += 'if (di["' + context.current + '"] && di["' + context.current + '"]["@odata.type"]){'; context.src += 'var odataType = Container.resolveType(di["' + context.current + '"]["@odata.type"].split("#")[1]);'; context.src += 'if (odataType){'; context.src += item + '_inheritance = new odataType(undefined, { setDefaultValues: false });'; /*di["' + context.current + '"])';*/ context.src += '}'; context.src += '}else{'; } if (isEntityType) { context.src += item + ' = new (Container.resolveByIndex(' + typeIndex + '))(undefined, { setDefaultValues: false });'; } else if (isEnum) { context.src += item + ' = Container.resolveByIndex(' + typeIndex + ')[di["' + context.current + '"]];'; } else { context.src += item + ' = new (Container.resolveByIndex(' + typeIndex + '))();'; } if (resolvedType.inheritedTo) { context.src += '}'; } } } var openTypeProperty = null; if (this.providerName == "oData" && resolvedType && resolvedType.openType) { openTypeProperty = resolvedType.openType === true ? _index2.default.defaults.openTypeDefaultPropertyName : resolvedType.openType; context.src += item + '.' + openTypeProperty + ' = {};'; context.src += 'for (var prop in di){ if ([' + resolvedType.memberDefinitions.getPublicMappedPropertyNames().map(function (prop) { return '"' + prop + '"'; }).join(',') + '].indexOf(prop) < 0 && prop.indexOf("@") < 0 && prop.indexOf("#") < 0){ ' + item + '.' + openTypeProperty + '[prop] = di[prop]; } };'; } context.src += 'var ' + context.item + '_type;'; context.src += 'var ' + context.item + '_memberDefinitionNames;'; context.src += 'if (' + context.item + '_inheritance){'; context.src += context.item + ' = ' + context.item + '_inheritance;'; context.src += 'if (typeof ' + context.item + '.getType == "function"){'; context.src += context.item + '_type = ' + context.item + '.getType();'; context.src += context.item + '_memberDefinitionNames = ' + context.item + '_type' + '.memberDefinitions.getPublicMappedProperties()' + '.filter(function(it){ return it.definedBy == ' + context.item + '_type || it.definedBy == ' + context.item + '_type.inheritsFrom; })' + '.map(function(it){ return it.name; });'; context.src += '}'; context.src += '}'; for (var i in meta) { if (i.indexOf('$') < 0 && i != openTypeProperty) { context.src += 'if (!' + context.item + '_memberDefinitionNames || (' + context.item + '_memberDefinitionNames && ' + context.item + '_memberDefinitionNames.indexOf("' + i + '") >= 0)){'; context.current = i; if (!meta[i].$item) { if (meta[i].$value) { context.meta.push(i); var item = context.item; this.build(meta[i], context); context.src += item + '.' + i + ' = ' + context.item + ';'; context.item = item; context.meta.pop(); } else if (meta[i].$source) { context.src += 'var fn = function(di){'; this._buildSelector(meta[i], context); if (meta[i].$type) { var type = _index.Container.resolveName(_index.Container.resolveType(meta[i].$type)); var typeIndex = _index.Container.getIndex(_index.Container.resolveType(meta[i].$type)); var converter = this.context.storageProvider.fieldConverter.fromDb[type]; if (converter) { context.src += 'return self.context.storageProvider.fieldConverter.fromDb["' + type + '"](di["' + meta[i].$source + '"]);'; } else { context.src += 'return new (Container.resolveByIndex(' + typeIndex + '))(di["' + meta[i].$source + '"]);'; } } else { context.src += item + '.' + i + ' = di["' + meta[i].$source + '"];'; } context.src += '};'; if (meta[i].$type) context.src += item + '.' + i + ' = fn(di);';else context.src += 'fn(di);'; } else if (meta[i].$type) { context.meta.push(i); context.src += 'var fn = function(di){'; this._buildSelector(meta[i], context); this.build(meta[i], context); context.src += 'return ' + context.item + ';};'; if (meta[i].$type === _index2.default.Object) context.src += item + '.' + i + ' = self._deepExtend(' + item + '.' + i + ', fn(di));';else context.src += item + '.' + i + ' = fn(di);'; context.item = item; context.meta.pop(); } else if (meta.$type) { var memDef = _index.Container.resolveType(meta.$type).memberDefinitions.getMember(i); var type = _index.Container.resolveName(memDef.type); var entityType = _index.Container.resolveType(meta.$type); var entityTypeIndex = _index.Container.getIndex(meta.$type); var converter = this.context.storageProvider.fieldConverter.fromDb[type]; if (entityType.inheritedTo) { context.src += 'if (di["' + meta[i] + '"] && di["' + meta[i] + '"]["@odata.type"]){'; context.src += 'var odataType = Container.resolveType(di["' + meta[i] + '"]["@odata.type"].split("#")[1]);'; context.src += 'if (odataType){'; context.src += item + '.' + i + ' = new odataType(undefined, { setDefaultValues: false });'; //di["' + meta[i] + '"])'; context.src += '}'; context.src += '}else{'; } if (this.providerName && memDef && memDef.converter && memDef.converter[this.providerName] && typeof memDef.converter[this.providerName].fromDb == 'function') { context.src += item + '.' + i + ' = Container.resolveByIndex("' + entityTypeIndex + '").memberDefinitions.getMember("' + i + '").converter.' + this.providerName + '.fromDb(di["' + meta[i] + '"], Container.resolveByIndex("' + entityTypeIndex + '").memberDefinitions.getMember("' + i + '"), self.context, Container.resolveByIndex("' + entityTypeIndex + '"));'; } else if (converter) { context.src += item + '.' + i + ' = self.context.storageProvider.fieldConverter.fromDb["' + type + '"](di["' + meta[i] + '"]);'; } else { var typeIndex = _index.Container.getIndex(_index.Container.resolveType(type.memberDefinitions.getMember(i).type)); context.src += item + '.' + i + ' = new (Container.resolveByIndex(' + typeIndex + '))(di["' + meta[i] + '"]);'; } if (entityType.inheritedTo) { context.src += '}'; } } } else { context.meta.push(i); this.build(meta[i], context); context.item = item; context.meta.pop(); } context.src += '}'; } } context.src += item + ' = self._finalize(' + /*item + '_inheritance' + ' || ' +*/item + ');'; } }, call: function call(data, meta) { if (!Object.getOwnPropertyNames(meta).length) { return data; } var context = { src: '', meta: [] }; context.src += 'var self = this;'; context.src += 'var result;'; context.src += 'var cache = {};'; context.src += 'var keycache = [];'; context.src += 'var keycacheIter = [];'; this.build(meta, context); if (context.item) context.src += 'if (typeof result === "undefined") result = ' + context.item + ';'; context.src += 'return result;'; var fn = new Function('meta', 'data', 'Container', context.src).bind(this); var ret = fn(meta, data, _index.Container); return ret; } }); exports.default = _index2.default; module.exports = exports['default'];