UNPKG

@pebula/metap

Version:
1,289 lines (1,251 loc) 58 kB
(function (global, factory) { typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('@pebula/metap/internal'), require('@pebula/utils')) : typeof define === 'function' && define.amd ? define('@pebula/metap', ['exports', '@pebula/metap/internal', '@pebula/utils'], factory) : (global = global || self, factory((global.pebula = global.pebula || {}, global.pebula.metap = {}), global.pebula.metap.internal, global.pebula.utils)); }(this, function (exports, internal, utils) { 'use strict'; /*! ***************************************************************************** Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 THIS CODE IS PROVIDED ON AN *AS IS* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION ANY IMPLIED WARRANTIES OR CONDITIONS OF TITLE, FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABLITY OR NON-INFRINGEMENT. See the Apache Version 2.0 License for specific language governing permissions and limitations under the License. ***************************************************************************** */ /* global Reflect, Promise */ var extendStatics = function(d, b) { extendStatics = Object.setPrototypeOf || ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) || function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; }; return extendStatics(d, b); }; function __extends(d, b) { extendStatics(d, b); function __() { this.constructor = d; } d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __()); } var __assign = function() { __assign = Object.assign || function __assign(t) { for (var s, i = 1, n = arguments.length; i < n; i++) { s = arguments[i]; for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p]; } return t; }; return __assign.apply(this, arguments); }; function __rest(s, e) { var t = {}; for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0) t[p] = s[p]; if (s != null && typeof Object.getOwnPropertySymbols === "function") for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) { if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i])) t[p[i]] = s[p[i]]; } return t; } function __decorate(decorators, target, key, desc) { var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d; if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc); else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r; return c > 3 && r && Object.defineProperty(target, key, r), r; } function __param(paramIndex, decorator) { return function (target, key) { decorator(target, key, paramIndex); } } function __metadata(metadataKey, metadataValue) { if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(metadataKey, metadataValue); } function __awaiter(thisArg, _arguments, P, generator) { return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); } function __generator(thisArg, body) { var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g; return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g; function verb(n) { return function (v) { return step([n, v]); }; } function step(op) { if (f) throw new TypeError("Generator is already executing."); while (_) try { if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t; if (y = 0, t) op = [op[0] & 2, t.value]; switch (op[0]) { case 0: case 1: t = op; break; case 4: _.label++; return { value: op[1], done: false }; case 5: _.label++; y = op[1]; op = [0]; continue; case 7: op = _.ops.pop(); _.trys.pop(); continue; default: if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; } if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; } if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; } if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; } if (t[2]) _.ops.pop(); _.trys.pop(); continue; } op = body.call(thisArg, _); } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; } if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true }; } } function __exportStar(m, exports) { for (var p in m) if (!exports.hasOwnProperty(p)) exports[p] = m[p]; } function __values(o) { var m = typeof Symbol === "function" && o[Symbol.iterator], i = 0; if (m) return m.call(o); return { next: function () { if (o && i >= o.length) o = void 0; return { value: o && o[i++], done: !o }; } }; } function __read(o, n) { var m = typeof Symbol === "function" && o[Symbol.iterator]; if (!m) return o; var i = m.call(o), r, ar = [], e; try { while ((n === void 0 || n-- > 0) && !(r = i.next()).done) ar.push(r.value); } catch (error) { e = { error: error }; } finally { try { if (r && !r.done && (m = i["return"])) m.call(i); } finally { if (e) throw e.error; } } return ar; } function __spread() { for (var ar = [], i = 0; i < arguments.length; i++) ar = ar.concat(__read(arguments[i])); return ar; } function __spreadArrays() { for (var s = 0, i = 0, il = arguments.length; i < il; i++) s += arguments[i].length; for (var r = Array(s), k = 0, i = 0; i < il; i++) for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++) r[k] = a[j]; return r; }; function __await(v) { return this instanceof __await ? (this.v = v, this) : new __await(v); } function __asyncGenerator(thisArg, _arguments, generator) { if (!Symbol.asyncIterator) throw new TypeError("Symbol.asyncIterator is not defined."); var g = generator.apply(thisArg, _arguments || []), i, q = []; return i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i; function verb(n) { if (g[n]) i[n] = function (v) { return new Promise(function (a, b) { q.push([n, v, a, b]) > 1 || resume(n, v); }); }; } function resume(n, v) { try { step(g[n](v)); } catch (e) { settle(q[0][3], e); } } function step(r) { r.value instanceof __await ? Promise.resolve(r.value.v).then(fulfill, reject) : settle(q[0][2], r); } function fulfill(value) { resume("next", value); } function reject(value) { resume("throw", value); } function settle(f, v) { if (f(v), q.shift(), q.length) resume(q[0][0], q[0][1]); } } function __asyncDelegator(o) { var i, p; return i = {}, verb("next"), verb("throw", function (e) { throw e; }), verb("return"), i[Symbol.iterator] = function () { return this; }, i; function verb(n, f) { i[n] = o[n] ? function (v) { return (p = !p) ? { value: __await(o[n](v)), done: n === "return" } : f ? f(v) : v; } : f; } } function __asyncValues(o) { if (!Symbol.asyncIterator) throw new TypeError("Symbol.asyncIterator is not defined."); var m = o[Symbol.asyncIterator], i; return m ? m.call(o) : (o = typeof __values === "function" ? __values(o) : o[Symbol.iterator](), i = {}, verb("next"), verb("throw"), verb("return"), i[Symbol.asyncIterator] = function () { return this; }, i); function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; } function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); } } function __makeTemplateObject(cooked, raw) { if (Object.defineProperty) { Object.defineProperty(cooked, "raw", { value: raw }); } else { cooked.raw = raw; } return cooked; }; function __importStar(mod) { if (mod && mod.__esModule) return mod; var result = {}; if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; result.default = mod; return result; } function __importDefault(mod) { return (mod && mod.__esModule) ? mod : { default: mod }; } /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ /* We need to do some funky stuff for angular compiler... If we wont, the output d.ts files will be messed up For example: export const Prop = MetaClass.decorator(PropMetadata, true); WILL BECOME IN "d.ts" export declare const Prop: (def?: import("../../../../../dist/@pebula/metap/internal/pebula-metap-internal").PropMetadataArgs) => (target: any, propertyKey?: string | number | symbol, descOrIndex?: number | PropertyDescriptor) => any; This will happen because ngc doesn't know how properly get the symbol declaration so it fallbacks to the import style.... */ /** * \@propertyDecorator instance * \@param def * @type {?} */ var Prop = internal.MetaClass.decorator(internal.PropMetadata, true); /** * \@propertyDecorator instance * \@param def * @type {?} */ var Exclude = internal.MetaClass.decorator(internal.ExcludeMetadata, true); /** * \@propertyDecorator instance * \@param def * @type {?} */ var Relation = internal.MetaClass.decorator(internal.RelationMetadata, true); /** * \@propertyDecorator instance * \@param def * @type {?} */ var Type = internal.MetaClass.decorator(internal.TypeMetadata); /** * \@propertyDecorator instance * @return {?} */ function Identity() { return (/** * @param {?} target * @param {?} key * @return {?} */ function (target, key) { internal.targetStore.getTargetMeta((/** @type {?} */ (target.constructor))).model().identity = key; }); } /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ /** * \@propertyDecorator static * @param {?=} metaArgs * @return {?} */ function Model(metaArgs) { return (/** * @param {?} target * @return {?} */ function (target) { /** @type {?} */ var metaClass = internal.MetaClass.create(internal.ModelMetadata, metaArgs, target); processModel(target, metaClass, metaClass.skip !== true); }); } /** * Takes a model and process it. * The first step is to extend the target, if it inherits. * The second step is calling the build() method on the metadata class which will * start the event life-cycle. * @param {?} target * @param {?} metaClass * @param {?=} build * @return {?} */ function processModel(target, metaClass, build) { var e_1, _a; try { for (var _b = __values(utils.getProtoChain(target)), _c = _b.next(); !_c.done; _c = _b.next()) { var proto = _c.value; if (target !== proto && internal.targetStore.hasTarget(proto)) { internal.targetStore.extend(proto, target); } } } catch (e_1_1) { e_1 = { error: e_1_1 }; } finally { try { if (_c && !_c.done && (_a = _b.return)) _a.call(_b); } finally { if (e_1) throw e_1.error; } } if (build) { metaClass.build(); } } /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ /** * @record */ function CompiledTransformation() { } if (false) { /** * Excluded members that doesn't have a \@Prop decorator. * All \@Exclude instructions on members with \@Prop instructions are add to the PoClassPropertyMap * @type {?} */ CompiledTransformation.prototype.excluded; /** @type {?} */ CompiledTransformation.prototype.instructions; } /** * @param {?} value * @param {?} prop * @return {?} */ function transformValueOut(value, prop) { if (prop && prop.transform && prop.transform.outgoing) { return prop.transform.outgoing(value); } return value; } /** * @param {?} value * @param {?} prop * @return {?} */ function transformValueIn(value, prop) { if (prop && prop.transform && prop.transform.incoming) { return prop.transform.incoming(value); } return value; } /** * @param {?} e * @return {?} */ function excludedPredicate(e) { return e.name === this; } var InclusivePropertyContainer = /** @class */ (function () { function InclusivePropertyContainer(target, compiled, predicate, renamer) { this.target = target; this.compiled = compiled; this.predicate = predicate; this.renamer = renamer; } /** * @param {?} keys * @param {?} cb * @return {?} */ InclusivePropertyContainer.prototype.forEach = /** * @param {?} keys * @param {?} cb * @return {?} */ function (keys, cb) { /** @type {?} */ var len = keys.length; /** @type {?} */ var instructions = this.compiled.instructions.slice(); /** @type {?} */ var excluded = this.compiled.excluded.slice(); for (var i = 0; i < len; i++) { /** @type {?} */ var prop = internal.array.findRemove(instructions, this.predicate, keys[i]) || { cls: keys[i], obj: keys[i], exclude: internal.array.findRemove(excluded, excludedPredicate, keys[i]) }; if (!prop.exclude) { // we only transform names for ad-hoc properties. registered @Prop's are transformed // when the prop is compiled. if (!prop.prop && this.renamer) { this.renamer(prop); } cb(prop); } } }; /** * A forEach loop on all instructions including excluded instructions and properties not in "keys" but in metadata. * It is recommended to use "forEach" unless the mapper implementation has different transformation strategies. * @param keys * @param cb */ /** * A forEach loop on all instructions including excluded instructions and properties not in "keys" but in metadata. * It is recommended to use "forEach" unless the mapper implementation has different transformation strategies. * @param {?} keys * @param {?} cb * @return {?} */ InclusivePropertyContainer.prototype.forEachRaw = /** * A forEach loop on all instructions including excluded instructions and properties not in "keys" but in metadata. * It is recommended to use "forEach" unless the mapper implementation has different transformation strategies. * @param {?} keys * @param {?} cb * @return {?} */ function (keys, cb) { /** @type {?} */ var len = keys.length; /** @type {?} */ var instructions = this.compiled.instructions.slice(); /** @type {?} */ var excluded = this.compiled.excluded.slice(); for (var i = 0; i < len; i++) { /** @type {?} */ var prop = internal.array.findRemove(instructions, this.predicate, keys[i]) || { cls: keys[i], obj: keys[i], exclude: internal.array.findRemove(excluded, excludedPredicate, keys[i]) }; // we only transform names for ad-hoc properties. registered @Prop's are transformed // when the prop is compiled. if (!prop.prop && this.renamer) { this.renamer(prop); } cb(prop); } len = instructions.length; for (var i = 0; i < len; i++) { /** @type {?} */ var prop = instructions[i]; // we only transform names for ad-hoc properties. registered @Prop's are transformed // when the prop is compiled. if (!prop.prop && this.renamer) { this.renamer(prop); } cb(prop); } }; return InclusivePropertyContainer; }()); if (false) { /** @type {?} */ InclusivePropertyContainer.prototype.target; /** * @type {?} * @private */ InclusivePropertyContainer.prototype.compiled; /** * @type {?} * @private */ InclusivePropertyContainer.prototype.predicate; /** * @type {?} * @private */ InclusivePropertyContainer.prototype.renamer; } var ExclusivePropertyContainer = /** @class */ (function () { function ExclusivePropertyContainer(target, compiled) { this.target = target; this.compiled = compiled; } /** * @param {?} keys * @param {?} cb * @return {?} */ ExclusivePropertyContainer.prototype.forEach = /** * @param {?} keys * @param {?} cb * @return {?} */ function (keys, cb) { /** @type {?} */ var instructions = this.compiled.instructions; // No need to apply transformNameStrategy, it is cached in the instructions. for (var i = 0, len = instructions.length; i < len; i++) { !instructions[i].exclude && cb(instructions[i]); } }; /** * A forEach loop on all instructions including excluded instructions and properties not in "keys" but in metadata. * It is recommended to use "forEach" unless the mapper implementation has different transformation strategies. * @param keys * @param cb */ /** * A forEach loop on all instructions including excluded instructions and properties not in "keys" but in metadata. * It is recommended to use "forEach" unless the mapper implementation has different transformation strategies. * @param {?} keys * @param {?} cb * @return {?} */ ExclusivePropertyContainer.prototype.forEachRaw = /** * A forEach loop on all instructions including excluded instructions and properties not in "keys" but in metadata. * It is recommended to use "forEach" unless the mapper implementation has different transformation strategies. * @param {?} keys * @param {?} cb * @return {?} */ function (keys, cb) { /** @type {?} */ var instructions = this.compiled.instructions; for (var i = 0, len = instructions.length; i < len; i++) { cb(instructions[i]); } }; return ExclusivePropertyContainer; }()); if (false) { /** @type {?} */ ExclusivePropertyContainer.prototype.target; /** * @type {?} * @private */ ExclusivePropertyContainer.prototype.compiled; } /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ var TransformationError = /** @class */ (function (_super) { __extends(TransformationError, _super); function TransformationError(message) { return _super.call(this, message) || this; } /** * @param {?} expectedCol * @return {?} */ TransformationError.coll_obj = /** * @param {?} expectedCol * @return {?} */ function (expectedCol) { return new TransformationError(expectedCol ? "Expected a collection but got an object" : "Expected an object but got a collection"); }; return TransformationError; }(Error)); /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ /** * Returns an array of 2 property names, first is the name of the transformed output * second is the name of the property name to transform. * Used for applying NamingStrategyConfig based on the TransformDir * @param {?} dir * @param {?} transformNameStrategy * @return {?} */ function namingStrategyMap(dir, transformNameStrategy) { return transformNameStrategy && utils.isFunction(transformNameStrategy[dir]); } /** * \@internal * @template T, Z * @param {?} meta * @param {?} dir * @return {?} */ function getInstructions(meta, dir) { // all excluded instructions for this type // this array will be filtered to hold only @Exclude without @Prop /** @type {?} */ var excluded = meta .getValues(internal.ExcludeMetadata) .filter((/** * @param {?} e * @return {?} */ function (e) { return !e.from || e.from === dir; })); /** @type {?} */ var model = meta.model(); // in exclusive mode there is no point in have 2 transformation strategies. // incoming is never there since incoming keys are not calculated, only defined Props. if (model.transformStrategy === 'exclusive') { dir = 'outgoing'; } // only apply naming strategy on outgoing, incoming has no effect here /** @type {?} */ var naming = namingStrategyMap(dir, model.transformNameStrategy); /** @type {?} */ var fkMap = new Map(); // TODO: move to for loop /** @type {?} */ var instructions = meta.getValues(internal.PropMetadata).map((/** * @param {?} prop * @return {?} */ function (prop) { /** @type {?} */ var obj = { cls: prop.name, obj: prop.alias[dir], exclude: internal.array.findRemove(excluded, (/** * @param {?} e * @return {?} */ function (e) { return e.name === prop.name; })), prop: prop }; // apply naming strategy when DONT HAVE ALIAS! if (!obj.exclude && naming && obj.cls === obj.obj) { obj.obj = model.transformNameStrategy[dir](obj.cls); } // store the PoClassPropertyMap of a belongsTo PropMetadata relation // and the PoClassPropertyMap of all foreign key PropMetadata. // These arr actually matching pairs of a belongTo relation and it's fk // (not all belongsTo has fk, only different property name is a fk) // // At the end, go through the stored PropMetadata and see if matching pairs found (2 values in array) // for all of them, swap the prop names so: // belongsTo PoClassPropertyMap will output (deserialize) to the original fk property name // foreignKey PoClassPropertyMap wil input (serialize) to the belongsTo property name // this swap make the deserialize/serialize process transparent to fk mismatch defined on the model. // De/Serialize implementations are only responsible to return the right object // (e.g. detect when a key is incoming, return obj instead) if (prop.relation) { /** @type {?} */ var arr = fkMap.get(prop) || []; arr[0] = obj; fkMap.set(prop, arr); } else if (prop.foreignKeyOf) { /** @type {?} */ var arr = fkMap.get(prop.foreignKeyOf) || []; arr[1] = obj; fkMap.set(prop.foreignKeyOf, arr); } return obj; })); Array.from(fkMap.entries()).forEach((/** * @param {?} __0 * @return {?} */ function (_a) { var _b = __read(_a, 2), k = _b[0], v = _b[1]; if (v.length === 2) { // this is a swap v[0].obj = (/** @type {?} */ (v[1].cls)); v[1].cls = (/** @type {?} */ (k.name)); // v[0].cls === k.name } })); return { excluded: excluded, instructions: instructions }; } /** * @param {?} p * @return {?} */ function serializePredicate(p) { return p.cls === this; } /** * @param {?} p * @return {?} */ function deserializePredicate(p) { return p.obj === this; } var ɵ0 = /** * @this {?} * @return {?} */ function () { /** @type {?} */ var idKey = this.meta.getIdentityKey(); if (idKey) { return (this.hasOwnProperty('incoming') ? this.incoming : this.outgoing).instructions.find((/** * @param {?} p * @return {?} */ function (p) { return p.prop.name === idKey; })); } }, ɵ1 = /** * @this {?} * @return {?} */ function () { return getInstructions(this.meta, 'incoming'); }, ɵ2 = /** * @this {?} * @return {?} */ function () { return getInstructions(this.meta, 'outgoing'); }, ɵ3 = /** * @this {?} * @return {?} */ function () { /** @type {?} */ var model = this.meta.model(); if (model.transformStrategy === 'exclusive') { return new ExclusivePropertyContainer(this.meta.target, this.incoming); } else { /** @type {?} */ var rename = namingStrategyMap('incoming', model.transformNameStrategy) ? (/** * @param {?} prop * @return {?} */ function (prop) { return (prop.cls = model.transformNameStrategy.incoming(prop.obj)); }) : undefined; return new InclusivePropertyContainer(this.meta.target, this.incoming, deserializePredicate, rename); } }, ɵ4 = /** * @this {?} * @return {?} */ function () { /** @type {?} */ var model = this.meta.model(); if (model.transformStrategy === 'exclusive') { return new ExclusivePropertyContainer(this.meta.target, this.outgoing); } else { /** @type {?} */ var rename = namingStrategyMap('outgoing', model.transformNameStrategy) ? (/** * @param {?} prop * @return {?} */ function (prop) { return (prop.obj = model.transformNameStrategy.outgoing(prop.cls)); }) : undefined; return new InclusivePropertyContainer(this.meta.target, this.outgoing, serializePredicate, rename); } }; // @dynamic /** * A TargetSerializationContext is the running context of a mapper for a specific target class that * can serialize and deserialize instances of the target class. * It will run the mapper, provide input and parse results * @template T, Z */ var TargetSerializationContext = /** @class */ (function () { function TargetSerializationContext(meta) { this.meta = meta; } /** * @param {?} mapper * @return {?} */ TargetSerializationContext.prototype.serialize = /** * @param {?} mapper * @return {?} */ function (mapper) { return mapper.serialize(this.outgoingContainer); }; /** * Deserialize a single target. * Does not support collection deserialization, if mapper is a collection will throw. * @param mapper * @param target */ /** * Deserialize a single target. * Does not support collection deserialization, if mapper is a collection will throw. * @param {?} mapper * @param {?} target * @return {?} */ TargetSerializationContext.prototype.deserialize = /** * Deserialize a single target. * Does not support collection deserialization, if mapper is a collection will throw. * @param {?} mapper * @param {?} target * @return {?} */ function (mapper, target) { /** @type {?} */ var cb = (/** * @param {?} prop * @return {?} */ function (prop) { /** @type {?} */ var propMeta = (prop.prop && prop.prop.foreignKeyOf) || prop.prop; target[prop.cls] = transformValueIn(mapper.getValue(prop.obj, propMeta), propMeta); }); if (utils.isFunction(mapper.setRef)) { mapper.setRef(target); } if (mapper.raw === true) { this.incomingContainer.forEachRaw(mapper.getKeys(), cb); } else { this.incomingContainer.forEach(mapper.getKeys(), cb); } if (utils.isFunction(mapper.getIdentity)) { if (this.identity) { /** @type {?} */ var ident = transformValueIn(mapper.getIdentity(), this.identity.prop); if (ident) { target[this.identity.cls] = ident; } } } }; __decorate([ internal.LazyInit((ɵ0)), __metadata("design:type", Object) ], TargetSerializationContext.prototype, "identity", void 0); __decorate([ internal.LazyInit((ɵ1)), __metadata("design:type", Object) ], TargetSerializationContext.prototype, "incoming", void 0); __decorate([ internal.LazyInit((ɵ2)), __metadata("design:type", Object) ], TargetSerializationContext.prototype, "outgoing", void 0); __decorate([ internal.LazyInit((ɵ3)), __metadata("design:type", Object) ], TargetSerializationContext.prototype, "incomingContainer", void 0); __decorate([ internal.LazyInit((ɵ4)), __metadata("design:type", Object) ], TargetSerializationContext.prototype, "outgoingContainer", void 0); return TargetSerializationContext; }()); if (false) { /** * @type {?} * @protected */ TargetSerializationContext.prototype.identity; /** * @type {?} * @protected */ TargetSerializationContext.prototype.incoming; /** * @type {?} * @protected */ TargetSerializationContext.prototype.outgoing; /** * @type {?} * @protected */ TargetSerializationContext.prototype.incomingContainer; /** * @type {?} * @protected */ TargetSerializationContext.prototype.outgoingContainer; /** * @type {?} * @protected */ TargetSerializationContext.prototype.meta; } /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ /** @type {?} */ var targetSerializationContextStore = new Map(); /** * @param {?} targetMeta * @return {?} */ function getTargetSerializationContext(targetMeta) { /** @type {?} */ var ctx = targetSerializationContextStore.get(targetMeta); if (!ctx) { ctx = new TargetSerializationContext(targetMeta); targetSerializationContextStore.set(targetMeta, ctx); } return ctx; } /** * @template TMeta * @param {?} targetMeta * @param {?} mapper * @return {?} */ function serializeTargetMeta(targetMeta, mapper) { return getTargetSerializationContext(targetMeta).serialize(mapper); } /** * @template TMeta * @param {?} targetMeta * @param {?} mapper * @param {?} target * @param {?=} plain * @return {?} */ function deserializeTargetMeta(targetMeta, mapper, target, plain) { if (plain === void 0) { plain = false; } if (mapper.isCollection) { if (!Array.isArray(target)) { throw TransformationError.coll_obj(true); } /** @type {?} */ var refItems = target.splice(0, target.length); /** @type {?} */ var identKey_1 = internal.targetStore.getIdentityKey(targetMeta.target, 'incoming'); var _loop_1 = function () { /** @type {?} */ var t = void 0; // compare current item to map with a list of items that if we, if we got. // if match use that instance. // TODO: Move compare to the global store, so logic can change without bugs. if (refItems.length > 0 && utils.isFunction(mapper.getIdentity)) { /** @type {?} */ var incomingIdent_1 = mapper.getIdentity(); t = internal.array.findRemove(refItems, (/** * @param {?} item * @return {?} */ function (item) { return item[identKey_1] === incomingIdent_1; })); } if (!t) { t = plain ? {} : targetMeta.model().factory(false); } getTargetSerializationContext(targetMeta).deserialize(mapper, t); target.push(t); }; while (mapper.next()) { _loop_1(); } } else { if (Array.isArray(target)) { throw TransformationError.coll_obj(false); } getTargetSerializationContext(targetMeta).deserialize(mapper, target); } } /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ var PlainObject = /** @class */ (function () { function PlainObject() { } PlainObject = __decorate([ Model({ resName: 'InternalPlainObject' }) ], PlainObject); return PlainObject; }()); /** * @param {?} mapper * @param {?} instanceOrTarget * @param {?=} target * @return {?} */ function serialize(mapper, instanceOrTarget, target) { if (mapper instanceof internal.BaseSerializer) { /** @type {?} */ var meta = internal.targetStore.getTargetMeta(instanceOrTarget); if (meta) { return serializeTargetMeta(meta, mapper); } } else { /** @type {?} */ var meta = internal.targetStore.getTargetMeta(target || instanceOrTarget.constructor); if (meta) { return serializeTargetMeta(meta, mapper.serializer(instanceOrTarget)); } } } /** * Automatically serialize an instance. * This method will serialize an instance by first trying to locate the target using the `constructor` function. * If a target is found and if it's a model target (i.e. ModelMetadata) it will try to get the mapper assign for that * model. * * If no target, model or mapper was found it will use the fallbackMapper mapper provided, or `directMapper` * if no fallback is provided provided. * * Note that when provided a fallback mapper, make sure it is able to serialize unknown targets. (plain objects) * @param {?} instance * @param {?=} fallbackMapper * @return {?} */ function autoSerialize(instance, fallbackMapper) { /** @type {?} */ var tMeta = internal.targetStore.getTargetMeta((/** @type {?} */ (instance.constructor))); /** @type {?} */ var mapper = (tMeta && tMeta.hasModel && tMeta.model().mapper) || fallbackMapper || directMapper; return serialize(mapper, instance); } /** * @param {?} mapper * @param {?=} plainObject * @param {?=} type * @param {?=} instance * @return {?} */ function deserialize(mapper, plainObject, type, instance) { /** @type {?} */ var deserializer; if (mapper instanceof internal.BaseDeserializer) { instance = plainObject; deserializer = mapper; } else { deserializer = mapper.deserializer(plainObject, type); } if (internal.targetStore.hasTarget(deserializer.sourceType)) { /** @type {?} */ var meta = internal.targetStore.getTargetMeta(deserializer.sourceType); /** @type {?} */ var result = instance || meta.model().factory(deserializer.isCollection); deserializeTargetMeta(meta, deserializer, result); return result; } else { /** @type {?} */ var meta = internal.targetStore.getTargetMeta(PlainObject); /** @type {?} */ var result = instance || deserializer.isCollection ? [] : {}; deserializeTargetMeta(meta, deserializer, result, true); return result; } } /** * Automatically de-serialize an object to/into an instance. * This method will de-serialize an object by first trying to locate a model (i.e. ModelMetadata) for the target. * If a model is found it will try to get the mapper assign for that model. * * If no model or mapper was found it will use the fallbackMapper mapper provided, or `directMapper` * if no fallback is provided provided. * * @template T, Z * @param {?} plainObject * @param {?} type * @param {?=} instance * @param {?=} fallbackMapper * @return {?} */ function autoDeserialize(plainObject, type, instance, fallbackMapper) { if (instance === void 0) { instance = null; } /** @type {?} */ var tMeta = internal.targetStore.getTargetMeta(type); /** @type {?} */ var mapper = (tMeta && tMeta.hasModel && tMeta.model().mapper) || fallbackMapper || directMapper; return deserialize(mapper, plainObject, type, instance); } /** * Performs a deep clone to the resource using serialization and deserialization, which means that all rules apply (i.e \@Exclude) * * @template T * @param {?} resource the resource (instance) to clone * @param {?=} serializationFactory Optional, The [[SerializationFactory]] to use, defaults to [[directMapper]]. * @return {?} */ function clone(resource, serializationFactory) { return autoDeserialize(autoSerialize(resource, serializationFactory), (/** @type {?} */ (resource.constructor)), null, serializationFactory); } /** * @fileoverview added by tsickle * @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ /** * A mapper that has no mapping effect. * Maps every property on the source to the same property on the target. * This mapper does not support non primitive id's * @template T, Z */ var /** * A mapper that has no mapping effect. * Maps every property on the source to the same property on the target. * This mapper does not support non primitive id's * @template T, Z */ DirectDeserializeMapper = /** @class */ (function (_super) { __extends(DirectDeserializeMapper, _super); function DirectDeserializeMapper(source, sourceType, plainMapper) { var _this = _super.call(this, source, sourceType, plainMapper) || this; _this.idx = -1; if (!(_this instanceof DirectChildDeserializeMapper)) { _this.existing = new internal.DualKeyMap(); } _this.identity = internal.targetStore.getIdentityKey(_this.sourceType, 'outgoing'); _this.isCollection = Array.isArray(source); if (!_this.isCollection) { _this.current = _this.source; } return _this; } /** * @param {?} value * @return {?} */ DirectDeserializeMapper.prototype.setRef = /** * @param {?} value * @return {?} */ function (value) { if (this.current) { this.existing.set(this.sourceType, this.getIdentity(), value); } }; Object.defineProperty(DirectDeserializeMapper.prototype, "ref", { get: /** * @protected * @return {?} */ function () { if (this.current) { return this.existing.get(this.sourceType, this.getIdentity()); } }, enumerable: true, configurable: true }); /** * @return {?} */ DirectDeserializeMapper.prototype.getIdentity = /** * @return {?} */ function () { // TODO: Move to the global store, so logic can change without bugs. return this.current[this.identity]; }; /** * @return {?} */ DirectDeserializeMapper.prototype.next = /** * @return {?} */ function () { if (this.isCollection) { this.current = this.source[++this.idx]; return !!this.current; } else { return false; } }; /** * @return {?} */ DirectDeserializeMapper.prototype.getKeys = /** * @return {?} */ function () { return Object.keys(this.current); }; /** * @param {?} key * @param {?=} prop * @return {?} */ DirectDeserializeMapper.prototype.getValue = /** * @param {?} key * @param {?=} prop * @return {?} */ function (key, prop) { /** @type {?} */ var value = this.current[key]; if (prop) { // The adapter has the responsibility to manage relationships. // It doesn't care about key matching (e.g. key in property customer_id but property is customer) // it get's a value and the property to assign to, the adapter should check if the value it got // was an id or an object. // this relationship handling logic makes this whole adapter support only primitive ID properties. // if we have primitives we treat them as id's and create an object. // later we wil check if this value is in cache, if not create it. // if its not a primitive, it will process as a full object included in the payload. /** @type {?} */ var rel = this.getRelationQuery(prop, value); if (rel) { value = rel; } if (internal.targetStore.hasTarget(prop.type.ref)) { return (this.getCache(prop.type.ref, value) || this.deserialize(value, prop)); } } return typeof value === 'object' ? this.plainMapper.deserialize(value) : value; }; /** * @protected * @param {?} value * @param {?} prop * @return {?} */ DirectDeserializeMapper.prototype.deserialize = /** * @protected * @param {?} value * @param {?} prop * @return {?} */ function (value, prop) { /** @type {?} */ var deserializer = this.ref ? new DirectChildDeserializeMapper(value, prop.type.ref, this.existing, this.plainMapper) : directMapper.deserializer(value, prop.type.ref, this.plainMapper); return deserialize(deserializer); }; /** * Returns a relationship object with the identity property set. * This object can then be used by the cache to identify if a value is cached or not (using the type & identity comb) */ /** * Returns a relationship object with the identity property set. * This object can then be used by the cache to identify if a value is cached or not (using the type & identity comb) * @protected * @param {?} prop * @param {?} value * @return {?} */ DirectDeserializeMapper.prototype.getRelationQuery = /** * Returns a relationship object with the identity property set. * This object can then be used by the cache to identify if a value is cached or not (using the type & identity comb) * @protected * @param {?} prop * @param {?} value * @return {?} */ function (prop, value) { var _a; if (prop.relation && utils.isPrimitive(value)) { return _a = {}, _a[internal.targetStore.getIdentityKey((/** @type {?} */ (prop.type.ref)), 'outgoing')] = value, _a; } }; /** * @protected * @param {?} type * @param {?} value * @return {?} */ DirectDeserializeMapper.prototype.getCache = /** * @protected * @param {?} type * @param {?} value * @return {?} */ function (type, value) { /** @type {?} */ var idKey = internal.targetStore.getIdentityKey(type, 'outgoing'); /** @type {?} */ var idVal = idKey && value[idKey]; if (idVal) { return this.existing.get(type, idVal); } }; return DirectDeserializeMapper; }(internal.BaseDeserializer)); if (false) {