pax_global_header00006660000000000000000000000064141376055260014523gustar00rootroot0000000000000052 comment=37826bdf3689e74a317cd0dd0827e236c9ccd1dc copy-props-3.0.1/000077500000000000000000000000001413760552600136375ustar00rootroot00000000000000copy-props-3.0.1/.editorconfig000066400000000000000000000003261413760552600163150ustar00rootroot00000000000000# http://editorconfig.org root = true [*] indent_style = space indent_size = 2 charset = utf-8 trim_trailing_whitespace = true insert_final_newline = true end_of_line = lf [*.md] trim_trailing_whitespace = false copy-props-3.0.1/.eslintignore000066400000000000000000000001471413760552600163440ustar00rootroot00000000000000# Coverage directory used by tools like istanbul coverage # Browerify output directories web test/web copy-props-3.0.1/.eslintrc000066400000000000000000000001021413760552600154540ustar00rootroot00000000000000{ "extends": "gulp", "rules": { "max-statements": 0 } } copy-props-3.0.1/.gitattributes000066400000000000000000000000161413760552600165270ustar00rootroot00000000000000* text eol=lf copy-props-3.0.1/.github/000077500000000000000000000000001413760552600151775ustar00rootroot00000000000000copy-props-3.0.1/.github/workflows/000077500000000000000000000000001413760552600172345ustar00rootroot00000000000000copy-props-3.0.1/.github/workflows/dev.yml000066400000000000000000000031071413760552600205360ustar00rootroot00000000000000name: dev on: pull_request: push: branches: - master - main env: CI: true jobs: prettier: name: Format code runs-on: ubuntu-latest if: ${{ github.event_name == 'push' }} steps: - name: Checkout uses: actions/checkout@v2 - name: Prettier uses: gulpjs/prettier_action@v3.0 with: commit_message: 'chore: Run prettier' prettier_options: '--write .' test: name: Tests for Node ${{ matrix.node }} on ${{ matrix.os }} runs-on: ${{ matrix.os }} strategy: fail-fast: false matrix: node: [10, 12, 14, 16] os: [ubuntu-latest, windows-latest, macos-latest] steps: - name: Clone repository uses: actions/checkout@v2 - name: Set Node.js version uses: actions/setup-node@v2 with: node-version: ${{ matrix.node }} - run: node --version - run: npm --version - name: Install npm dependencies run: npm install - name: Run lint run: npm run lint - name: Run tests run: npm test - name: Coveralls uses: coverallsapp/github-action@v1.1.2 with: github-token: ${{ secrets.GITHUB_TOKEN }} flag-name: ${{ matrix.os }}-node-${{ matrix.node }} parallel: true coveralls: needs: test name: Finish up runs-on: ubuntu-latest steps: - name: Coveralls Finished uses: coverallsapp/github-action@v1.1.2 with: github-token: ${{ secrets.GITHUB_TOKEN }} parallel-finished: true copy-props-3.0.1/.github/workflows/release.yml000066400000000000000000000005511413760552600214000ustar00rootroot00000000000000name: release on: push: branches: - master - main jobs: release-please: runs-on: ubuntu-latest steps: - uses: GoogleCloudPlatform/release-please-action@v2 with: token: ${{ secrets.GITHUB_TOKEN }} release-type: node package-name: release-please-action bump-minor-pre-major: true copy-props-3.0.1/.gitignore000066400000000000000000000017101413760552600156260ustar00rootroot00000000000000# Logs logs *.log npm-debug.log* yarn-debug.log* yarn-error.log* # Runtime data pids *.pid *.seed *.pid.lock # Directory for instrumented libs generated by jscoverage/JSCover lib-cov # Coverage directory used by tools like istanbul coverage # nyc test coverage .nyc_output # Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files) .grunt # Bower dependency directory (https://bower.io/) bower_components # node-waf configuration .lock-wscript # Compiled binary addons (https://nodejs.org/api/addons.html) build/Release # Dependency directories node_modules/ jspm_packages/ # TypeScript v1 declaration files typings/ # Optional npm cache directory .npm # Optional eslint cache .eslintcache # Optional REPL history .node_repl_history # Output of 'npm pack' *.tgz # Yarn Integrity file .yarn-integrity # dotenv environment variables file .env # next.js build output .next # Garbage files .DS_Store # Test results test.xunit copy-props-3.0.1/.npmrc000066400000000000000000000000231413760552600147520ustar00rootroot00000000000000package-lock=false copy-props-3.0.1/.prettierignore000066400000000000000000000000511413760552600166760ustar00rootroot00000000000000coverage/ .nyc_output/ CHANGELOG.md web/ copy-props-3.0.1/CHANGELOG.md000066400000000000000000000014671413760552600154600ustar00rootroot00000000000000# Changelog ### [3.0.1](https://www.github.com/gulpjs/copy-props/compare/v3.0.0...v3.0.1) (2021-10-31) ### Bug Fixes * **ci:** Rename prettierignore typo & avoid formatting web ([192badf](https://www.github.com/gulpjs/copy-props/commit/192badffd26c22198267409e4f7f337709c6a077)) * Update dependencies ([ba8a51c](https://www.github.com/gulpjs/copy-props/commit/ba8a51c28375ddd1b048e40950423caae013ba03)) ## [3.0.0](https://www.github.com/gulpjs/copy-props/compare/v2.0.5...v3.0.0) (2021-09-25) ### ⚠ BREAKING CHANGES - Normalize repository, dropping node <10.13 support (#8) ### Miscellaneous Chores - Normalize repository, dropping node <10.13 support ([#8](https://www.github.com/gulpjs/copy-props/issues/8)) ([85b1165](https://www.github.com/gulpjs/copy-props/commit/85b1165d3454791d8454ac6b74cbcb993c77bfc6)) copy-props-3.0.1/LICENSE000066400000000000000000000022321413760552600146430ustar00rootroot00000000000000MIT License Copyright (c) 2016-2021 Takayuki Sato , Blaine Bublitz , and Eric Schoffstall Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. copy-props-3.0.1/README.md000066400000000000000000000173611413760552600151260ustar00rootroot00000000000000

# copy-props [![NPM version][npm-image]][npm-url] [![Downloads][downloads-image]][npm-url] [![Build Status][ci-image]][ci-url] [![Coveralls Status][coveralls-image]][coveralls-url] Copy properties between two objects deeply. ## Install To install from npm: ```sh $ npm i copy-props --save ``` ## Load this module For Node.js: ```js const copyProps = require('copy-props'); ``` For Web browser: ```html ``` ## Usage Copy _src_ to _dst_ simply (and return _dst_) : ```js var src = { a: 1, b: { b1: 'bbb' }, c: 'ccc' }; var dst = { a: 2, b: { b1: 'xxx', b2: 'yyy' } }; copyProps(src, dst); // => { a: 1, b: { b1: 'bbb', b2: 'yyy' }, c: 'ccc' } ``` Copy _src_ to _dst_ with property mapping (and return _dst_) : ```js var src = { a: 1, b: { b1: 'bbb' }, c: 'ccc', d: 'ddd' }; var dst = { f: { a: 2, b1: 'xxx', b2: 'yyy' }, e: 'zzz' }; copyProps(src, dst, { a: 'f.a', 'b.b1': 'f.b1', 'b.b2': 'f.b2', c: 'f.c', }); // => { f: { a: 1, b1: 'bbb', b2: 'yyy', c: 'ccc' }, e: 'zzz' } ``` Copy _src_ to _dst_ with convert function (and return _dst_) : ```js var src = { a: 1, b: { b1: 'bbb' } }; var dst = { a: 0 }; copyProps(src, dst, function (srcInfo) { if (srcInfo.keyChain === 'a') { return srcInfo.value * 2; } if (srcInfo.keyChain === 'b.b1') { return srcInfo.value.toUpperCase(); } }); // => { a: 2, b: { b1: 'BBB' } } ``` Can use an array instead of a map as property mapping : ```js var src = { a: 1, b: { c: 'CCC' }, d: { e: 'EEE' } }; var dst = { a: 9, b: { c: 'xxx' }, d: { e: 'yyy' } }; var fromto = ['b.c', 'd.e']; copyProps(src, dst, fromto); // => { a: 9, b: { c: 'CCC' }, d: { e: 'EEE' } } ``` Can copy reversively (from _dst_ to _src_) by reverse flag (and return _src_): ```js var src = { a: 1, b: { b1: 'bbb' }, c: 'ccc' }; var dst = { a: 2, b: { b1: 'xxx', b2: 'yyy' } }; copyProps(src, dst, true); // => { a: 2, b: { b1: 'xxx', b2: 'yyy' }, c: 'ccc' } ``` ```js var src = { a: 1, b: { b1: 'bbb' }, c: 'ccc', d: 'ddd' }; var dst = { f: { a: 2, b1: 'xxx', b2: 'yyy' }, e: 'zzz' }; copyProps( src, dst, { a: 'f.a', 'b.b2': 'f.b2', c: 'f.c', }, true ); // => { a: 2, b: { b1: 'bbb', b2: 'yyy' }, c: 'ccc', d: 'ddd' } ``` If a value of source property is undefined (when not using converter), or a result of converter is undefined (when using converter), the value is not copied. ```js var src = { a: 'A', b: undefined, c: null, d: 1 }; var dst = { a: 'a', b: 'b', c: 'c' }; copyProps(src, dst, function (srcInfo) { if (srcInfo.keyChain === 'd') { return undefined; } else { return srcInfo.value; } }); // => { a: 'A', b: 'b', c: null } ``` You can operate the parent node object directly in converter. ```js var src = { a: 1, b: 2 }; var dst = {}; copyProps(src, dst, function (srcInfo, dstInfo) { Object.defineProperty(dstInfo.parent, dstInfo.key, { writable: false, enumerable: true, configurable: false, value: srcInfo.value * 2, }); }); // => { a: 2, b: 4 } dst; // => { a: 2, b: 4 } dst.a = 9; dst; // -> { a: 2, b: 4 } ``` ## API ### copyProps(src, dst [, fromto] [, converter] [, reverse]) => object Copy properties of _src_ to _dst_ deeply. If _fromto_ is given, it is able to copy between different properties. If _converter_ is given, it is able to convert the terminal values. #### Parameters: | Parameter | Type | Description | | :---------- | :-----------------: | :------------------------------------------------------------------------------------------------------------------------------------------------------------------ | | _src_ | object | A source object of copy. | | _dst_ | object | A destinate object of copy. | | _fromto_ | object | array | An object mapping properties between _src_ and _dst_. (Optional) | | _converter_ | function | A function to convert terminal values in _src_. (Optional) | | _reverse_ | boolean | True, if copying reversively from dst to src and returns src object. `fromto` is also reversively used from value to key. This default value is `false`. (Optional) | #### Returns: _dst_ object after copying. **Type:** object - **Format of fromto** _fromto_ is a non-nested key-value object. And the *key*s are property key chains of _src_ and the *value*s are property key chains of _dst_. The key chain is a string which is concatenated property keys on each level with dots, like `'aaa.bbb.ccc'`. The following example copys the value of `src.aaa.bbb.ccc` to `dst.xxx.yyy`. ```js copyProps(src, dst, { 'aaa.bbb.ccc': 'xxx.yyy', }); ``` _fromto_ can be an array. In that case, the array works as a map which has pairs of same key and value. - **API of converter** **converter(srcInfo, dstInfo) : Any** _converter_ is a function to convert terminal values of propeerties of _src_. **Parameters:** | Parameter | Type | Description | | :-------- | :----: | :---------------------------------------------------------------- | | _srcInfo_ | object | An object which has informations about the current node of _src_. | | _dstInfo_ | object | An object which has informations about the current node of _dst_. | **Return:** The converted value to be set as a destination property value. If this value is undefined, the destination property is not set to the destination node object. **Type:** _Any_ - **Properties of srcInfo and dstInfo** _srcInfo_ and _dstInfo_ has same properties, as follows: | Property | Type | Description | | :--------- | :----: | :------------------------------------------------------ | | _value_ | _Any_ | The value of the current node. | | _key_ | string | The key name of the current node. | | _keyChain_ | string | The full key of the current node concatenated with dot. | | _depth_ | number | The depth of the current node. | | _parent_ | object | The parent node of the current node. | ## License Copyright (C) 2016-2021 Gulp Team. This program is free software under [MIT][mit-url] License. See the file LICENSE in this distribution for more details. [downloads-image]: https://img.shields.io/npm/dm/copy-props.svg?style=flat-square [npm-url]: https://www.npmjs.org/package/copy-props [npm-image]: https://img.shields.io/npm/v/copy-props.svg?style=flat-square [ci-url]: https://github.com/gulpjs/copy-props/actions?query=workflow:dev [ci-image]: https://img.shields.io/github/workflow/status/gulpjs/copy-props/dev?style=flat-square [coveralls-url]: https://coveralls.io/r/gulpjs/copy-props [coveralls-image]: https://img.shields.io/coveralls/gulpjs/copy-props/master.svg [mit-url]: https://opensource.org/licenses/MIT copy-props-3.0.1/index.js000066400000000000000000000110401413760552600153000ustar00rootroot00000000000000'use strict'; var eachProps = require('each-props'); var isPlainObject = require('is-plain-object').isPlainObject; module.exports = function (src, dst, fromto, converter, reverse) { if (!isObject(src)) { src = {}; } if (!isObject(dst)) { dst = {}; } if (isPlainObject(fromto)) { fromto = onlyValueIsString(fromto); } else if (Array.isArray(fromto)) { fromto = arrayToObject(fromto); } else if (typeof fromto === 'boolean') { reverse = fromto; converter = noop; fromto = null; } else if (typeof fromto === 'function') { reverse = converter; converter = fromto; fromto = null; } else { fromto = null; } if (typeof converter !== 'function') { if (typeof converter === 'boolean') { reverse = converter; converter = noop; } else { converter = noop; } } if (typeof reverse !== 'boolean') { reverse = false; } if (reverse) { var tmp = src; src = dst; dst = tmp; if (fromto) { fromto = invert(fromto); } } var opts = { dest: dst, fromto: fromto, convert: converter, }; if (fromto) { eachProps(src, copyWithFromto, opts); setParentEmptyObject(dst, fromto); } else { eachProps(src, copyWithoutFromto, opts); } return dst; }; function copyWithFromto(value, keyChain, nodeInfo) { if (isPlainObject(value)) { return; } var dstKeyChains = nodeInfo.fromto[keyChain]; if (!dstKeyChains) { return; } delete nodeInfo.fromto[keyChain]; if (!Array.isArray(dstKeyChains)) { dstKeyChains = [dstKeyChains]; } var srcInfo = { keyChain: keyChain, value: value, key: nodeInfo.name, depth: nodeInfo.depth, parent: nodeInfo.parent, }; for (var i = 0, n = dstKeyChains.length; i < n; i++) { setDeep(nodeInfo.dest, dstKeyChains[i], function (parent, key, depth) { var dstInfo = { keyChain: dstKeyChains[i], value: parent[key], key: key, depth: depth, parent: parent, }; return nodeInfo.convert(srcInfo, dstInfo); }); } } function copyWithoutFromto(value, keyChain, nodeInfo) { if (isPlainObject(value)) { for (var k in value) { return; } setDeep(nodeInfo.dest, keyChain, newObject); return; } var srcInfo = { keyChain: keyChain, value: value, key: nodeInfo.name, depth: nodeInfo.depth, parent: nodeInfo.parent, }; setDeep(nodeInfo.dest, keyChain, function (parent, key, depth) { var dstInfo = { keyChain: keyChain, value: parent[key], key: key, depth: depth, parent: parent, }; return nodeInfo.convert(srcInfo, dstInfo); }); } function newObject() { return {}; } function noop(srcInfo) { return srcInfo.value; } function onlyValueIsString(obj) { var newObj = {}; for (var key in obj) { var val = obj[key]; if (typeof val === 'string') { newObj[key] = val; } } return newObj; } function arrayToObject(arr) { var obj = {}; for (var i = 0, n = arr.length; i < n; i++) { var elm = arr[i]; if (typeof elm === 'string') { obj[elm] = elm; } } return obj; } function invert(fromto) { var inv = {}; for (var key in fromto) { var val = fromto[key]; if (!inv[val]) { inv[val] = []; } inv[val].push(key); } return inv; } function setDeep(obj, keyChain, valueCreator) { _setDeep(obj, keyChain.split('.'), 1, valueCreator); } function _setDeep(obj, keyElems, depth, valueCreator) { var key = keyElems.shift(); if (isPossibilityOfPrototypePollution(key)) { return; } if (!keyElems.length) { var value = valueCreator(obj, key, depth); if (value === undefined) { return; } if (isPlainObject(value)) { // value is always an empty object. if (isPlainObject(obj[key])) { return; } } obj[key] = value; return; } if (!isPlainObject(obj[key])) { obj[key] = {}; } _setDeep(obj[key], keyElems, depth + 1, valueCreator); } function setParentEmptyObject(obj, fromto) { for (var srcKeyChain in fromto) { var dstKeyChains = fromto[srcKeyChain]; if (!Array.isArray(dstKeyChains)) { dstKeyChains = [dstKeyChains]; } for (var i = 0, n = dstKeyChains.length; i < n; i++) { setDeep(obj, dstKeyChains[i], newUndefined); } } } function newUndefined() { return undefined; } function isObject(v) { return Object.prototype.toString.call(v) === '[object Object]'; } function isPossibilityOfPrototypePollution(key) { return key === '__proto__' || key === 'constructor'; } copy-props-3.0.1/package.json000066400000000000000000000030711413760552600161260ustar00rootroot00000000000000{ "name": "copy-props", "version": "3.0.1", "description": "Copy properties deeply between two objects.", "author": "Gulp Team (https://gulpjs.com/)", "main": "index.js", "files": [ "index.js" ], "scripts": { "lint": "eslint .", "pretest": "npm run lint", "test": "nyc mocha", "web:build": "browserify index.js --standalone copyProps -o web/copy-props.js && cd web && uglifyjs copy-props.js --compress --mangle -o copy-props.min.js --source-map url=copy-props.min.js.map", "chrome:install": "npm i --no-save mocha-chrome", "chrome:test": "mocha-chrome test/web/browser-test.html", "build": "npm run lint && npm run test && npm run web:build && node test/web/make.js" }, "repository": { "type": "git", "url": "git+https://github.com/gulpjs/copy-props.git" }, "keywords": [ "object", "property", "copy", "deep", "map", "convert" ], "license": "MIT", "engines": { "node": ">= 10.13.0" }, "bugs": { "url": "https://github.com/gulpjs/copy-props/issues" }, "homepage": "https://github.com/gulpjs/copy-props#readme", "nyc": { "reporter": [ "lcov", "text-summary" ] }, "prettier": { "singleQuote": true }, "dependencies": { "each-props": "^2.0.0", "is-plain-object": "^5.0.0" }, "devDependencies": { "browserify": "^17.0.0", "chai": "^4.3.4", "eslint": "^7.32.0", "eslint-config-gulp": "^5.0.1", "eslint-plugin-node": "^11.1.0", "mocha": "^8.4.0", "nyc": "^15.1.0", "uglify-js": "^3.14.2" } } copy-props-3.0.1/test/000077500000000000000000000000001413760552600146165ustar00rootroot00000000000000copy-props-3.0.1/test/copy-props-args.js000066400000000000000000000212261413760552600202240ustar00rootroot00000000000000'use strict'; var copyProps = require('..'); var chai = require('chai'); var expect = chai.expect; /* eslint max-statements: "off", brace-style: "off" */ describe('Arguments', function () { describe('When arguments is src and dest', function () { it('Should succeed when src and dst is normal', function (done) { var src = { a: 1, b: 2 }; var dst = { a: 9, c: 3 }; expect(copyProps(src, dst)).to.deep.equal({ a: 1, b: 2, c: 3 }); done(); }); it('Should not change dst when src is not an plain object', function (done) { var dst = { a: 9, c: 3 }; expect(copyProps(undefined, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(null, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(true, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(false, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(0, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(123, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps('', dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps('A', dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps([], dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps([1, 2, 3], dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(new Date(0), dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(function () {}, dst)).to.deep.equal({ a: 9, c: 3 }); done(); }); it('Should return copy of src when dst is not a plain object', function (done) { var src = { a: 9, c: 3 }; expect(copyProps(src, undefined)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, null)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, true)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, false)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, 0)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, 123)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, '')).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, 'A')).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, [])).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, [1, 2, 3])).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, new Date(0))).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, function () {})).to.deep.equal({ a: 9, c: 3 }); done(); }); }); describe('When arguments is src, dst, fromto/converter/reverse', function () { it('Should succeed when 3rd arg is a plain object', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C' }; var expected = { A: 1, B: { C: 2, D: 20 } }; expect(copyProps(src, dst, fromto)).to.deep.equal(expected); done(); }); it('Should only pass fromto properties of which value is a string', function (done) { var src = { a: 1, b: 2 }; var dst = { A: 10, true: 20 }; var fromto = { a: 'A', b: true }; var expected = { A: 1, true: 20 }; expect(copyProps(src, dst, fromto)).to.deep.equal(expected); done(); }); it('Should succeed when 3rd arg is an array', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { a: 10, b: { d: 20 } }; var fromto = ['a', 'b.c']; var expected = { a: 1, b: { c: 2, d: 20 } }; expect(copyProps(src, dst, fromto)).to.deep.equal(expected); done(); }); it('Should only pas frommto elements which is a string', function (done) { var src = { a: 1, 123: 99 }; var dst = { a: 10, 123: 8 }; var fromto = ['a', 123]; var expected = { a: 1, 123: 8 }; expect(copyProps(src, dst, fromto)).to.deep.equal(expected); done(); }); it('Should succeed when 3rd arg is a function', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { a: 10, b: { d: 20 } }; var converter = function (srcInfo) { return srcInfo.value * 2; }; var expected = { a: 2, b: { c: 4, d: 20 } }; expect(copyProps(src, dst, converter)).to.deep.equal(expected); done(); }); it('Should succeed when 3rd arg is a boolean', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { a: 10, b: { d: 20 } }; var expected = { a: 10, b: { c: 2, d: 20 } }; expect(copyProps(src, dst, true)).to.deep.equal(expected); done(); }); it('Should ignore 3rd arg when it is other type', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { a: 10, b: { d: 20 } }; var expected = { a: 1, b: { c: 2, d: 20 } }; expect(copyProps(src, dst, undefined)).to.deep.equal(expected); expect(copyProps(src, dst, null)).to.deep.equal(expected); expect(copyProps(src, dst, 0)).to.deep.equal(expected); expect(copyProps(src, dst, 123)).to.deep.equal(expected); expect(copyProps(src, dst, '')).to.deep.equal(expected); expect(copyProps(src, dst, 'ABC')).to.deep.equal(expected); expect(copyProps(src, dst, new Date(0))).to.deep.equal(expected); done(); }); }); describe('When arguments is src, dst, fromto, converter/reverse', function () { it('Should succeed when 4th arg is a function', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C' }; var expected = { A: 2, B: { C: 4, D: 20 } }; expect( copyProps(src, dst, fromto, function (srcInfo) { return srcInfo.value * 2; }) ).to.deep.equal(expected); done(); }); it('Should succeed when 4th arg is a boolean', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C', 'b.d': 'B.D' }; var expected = { a: 10, b: { c: 2, d: 20 } }; expect(copyProps(src, dst, fromto, true)).to.deep.equal(expected); done(); }); it('Should ignore 4th arg when it is other type', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var map = { a: 'A', 'b.c': 'B.C' }; var expected = { A: 1, B: { C: 2, D: 20 } }; expect(copyProps(src, dst, map, undefined)).to.deep.equal(expected); expect(copyProps(src, dst, map, null)).to.deep.equal(expected); expect(copyProps(src, dst, map, 0)).to.deep.equal(expected); expect(copyProps(src, dst, map, 123)).to.deep.equal(expected); expect(copyProps(src, dst, map, '')).to.deep.equal(expected); expect(copyProps(src, dst, map, 'ABC')).to.deep.equal(expected); expect(copyProps(src, dst, map, [1, 2])).to.deep.equal(expected); expect(copyProps(src, dst, map, { a: 1, b: 2 })).to.deep.equal(expected); expect(copyProps(src, dst, map, new Date())).to.deep.equal(expected); done(); }); }); describe('When arguments is src, dst, fromto, converter, reverse', function () { it('Should succeed when 5th arg is a boolean', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C', 'b.d': 'B.D' }; var converter = function (srcInfo) { return srcInfo.value * 2; }; var expected = { a: 20, b: { c: 2, d: 40 } }; expect(copyProps(src, dst, fromto, converter, true)).to.deep.equal( expected ); done(); }); it('Should ignore 5th arg when it is other type', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C', 'b.d': 'B.D' }; var converter = function (srcInfo) { return srcInfo.value * 2; }; var expected = { A: 2, B: { C: 4, D: 20 } }; expect(copyProps(src, dst, fromto, converter, undefined)).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, null)).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, 0)).to.deep.equal(expected); expect(copyProps(src, dst, fromto, converter, 123)).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, '')).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, 'ABC')).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, [1, 2])).to.deep.equal( expected ); expect( copyProps(src, dst, fromto, converter, { a: 1, b: 2 }) ).to.deep.equal(expected); expect(copyProps(src, dst, fromto, converter, new Date())).to.deep.equal( expected ); expect( copyProps(src, dst, fromto, converter, function () {}) ).to.deep.equal(expected); done(); }); }); }); copy-props-3.0.1/test/copy-props-proc.js000066400000000000000000000700671413760552600202420ustar00rootroot00000000000000'use strict'; var copyProps = require('..'); var chai = require('chai'); var expect = chai.expect; /* eslint max-statements: "off" */ describe('Processing', function () { describe('When src and dst is single depth objects', function () { it('Should copy properties of src to dst', function (done) { var fn = function () {}; var src = { a: null, b: true, c: 123, d: 'ABC', e: [1, 2, 3], f: { g: 1, h: 'H' }, i: new Date(0), j: fn, }; var dst = {}; var result = copyProps(src, dst); expect(result).to.equal(dst); expect(dst).to.deep.equal(src); done(); }); it('Should overwrite dst properties by src properties', function (done) { var src = { a: 123, b: 'bbb', c: true }; var dst = { a: 987, b: 'BBB', c: false }; var result = copyProps(src, dst); expect(result).to.deep.equal(src); done(); }); it('Should ignore src properties of which value is undefined', function (done) { var src = { a: 0, b: '', c: null, d: undefined }; var dst = {}; var result = copyProps(src, dst); var expected = { a: 0, b: '', c: null }; expect(result).to.deep.equal(expected); done(); }); }); describe('When src and dst is multiple depth objects', function () { it('Should copy properties of src to dst', function (done) { var src = { a: 'A1', b: { c: 'C1', d: 'D1', e: { f: 'F1', g: 'G1', }, h: 'H1', }, }; var dst = {}; var result = copyProps(src, dst); expect(result).to.equal(dst); expect(result).to.deep.equal(src); done(); }); it('Should overwrite dst properties by src properties', function (done) { var src = { a: 'A1', b: { c: 'C1', d: 'D1', e: { f: 'F1', g: 'G1', }, h: 'H1', }, }; var dst = { a: 'A2', b: { c: 'C2', d: 'D2', e: { f: 'F2', g: 'G2', }, h: 'H2', }, }; var result = copyProps(src, dst); expect(result).to.deep.equal(src); done(); }); it('Should ignore src properties of which value is undefined', function (done) { var src = { a: '', b: { c: undefined, d: null, e: { f: 0, g: undefined, }, h: [], i: {}, }, }; var dst = { a: 'A2', b: { c: 'C2', d: 'D2', e: { f: 'F2', g: 'G2', }, h: 'H2', }, }; var expected = { a: '', b: { c: 'C2', d: null, e: { f: 0, g: 'G2', }, h: [], i: {}, }, }; var result = copyProps(src, dst); expect(result).to.deep.equal(expected); done(); }); it('Should copy properties until parent object if value is undefined', function (done) { var src = { a: undefined, b: { c: undefined }, e: { f: { g: undefined } }, h: {}, i: { j: {} }, }; var dst = {}; var result = copyProps(src, dst); var expected = { b: {}, e: { f: {} }, h: {}, i: { j: {} } }; expect(result).to.deep.equal(expected); expect(result.a).to.be.undefined; expect(result.b.c).to.be.undefined; expect(result.b.d).to.be.undefined; expect(result.e.f.g).to.be.undefined; expect(result.h.xxx).to.be.undefined; expect(result.i.j.yyy).to.be.undefined; done(); }); it( 'Should do nothing when src prop is an empty object and dst is an ' + 'object', function () { var src = { a: { b: {} } }; var dst = { a: { b: { c: 1 } } }; expect(copyProps(src, dst)).to.deep.equal({ a: { b: { c: 1 } } }); } ); it( 'Should copy normally when src prop is not a plain object but an ' + 'object', function () { function O(v) { this.a = { b: { c: v } }; } var o1 = new O(123); var o2 = new O(456); var p1 = { o: o1 }; var p2 = { o: o2 }; copyProps(p1, p2); expect(p2.o).to.equal(o1); } ); }); describe('About fromto special cases', function () { it('When fromto has surplus properties to src', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 9, B: { C: 8 } }; var fromto = { a: 'A', b: 'B', 'b.c': 'B.C', 'b.d': 'B.D', e: 'E' }; var result = copyProps(src, dst, fromto); var expected = { A: 1, B: { C: 2 } }; expect(result).to.deep.equal(expected); done(); }); it('When fromto has a part of properties of src', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = { A: 9, B: { C: 8, d: 7 }, e: 6 }; var fromto = { a: 'A', b: 'B', 'b.c': 'B.C' }; var result = copyProps(src, dst, fromto); var expected = { A: 1, B: { C: 2, d: 7 }, e: 6 }; expect(result).to.deep.equal(expected); done(); }); it('When fromto changes the structure against src', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = { A: 9, B: { C: 8 }, d: 7, e: 6 }; var fromto = { a: 'A.A', 'b.c': 'B', 'b.d': 'D.E.F' }; var result = copyProps(src, dst, fromto); var expected = { A: { A: 1 }, B: 2, D: { E: { F: 3 } }, d: 7, e: 6 }; expect(result).to.deep.equal(expected); done(); }); it('When fromto is an empty object', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = {}; var fromto = {}; var result = copyProps(src, dst, fromto); var expected = {}; expect(result).to.deep.equal(expected); done(); }); it('When fromto is an empty array', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = {}; var fromto = []; var result = copyProps(src, dst, fromto); var expected = {}; expect(result).to.deep.equal(expected); done(); }); it('When fromto object contains non-string value', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = {}; var fromto = { a: 'A', 'b.c': true, 'b.d': 123, 'b.e': ['B.E'] }; var result = copyProps(src, dst, fromto); var expected = { A: 1 }; expect(result).to.deep.equal(expected); done(); }); it('When fromto array contains non-string element', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = {}; var fromto = ['a', true, 123, ['B.E']]; var result = copyProps(src, dst, fromto); var expected = { a: 1 }; expect(result).to.deep.equal(expected); done(); }); it('Should copy properties until parent object if value is undefined', function (done) { var src = {}; var dst = {}; var fromto = ['a', 'b.c', 'b.d', 'e.f.g']; var result = copyProps(src, dst, fromto); var expected = { b: {}, e: { f: {} } }; expect(result).to.deep.equal(expected); expect(result.a).to.be.undefined; expect(result.b.c).to.be.undefined; expect(result.b.d).to.be.undefined; expect(result.e.f.g).to.be.undefined; done(); }); it( 'Should do nothing when src prop is an empty object and dst is an ' + 'object', function () { var src = { a: { b: {} } }; var dst = { a: { b: { c: 1 } } }; var fromto = ['a.b']; expect(copyProps(src, dst, fromto)).to.deep.equal({ a: { b: { c: 1 } }, }); } ); }); describe('About patterns of converter returns', function () { it('When converter returns undefined', function (done) { var src = { a: 1, b: { c: 2, d: 3, e: 4 } }; var dst = { a: 'A', b: { e: 'E' } }; function fn(srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal(1); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(src); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('A'); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(dst); break; } case 'b.c': { expect(srcInfo.value).to.equal(2); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.d': { expect(srcInfo.value).to.equal(3); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.e': { expect(srcInfo.value).to.equal(4); expect(srcInfo.key).to.equal('e'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('E'); expect(dstInfo.key).to.equal('e'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } default: { expect(true).to.not.be.true; break; } } return srcInfo.keyChain === 'b.c' ? undefined : srcInfo.value; } var result = copyProps(src, dst, fn); var expected = { a: 1, b: { d: 3, e: 4 } }; expect(result).to.deep.equal(expected); done(); }); it('When converter returns null', function (done) { var src = { a: 1, b: { c: 2, d: 3 } }; var dst = {}; function fn(srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal(1); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(src); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(dst); break; } case 'b.c': { expect(srcInfo.value).to.equal(2); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.d': { expect(srcInfo.value).to.equal(3); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } default: { expect(true).to.not.be.true; break; } } return srcInfo.keyChain === 'b.c' ? null : srcInfo.value; } var result = copyProps(src, dst, fn); var expected = { a: 1, b: { c: null, d: 3 } }; expect(result).to.deep.equal(expected); done(); }); }); describe('About reverse', function () { it('When reverse is true', function (done) { var src = { a: 1, b: { d: 3 } }; var dst = { a: 'A', b: { c: 'C', d: 'D' } }; var result = copyProps(src, dst, true); var expected = { a: 'A', b: { c: 'C', d: 'D' } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D' } }; var fromto = ['a', 'b.d']; result = copyProps(src, dst, fromto, true); expected = { a: 'A', b: { c: 2, d: 'D' } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D' } }; var converter = function (srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal('A'); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(dst); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(1); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(src); break; } case 'b.c': { expect(srcInfo.value).to.equal('C'); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(2); expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } case 'b.d': { expect(srcInfo.value).to.equal('D'); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(3); expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } default: { expect(true).to.not.be.true; break; } } if (srcInfo.keyChain === 'b.c') { return undefined; } else { return srcInfo.value.toLowerCase(); } }; result = copyProps(src, dst, converter, true); expected = { a: 'a', b: { c: 2, d: 'd' } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D', e: 'E', f: 'F' } }; fromto = ['a', 'b.c', 'b.d', 'b.e']; converter = function (srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal('A'); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(dst); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(1); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(src); break; } case 'b.c': { expect(srcInfo.value).to.equal('C'); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(2); expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } case 'b.d': { expect(srcInfo.value).to.equal('D'); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(3); expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } case 'b.e': { expect(srcInfo.value).to.equal('E'); expect(srcInfo.key).to.equal('e'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('e'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } default: { expect(true).to.not.be.true; break; } } if (srcInfo.keyChain === 'b.c') { return undefined; } else { return srcInfo.value.toLowerCase(); } }; result = copyProps(src, dst, fromto, converter, true); expected = { a: 'a', b: { c: 2, d: 'd', e: 'e' } }; expect(result).to.deep.equal(expected); done(); }); it('When reverse is false', function (done) { var src = { a: 1, b: { d: 3 } }; var dst = { a: 'A', b: { c: 'C', d: 'D' } }; var result = copyProps(src, dst, false); var expected = { a: 1, b: { c: 'C', d: 3 } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D' } }; var fromto = ['a', 'b.d']; result = copyProps(src, dst, fromto, false); expected = { a: 1, b: { c: 'C', d: 3 } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D' } }; var converter = function (srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal(1); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(src); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('A'); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(dst); break; } case 'b.c': { expect(srcInfo.value).to.equal(2); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('C'); expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.d': { expect(srcInfo.value).to.equal(3); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('D'); expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } default: { expect(true).to.not.be.true; break; } } if (srcInfo.keyChain === 'b.c') { return undefined; } else { return srcInfo.value * 10; } }; result = copyProps(src, dst, converter, false); expected = { a: 10, b: { c: 'C', d: 30 } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D', e: 'E', f: 'F' } }; fromto = ['a', 'b.c', 'b.d', 'b.e']; converter = function (srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal(1); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(src); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('A'); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(dst); break; } case 'b.c': { expect(srcInfo.value).to.equal(2); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('C'); expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.d': { expect(srcInfo.value).to.equal(3); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('D'); expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.e': { expect(srcInfo.value).to.be.undefined; expect(srcInfo.key).to.equal('e'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('E'); expect(dstInfo.key).to.equal('e'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } default: { expect(true).to.not.be.true; break; } } if (srcInfo.keyChain === 'b.c') { return undefined; } else { return srcInfo.value * 10; } }; result = copyProps(src, dst, fromto, converter, false); expected = { a: 10, b: { c: 'C', d: 30, e: 'E', f: 'F' } }; expect(result).to.deep.equal(expected); done(); }); it( 'When reverse is true and fromto has a property of which value ' + 'is same \n\twith other properties', function (done) { var src = { a: 1, b: { c: 2, d: 3 } }; var dst = { A: 'AAA', B: 'BBB' }; var fromto = { a: 'A', 'b.c': 'B', 'b.d': 'B' }; var expected = { A: 1, B: 3 }; var result = copyProps(src, dst, fromto); expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { A: 'AAA', B: 'BBB' }; fromto = { a: 'A', 'b.c': 'B', 'b.d': 'B' }; expected = { a: 'AAA', b: { c: 'BBB', d: 'BBB' } }; result = copyProps(src, dst, fromto, true); expect(result).to.deep.equal(expected); done(); } ); }); describe('Avoid a prototype pollution vulnerability', function () { describe('The critical property key is in a src object', function () { it('should ignore a property key: __proto__', function (done) { var maliciousSrcJson = '{"__proto__":{"polluted":"polluted"},"a":1}'; expect({}.polluted).to.be.undefined; expect(copyProps(JSON.parse(maliciousSrcJson), {})).to.deep.equal({ a: 1, }); expect({}.polluted).to.be.undefined; done(); }); it('should ignore a property key: constructor.prototype', function (done) { var maliciousSrcJson = '{"constructor":{"prototype":{"polluted":"polluted"}},"a":1}'; expect({}.polluted).to.be.undefined; expect(copyProps(JSON.parse(maliciousSrcJson), {})).to.deep.equal({ a: 1, }); expect({}.polluted).to.be.undefined; done(); }); }); describe('The critical property key is in a dest object and using reverse', function () { it('should ignore a property key: __proto__', function (done) { var maliciousSrcJson = '{"__proto__":{"polluted":"polluted"},"a":1}'; expect({}.polluted).to.be.undefined; expect(copyProps({}, JSON.parse(maliciousSrcJson), true)).to.deep.equal( { a: 1 } ); expect({}.polluted).to.be.undefined; done(); }); it('should ignore a property key: constructor.prototype', function (done) { var maliciousSrcJson = '{"constructor":{"prototype":{"polluted":"polluted"}},"a":1}'; expect({}.polluted).to.be.undefined; expect(copyProps({}, JSON.parse(maliciousSrcJson), true)).to.deep.equal( { a: 1 } ); expect({}.polluted).to.be.undefined; done(); }); }); describe('The critical property value is in a fromto object', function () { it('should ignore a property value: __proto__', function (done) { var fromto = { a: '__proto__.poluuted', b: 'c' }; expect({}.polluted).to.be.undefined; expect(copyProps({ a: 'polluted', b: 1 }, {}, fromto)).to.deep.equal({ c: 1, }); expect({}.polluted).to.be.undefined; done(); }); it('should ignore a property value: constructor.prototype', function (done) { var fromto = { a: 'constructor.prototype.polluted', b: 'c' }; expect({}.polluted).to.be.undefined; expect(copyProps({ a: 'polluted', b: 1 }, {}, fromto)).to.deep.equal({ c: 1, }); expect({}.polluted).to.be.undefined; done(); }); }); describe('The critical property key is in a fromto object and using reverse', function () { it('should ignore a property key: __proto__', function (done) { var fromto = { '__proto__.poluuted': 'a', c: 'b' }; expect({}.polluted).to.be.undefined; expect( copyProps({}, { a: 'polluted', b: 1 }, fromto, true) ).to.deep.equal({ c: 1 }); expect({}.polluted).to.be.undefined; done(); }); it('should ignore a property key: constructor.prototype and using reverse', function (done) { var fromto = { 'constructor.prototype.polluted': 'a', c: 'b' }; expect({}.polluted).to.be.undefined; expect( copyProps({}, { a: 'polluted', b: 1 }, fromto, true) ).to.deep.equal({ c: 1 }); expect({}.polluted).to.be.undefined; done(); }); }); describe('The critical element is in a fromto array', function () { it('should ignore an element: __proto__', function (done) { var fromto = ['__proto__.polluted', 'b']; expect({}.polluted).to.be.undefined; expect( copyProps( JSON.parse('{"__proto__":{"polluted":"polluted"},"b":1}'), {}, fromto ) ).to.deep.equal({ b: 1 }); expect({}.polluted).to.be.undefined; done(); }); it('should ignore an element: constructor.prototype', function (done) { var fromto = ['constructor.prototype.polluted', 'b']; expect({}.polluted).to.be.undefined; expect( copyProps( JSON.parse( '{"constructor":{"prototype":{"polluted":"polluted"}},"b":1}' ), {}, fromto ) ).to.deep.equal({ b: 1 }); expect({}.polluted).to.be.undefined; done(); }); }); }); }); copy-props-3.0.1/test/web/000077500000000000000000000000001413760552600153735ustar00rootroot00000000000000copy-props-3.0.1/test/web/browser-test.html000066400000000000000000000012001413760552600207120ustar00rootroot00000000000000 copy-props test on browser
copy-props-3.0.1/test/web/copy-props-args.js000066400000000000000000000211331413760552600207760ustar00rootroot00000000000000'use strict'; var expect = chai.expect; /* eslint max-statements: "off", brace-style: "off" */ describe('Arguments', function () { describe('When arguments is src and dest', function () { it('Should succeed when src and dst is normal', function (done) { var src = { a: 1, b: 2 }; var dst = { a: 9, c: 3 }; expect(copyProps(src, dst)).to.deep.equal({ a: 1, b: 2, c: 3 }); done(); }); it('Should not change dst when src is not an plain object', function (done) { var dst = { a: 9, c: 3 }; expect(copyProps(undefined, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(null, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(true, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(false, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(0, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(123, dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps('', dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps('A', dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps([], dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps([1, 2, 3], dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(new Date(0), dst)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(function () {}, dst)).to.deep.equal({ a: 9, c: 3 }); done(); }); it('Should return copy of src when dst is not a plain object', function (done) { var src = { a: 9, c: 3 }; expect(copyProps(src, undefined)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, null)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, true)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, false)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, 0)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, 123)).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, '')).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, 'A')).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, [])).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, [1, 2, 3])).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, new Date(0))).to.deep.equal({ a: 9, c: 3 }); expect(copyProps(src, function () {})).to.deep.equal({ a: 9, c: 3 }); done(); }); }); describe('When arguments is src, dst, fromto/converter/reverse', function () { it('Should succeed when 3rd arg is a plain object', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C' }; var expected = { A: 1, B: { C: 2, D: 20 } }; expect(copyProps(src, dst, fromto)).to.deep.equal(expected); done(); }); it('Should only pass fromto properties of which value is a string', function (done) { var src = { a: 1, b: 2 }; var dst = { A: 10, true: 20 }; var fromto = { a: 'A', b: true }; var expected = { A: 1, true: 20 }; expect(copyProps(src, dst, fromto)).to.deep.equal(expected); done(); }); it('Should succeed when 3rd arg is an array', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { a: 10, b: { d: 20 } }; var fromto = ['a', 'b.c']; var expected = { a: 1, b: { c: 2, d: 20 } }; expect(copyProps(src, dst, fromto)).to.deep.equal(expected); done(); }); it('Should only pas frommto elements which is a string', function (done) { var src = { a: 1, 123: 99 }; var dst = { a: 10, 123: 8 }; var fromto = ['a', 123]; var expected = { a: 1, 123: 8 }; expect(copyProps(src, dst, fromto)).to.deep.equal(expected); done(); }); it('Should succeed when 3rd arg is a function', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { a: 10, b: { d: 20 } }; var converter = function (srcInfo) { return srcInfo.value * 2; }; var expected = { a: 2, b: { c: 4, d: 20 } }; expect(copyProps(src, dst, converter)).to.deep.equal(expected); done(); }); it('Should succeed when 3rd arg is a boolean', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { a: 10, b: { d: 20 } }; var expected = { a: 10, b: { c: 2, d: 20 } }; expect(copyProps(src, dst, true)).to.deep.equal(expected); done(); }); it('Should ignore 3rd arg when it is other type', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { a: 10, b: { d: 20 } }; var expected = { a: 1, b: { c: 2, d: 20 } }; expect(copyProps(src, dst, undefined)).to.deep.equal(expected); expect(copyProps(src, dst, null)).to.deep.equal(expected); expect(copyProps(src, dst, 0)).to.deep.equal(expected); expect(copyProps(src, dst, 123)).to.deep.equal(expected); expect(copyProps(src, dst, '')).to.deep.equal(expected); expect(copyProps(src, dst, 'ABC')).to.deep.equal(expected); expect(copyProps(src, dst, new Date(0))).to.deep.equal(expected); done(); }); }); describe('When arguments is src, dst, fromto, converter/reverse', function () { it('Should succeed when 4th arg is a function', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C' }; var expected = { A: 2, B: { C: 4, D: 20 } }; expect( copyProps(src, dst, fromto, function (srcInfo) { return srcInfo.value * 2; }) ).to.deep.equal(expected); done(); }); it('Should succeed when 4th arg is a boolean', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C', 'b.d': 'B.D' }; var expected = { a: 10, b: { c: 2, d: 20 } }; expect(copyProps(src, dst, fromto, true)).to.deep.equal(expected); done(); }); it('Should ignore 4th arg when it is other type', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var map = { a: 'A', 'b.c': 'B.C' }; var expected = { A: 1, B: { C: 2, D: 20 } }; expect(copyProps(src, dst, map, undefined)).to.deep.equal(expected); expect(copyProps(src, dst, map, null)).to.deep.equal(expected); expect(copyProps(src, dst, map, 0)).to.deep.equal(expected); expect(copyProps(src, dst, map, 123)).to.deep.equal(expected); expect(copyProps(src, dst, map, '')).to.deep.equal(expected); expect(copyProps(src, dst, map, 'ABC')).to.deep.equal(expected); expect(copyProps(src, dst, map, [1, 2])).to.deep.equal(expected); expect(copyProps(src, dst, map, { a: 1, b: 2 })).to.deep.equal(expected); expect(copyProps(src, dst, map, new Date())).to.deep.equal(expected); done(); }); }); describe('When arguments is src, dst, fromto, converter, reverse', function () { it('Should succeed when 5th arg is a boolean', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C', 'b.d': 'B.D' }; var converter = function (srcInfo) { return srcInfo.value * 2; }; var expected = { a: 20, b: { c: 2, d: 40 } }; expect(copyProps(src, dst, fromto, converter, true)).to.deep.equal( expected ); done(); }); it('Should ignore 5th arg when it is other type', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 10, B: { D: 20 } }; var fromto = { a: 'A', 'b.c': 'B.C', 'b.d': 'B.D' }; var converter = function (srcInfo) { return srcInfo.value * 2; }; var expected = { A: 2, B: { C: 4, D: 20 } }; expect(copyProps(src, dst, fromto, converter, undefined)).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, null)).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, 0)).to.deep.equal(expected); expect(copyProps(src, dst, fromto, converter, 123)).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, '')).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, 'ABC')).to.deep.equal( expected ); expect(copyProps(src, dst, fromto, converter, [1, 2])).to.deep.equal( expected ); expect( copyProps(src, dst, fromto, converter, { a: 1, b: 2 }) ).to.deep.equal(expected); expect(copyProps(src, dst, fromto, converter, new Date())).to.deep.equal( expected ); expect( copyProps(src, dst, fromto, converter, function () {}) ).to.deep.equal(expected); done(); }); }); }); copy-props-3.0.1/test/web/copy-props-proc.js000066400000000000000000000677741413760552600210320ustar00rootroot00000000000000'use strict'; var expect = chai.expect; /* eslint max-statements: "off" */ describe('Processing', function () { describe('When src and dst is single depth objects', function () { it('Should copy properties of src to dst', function (done) { var fn = function () {}; var src = { a: null, b: true, c: 123, d: 'ABC', e: [1, 2, 3], f: { g: 1, h: 'H' }, i: new Date(0), j: fn, }; var dst = {}; var result = copyProps(src, dst); expect(result).to.equal(dst); expect(dst).to.deep.equal(src); done(); }); it('Should overwrite dst properties by src properties', function (done) { var src = { a: 123, b: 'bbb', c: true }; var dst = { a: 987, b: 'BBB', c: false }; var result = copyProps(src, dst); expect(result).to.deep.equal(src); done(); }); it('Should ignore src properties of which value is undefined', function (done) { var src = { a: 0, b: '', c: null, d: undefined }; var dst = {}; var result = copyProps(src, dst); var expected = { a: 0, b: '', c: null }; expect(result).to.deep.equal(expected); done(); }); }); describe('When src and dst is multiple depth objects', function () { it('Should copy properties of src to dst', function (done) { var src = { a: 'A1', b: { c: 'C1', d: 'D1', e: { f: 'F1', g: 'G1', }, h: 'H1', }, }; var dst = {}; var result = copyProps(src, dst); expect(result).to.equal(dst); expect(result).to.deep.equal(src); done(); }); it('Should overwrite dst properties by src properties', function (done) { var src = { a: 'A1', b: { c: 'C1', d: 'D1', e: { f: 'F1', g: 'G1', }, h: 'H1', }, }; var dst = { a: 'A2', b: { c: 'C2', d: 'D2', e: { f: 'F2', g: 'G2', }, h: 'H2', }, }; var result = copyProps(src, dst); expect(result).to.deep.equal(src); done(); }); it('Should ignore src properties of which value is undefined', function (done) { var src = { a: '', b: { c: undefined, d: null, e: { f: 0, g: undefined, }, h: [], i: {}, }, }; var dst = { a: 'A2', b: { c: 'C2', d: 'D2', e: { f: 'F2', g: 'G2', }, h: 'H2', }, }; var expected = { a: '', b: { c: 'C2', d: null, e: { f: 0, g: 'G2', }, h: [], i: {}, }, }; var result = copyProps(src, dst); expect(result).to.deep.equal(expected); done(); }); it('Should copy properties until parent object if value is undefined', function (done) { var src = { a: undefined, b: { c: undefined }, e: { f: { g: undefined } }, h: {}, i: { j: {} }, }; var dst = {}; var result = copyProps(src, dst); var expected = { b: {}, e: { f: {} }, h: {}, i: { j: {} } }; expect(result).to.deep.equal(expected); expect(result.a).to.be.undefined; expect(result.b.c).to.be.undefined; expect(result.b.d).to.be.undefined; expect(result.e.f.g).to.be.undefined; expect(result.h.xxx).to.be.undefined; expect(result.i.j.yyy).to.be.undefined; done(); }); it( 'Should do nothing when src prop is an empty object and dst is an ' + 'object', function () { var src = { a: { b: {} } }; var dst = { a: { b: { c: 1 } } }; expect(copyProps(src, dst)).to.deep.equal({ a: { b: { c: 1 } } }); } ); it( 'Should copy normally when src prop is not a plain object but an ' + 'object', function () { function O(v) { this.a = { b: { c: v } }; } var o1 = new O(123); var o2 = new O(456); var p1 = { o: o1 }; var p2 = { o: o2 }; copyProps(p1, p2); expect(p2.o).to.equal(o1); } ); }); describe('About fromto special cases', function () { it('When fromto has surplus properties to src', function (done) { var src = { a: 1, b: { c: 2 } }; var dst = { A: 9, B: { C: 8 } }; var fromto = { a: 'A', b: 'B', 'b.c': 'B.C', 'b.d': 'B.D', e: 'E' }; var result = copyProps(src, dst, fromto); var expected = { A: 1, B: { C: 2 } }; expect(result).to.deep.equal(expected); done(); }); it('When fromto has a part of properties of src', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = { A: 9, B: { C: 8, d: 7 }, e: 6 }; var fromto = { a: 'A', b: 'B', 'b.c': 'B.C' }; var result = copyProps(src, dst, fromto); var expected = { A: 1, B: { C: 2, d: 7 }, e: 6 }; expect(result).to.deep.equal(expected); done(); }); it('When fromto changes the structure against src', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = { A: 9, B: { C: 8 }, d: 7, e: 6 }; var fromto = { a: 'A.A', 'b.c': 'B', 'b.d': 'D.E.F' }; var result = copyProps(src, dst, fromto); var expected = { A: { A: 1 }, B: 2, D: { E: { F: 3 } }, d: 7, e: 6 }; expect(result).to.deep.equal(expected); done(); }); it('When fromto is an empty object', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = {}; var fromto = {}; var result = copyProps(src, dst, fromto); var expected = {}; expect(result).to.deep.equal(expected); done(); }); it('When fromto is an empty array', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = {}; var fromto = []; var result = copyProps(src, dst, fromto); var expected = {}; expect(result).to.deep.equal(expected); done(); }); it('When fromto object contains non-string value', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = {}; var fromto = { a: 'A', 'b.c': true, 'b.d': 123, 'b.e': ['B.E'] }; var result = copyProps(src, dst, fromto); var expected = { A: 1 }; expect(result).to.deep.equal(expected); done(); }); it('When fromto array contains non-string element', function (done) { var src = { a: 1, b: { c: 2, d: 3 }, e: 4 }; var dst = {}; var fromto = ['a', true, 123, ['B.E']]; var result = copyProps(src, dst, fromto); var expected = { a: 1 }; expect(result).to.deep.equal(expected); done(); }); it('Should copy properties until parent object if value is undefined', function (done) { var src = {}; var dst = {}; var fromto = ['a', 'b.c', 'b.d', 'e.f.g']; var result = copyProps(src, dst, fromto); var expected = { b: {}, e: { f: {} } }; expect(result).to.deep.equal(expected); expect(result.a).to.be.undefined; expect(result.b.c).to.be.undefined; expect(result.b.d).to.be.undefined; expect(result.e.f.g).to.be.undefined; done(); }); it( 'Should do nothing when src prop is an empty object and dst is an ' + 'object', function () { var src = { a: { b: {} } }; var dst = { a: { b: { c: 1 } } }; var fromto = ['a.b']; expect(copyProps(src, dst, fromto)).to.deep.equal({ a: { b: { c: 1 } }, }); } ); }); describe('About patterns of converter returns', function () { it('When converter returns undefined', function (done) { var src = { a: 1, b: { c: 2, d: 3, e: 4 } }; var dst = { a: 'A', b: { e: 'E' } }; function fn(srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal(1); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(src); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('A'); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(dst); break; } case 'b.c': { expect(srcInfo.value).to.equal(2); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.d': { expect(srcInfo.value).to.equal(3); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.e': { expect(srcInfo.value).to.equal(4); expect(srcInfo.key).to.equal('e'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('E'); expect(dstInfo.key).to.equal('e'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } default: { expect(true).to.not.be.true; break; } } return srcInfo.keyChain === 'b.c' ? undefined : srcInfo.value; } var result = copyProps(src, dst, fn); var expected = { a: 1, b: { d: 3, e: 4 } }; expect(result).to.deep.equal(expected); done(); }); it('When converter returns null', function (done) { var src = { a: 1, b: { c: 2, d: 3 } }; var dst = {}; function fn(srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal(1); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(src); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(dst); break; } case 'b.c': { expect(srcInfo.value).to.equal(2); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.d': { expect(srcInfo.value).to.equal(3); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } default: { expect(true).to.not.be.true; break; } } return srcInfo.keyChain === 'b.c' ? null : srcInfo.value; } var result = copyProps(src, dst, fn); var expected = { a: 1, b: { c: null, d: 3 } }; expect(result).to.deep.equal(expected); done(); }); }); describe('About reverse', function () { it('When reverse is true', function (done) { var src = { a: 1, b: { d: 3 } }; var dst = { a: 'A', b: { c: 'C', d: 'D' } }; var result = copyProps(src, dst, true); var expected = { a: 'A', b: { c: 'C', d: 'D' } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D' } }; var fromto = ['a', 'b.d']; result = copyProps(src, dst, fromto, true); expected = { a: 'A', b: { c: 2, d: 'D' } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D' } }; var converter = function (srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal('A'); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(dst); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(1); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(src); break; } case 'b.c': { expect(srcInfo.value).to.equal('C'); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(2); expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } case 'b.d': { expect(srcInfo.value).to.equal('D'); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(3); expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } default: { expect(true).to.not.be.true; break; } } if (srcInfo.keyChain === 'b.c') { return undefined; } else { return srcInfo.value.toLowerCase(); } }; result = copyProps(src, dst, converter, true); expected = { a: 'a', b: { c: 2, d: 'd' } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D', e: 'E', f: 'F' } }; fromto = ['a', 'b.c', 'b.d', 'b.e']; converter = function (srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal('A'); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(dst); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(1); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(src); break; } case 'b.c': { expect(srcInfo.value).to.equal('C'); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(2); expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } case 'b.d': { expect(srcInfo.value).to.equal('D'); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal(3); expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } case 'b.e': { expect(srcInfo.value).to.equal('E'); expect(srcInfo.key).to.equal('e'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(dst.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.be.undefined; expect(dstInfo.key).to.equal('e'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(src.b); break; } default: { expect(true).to.not.be.true; break; } } if (srcInfo.keyChain === 'b.c') { return undefined; } else { return srcInfo.value.toLowerCase(); } }; result = copyProps(src, dst, fromto, converter, true); expected = { a: 'a', b: { c: 2, d: 'd', e: 'e' } }; expect(result).to.deep.equal(expected); done(); }); it('When reverse is false', function (done) { var src = { a: 1, b: { d: 3 } }; var dst = { a: 'A', b: { c: 'C', d: 'D' } }; var result = copyProps(src, dst, false); var expected = { a: 1, b: { c: 'C', d: 3 } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D' } }; var fromto = ['a', 'b.d']; result = copyProps(src, dst, fromto, false); expected = { a: 1, b: { c: 'C', d: 3 } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D' } }; var converter = function (srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal(1); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(src); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('A'); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(dst); break; } case 'b.c': { expect(srcInfo.value).to.equal(2); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('C'); expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.d': { expect(srcInfo.value).to.equal(3); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('D'); expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } default: { expect(true).to.not.be.true; break; } } if (srcInfo.keyChain === 'b.c') { return undefined; } else { return srcInfo.value * 10; } }; result = copyProps(src, dst, converter, false); expected = { a: 10, b: { c: 'C', d: 30 } }; expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { a: 'A', b: { c: 'C', d: 'D', e: 'E', f: 'F' } }; fromto = ['a', 'b.c', 'b.d', 'b.e']; converter = function (srcInfo, dstInfo) { switch (srcInfo.keyChain) { case 'a': { expect(srcInfo.value).to.equal(1); expect(srcInfo.key).to.equal('a'); expect(srcInfo.depth).to.equal(1); expect(srcInfo.parent).to.equal(src); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('A'); expect(dstInfo.key).to.equal('a'); expect(dstInfo.depth).to.equal(1); expect(dstInfo.parent).to.equal(dst); break; } case 'b.c': { expect(srcInfo.value).to.equal(2); expect(srcInfo.key).to.equal('c'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('C'); expect(dstInfo.key).to.equal('c'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.d': { expect(srcInfo.value).to.equal(3); expect(srcInfo.key).to.equal('d'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('D'); expect(dstInfo.key).to.equal('d'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } case 'b.e': { expect(srcInfo.value).to.be.undefined; expect(srcInfo.key).to.equal('e'); expect(srcInfo.depth).to.equal(2); expect(srcInfo.parent).to.equal(src.b); expect(dstInfo.keyChain).to.equal(srcInfo.keyChain); expect(dstInfo.value).to.equal('E'); expect(dstInfo.key).to.equal('e'); expect(dstInfo.depth).to.equal(2); expect(dstInfo.parent).to.equal(dst.b); break; } default: { expect(true).to.not.be.true; break; } } if (srcInfo.keyChain === 'b.c') { return undefined; } else { return srcInfo.value * 10; } }; result = copyProps(src, dst, fromto, converter, false); expected = { a: 10, b: { c: 'C', d: 30, e: 'E', f: 'F' } }; expect(result).to.deep.equal(expected); done(); }); it( 'When reverse is true and fromto has a property of which value ' + 'is same \n\twith other properties', function (done) { var src = { a: 1, b: { c: 2, d: 3 } }; var dst = { A: 'AAA', B: 'BBB' }; var fromto = { a: 'A', 'b.c': 'B', 'b.d': 'B' }; var expected = { A: 1, B: 3 }; var result = copyProps(src, dst, fromto); expect(result).to.deep.equal(expected); src = { a: 1, b: { c: 2, d: 3 } }; dst = { A: 'AAA', B: 'BBB' }; fromto = { a: 'A', 'b.c': 'B', 'b.d': 'B' }; expected = { a: 'AAA', b: { c: 'BBB', d: 'BBB' } }; result = copyProps(src, dst, fromto, true); expect(result).to.deep.equal(expected); done(); } ); }); describe('Avoid a prototype pollution vulnerability', function () { describe('The critical property key is in a src object', function () { it('should ignore a property key: __proto__', function (done) { var maliciousSrcJson = '{"__proto__":{"polluted":"polluted"},"a":1}'; expect({}.polluted).to.be.undefined; expect(copyProps(JSON.parse(maliciousSrcJson), {})).to.deep.equal({ a: 1, }); expect({}.polluted).to.be.undefined; done(); }); it('should ignore a property key: constructor.prototype', function (done) { var maliciousSrcJson = '{"constructor":{"prototype":{"polluted":"polluted"}},"a":1}'; expect({}.polluted).to.be.undefined; expect(copyProps(JSON.parse(maliciousSrcJson), {})).to.deep.equal({ a: 1, }); expect({}.polluted).to.be.undefined; done(); }); }); describe('The critical property key is in a dest object and using reverse', function () { it('should ignore a property key: __proto__', function (done) { var maliciousSrcJson = '{"__proto__":{"polluted":"polluted"},"a":1}'; expect({}.polluted).to.be.undefined; expect(copyProps({}, JSON.parse(maliciousSrcJson), true)).to.deep.equal( { a: 1 } ); expect({}.polluted).to.be.undefined; done(); }); it('should ignore a property key: constructor.prototype', function (done) { var maliciousSrcJson = '{"constructor":{"prototype":{"polluted":"polluted"}},"a":1}'; expect({}.polluted).to.be.undefined; expect(copyProps({}, JSON.parse(maliciousSrcJson), true)).to.deep.equal( { a: 1 } ); expect({}.polluted).to.be.undefined; done(); }); }); describe('The critical property value is in a fromto object', function () { it('should ignore a property value: __proto__', function (done) { var fromto = { a: '__proto__.poluuted', b: 'c' }; expect({}.polluted).to.be.undefined; expect(copyProps({ a: 'polluted', b: 1 }, {}, fromto)).to.deep.equal({ c: 1, }); expect({}.polluted).to.be.undefined; done(); }); it('should ignore a property value: constructor.prototype', function (done) { var fromto = { a: 'constructor.prototype.polluted', b: 'c' }; expect({}.polluted).to.be.undefined; expect(copyProps({ a: 'polluted', b: 1 }, {}, fromto)).to.deep.equal({ c: 1, }); expect({}.polluted).to.be.undefined; done(); }); }); describe('The critical property key is in a fromto object and using reverse', function () { it('should ignore a property key: __proto__', function (done) { var fromto = { '__proto__.poluuted': 'a', c: 'b' }; expect({}.polluted).to.be.undefined; expect( copyProps({}, { a: 'polluted', b: 1 }, fromto, true) ).to.deep.equal({ c: 1 }); expect({}.polluted).to.be.undefined; done(); }); it('should ignore a property key: constructor.prototype and using reverse', function (done) { var fromto = { 'constructor.prototype.polluted': 'a', c: 'b' }; expect({}.polluted).to.be.undefined; expect( copyProps({}, { a: 'polluted', b: 1 }, fromto, true) ).to.deep.equal({ c: 1 }); expect({}.polluted).to.be.undefined; done(); }); }); describe('The critical element is in a fromto array', function () { it('should ignore an element: __proto__', function (done) { var fromto = ['__proto__.polluted', 'b']; expect({}.polluted).to.be.undefined; expect( copyProps( JSON.parse('{"__proto__":{"polluted":"polluted"},"b":1}'), {}, fromto ) ).to.deep.equal({ b: 1 }); expect({}.polluted).to.be.undefined; done(); }); it('should ignore an element: constructor.prototype', function (done) { var fromto = ['constructor.prototype.polluted', 'b']; expect({}.polluted).to.be.undefined; expect( copyProps( JSON.parse( '{"constructor":{"prototype":{"polluted":"polluted"}},"b":1}' ), {}, fromto ) ).to.deep.equal({ b: 1 }); expect({}.polluted).to.be.undefined; done(); }); }); }); }); copy-props-3.0.1/test/web/make.js000066400000000000000000000007601413760552600166510ustar00rootroot00000000000000'use strict'; var fs = require('fs'); var path = require('path'); var opts = { encoding: 'utf-8' }; function make(filename) { fs.readFile(path.join(__dirname, '..', filename), opts, function (err, data) { throwIfError(err); data = data.replace(/[^\r\n]*require[^\r|\n]*/g, ''); fs.writeFile(path.join(__dirname, filename), data, opts, throwIfError); }); } function throwIfError(err) { if (err) { throw err; } } make('copy-props-args.js'); make('copy-props-proc.js'); copy-props-3.0.1/web/000077500000000000000000000000001413760552600144145ustar00rootroot00000000000000copy-props-3.0.1/web/copy-props.js000066400000000000000000000443201413760552600170700ustar00rootroot00000000000000(function (f) { if (typeof exports === 'object' && typeof module !== 'undefined') { module.exports = f(); } else if (typeof define === 'function' && define.amd) { define([], f); } else { var g; if (typeof window !== 'undefined') { g = window; } else if (typeof global !== 'undefined') { g = global; } else if (typeof self !== 'undefined') { g = self; } else { g = this; } g.copyProps = f(); } })(function () { var define, module, exports; return (function () { function r(e, n, t) { function o(i, f) { if (!n[i]) { if (!e[i]) { var c = 'function' == typeof require && require; if (!f && c) return c(i, !0); if (u) return u(i, !0); var a = new Error("Cannot find module '" + i + "'"); throw ((a.code = 'MODULE_NOT_FOUND'), a); } var p = (n[i] = { exports: {} }); e[i][0].call( p.exports, function (r) { var n = e[i][1][r]; return o(n || r); }, p, p.exports, r, e, n, t ); } return n[i].exports; } for ( var u = 'function' == typeof require && require, i = 0; i < t.length; i++ ) o(t[i]); return o; } return r; })()( { 1: [ function (require, module, exports) { 'use strict'; var eachProps = require('each-props'); var isPlainObject = require('is-plain-object').isPlainObject; module.exports = function (src, dst, fromto, converter, reverse) { if (!isObject(src)) { src = {}; } if (!isObject(dst)) { dst = {}; } if (isPlainObject(fromto)) { fromto = onlyValueIsString(fromto); } else if (Array.isArray(fromto)) { fromto = arrayToObject(fromto); } else if (typeof fromto === 'boolean') { reverse = fromto; converter = noop; fromto = null; } else if (typeof fromto === 'function') { reverse = converter; converter = fromto; fromto = null; } else { fromto = null; } if (typeof converter !== 'function') { if (typeof converter === 'boolean') { reverse = converter; converter = noop; } else { converter = noop; } } if (typeof reverse !== 'boolean') { reverse = false; } if (reverse) { var tmp = src; src = dst; dst = tmp; if (fromto) { fromto = invert(fromto); } } var opts = { dest: dst, fromto: fromto, convert: converter, }; if (fromto) { eachProps(src, copyWithFromto, opts); setParentEmptyObject(dst, fromto); } else { eachProps(src, copyWithoutFromto, opts); } return dst; }; function copyWithFromto(value, keyChain, nodeInfo) { if (isPlainObject(value)) { return; } var dstKeyChains = nodeInfo.fromto[keyChain]; if (!dstKeyChains) { return; } delete nodeInfo.fromto[keyChain]; if (!Array.isArray(dstKeyChains)) { dstKeyChains = [dstKeyChains]; } var srcInfo = { keyChain: keyChain, value: value, key: nodeInfo.name, depth: nodeInfo.depth, parent: nodeInfo.parent, }; for (var i = 0, n = dstKeyChains.length; i < n; i++) { setDeep( nodeInfo.dest, dstKeyChains[i], function (parent, key, depth) { var dstInfo = { keyChain: dstKeyChains[i], value: parent[key], key: key, depth: depth, parent: parent, }; return nodeInfo.convert(srcInfo, dstInfo); } ); } } function copyWithoutFromto(value, keyChain, nodeInfo) { if (isPlainObject(value)) { for (var k in value) { return; } setDeep(nodeInfo.dest, keyChain, newObject); return; } var srcInfo = { keyChain: keyChain, value: value, key: nodeInfo.name, depth: nodeInfo.depth, parent: nodeInfo.parent, }; setDeep(nodeInfo.dest, keyChain, function (parent, key, depth) { var dstInfo = { keyChain: keyChain, value: parent[key], key: key, depth: depth, parent: parent, }; return nodeInfo.convert(srcInfo, dstInfo); }); } function newObject() { return {}; } function noop(srcInfo) { return srcInfo.value; } function onlyValueIsString(obj) { var newObj = {}; for (var key in obj) { var val = obj[key]; if (typeof val === 'string') { newObj[key] = val; } } return newObj; } function arrayToObject(arr) { var obj = {}; for (var i = 0, n = arr.length; i < n; i++) { var elm = arr[i]; if (typeof elm === 'string') { obj[elm] = elm; } } return obj; } function invert(fromto) { var inv = {}; for (var key in fromto) { var val = fromto[key]; if (!inv[val]) { inv[val] = []; } inv[val].push(key); } return inv; } function setDeep(obj, keyChain, valueCreator) { _setDeep(obj, keyChain.split('.'), 1, valueCreator); } function _setDeep(obj, keyElems, depth, valueCreator) { var key = keyElems.shift(); if (isPossibilityOfPrototypePollution(key)) { return; } if (!keyElems.length) { var value = valueCreator(obj, key, depth); if (value === undefined) { return; } if (isPlainObject(value)) { // value is always an empty object. if (isPlainObject(obj[key])) { return; } } obj[key] = value; return; } if (!isPlainObject(obj[key])) { obj[key] = {}; } _setDeep(obj[key], keyElems, depth + 1, valueCreator); } function setParentEmptyObject(obj, fromto) { for (var srcKeyChain in fromto) { var dstKeyChains = fromto[srcKeyChain]; if (!Array.isArray(dstKeyChains)) { dstKeyChains = [dstKeyChains]; } for (var i = 0, n = dstKeyChains.length; i < n; i++) { setDeep(obj, dstKeyChains[i], newUndefined); } } } function newUndefined() { return undefined; } function isObject(v) { return Object.prototype.toString.call(v) === '[object Object]'; } function isPossibilityOfPrototypePollution(key) { return key === '__proto__' || key === 'constructor'; } }, { 'each-props': 4, 'is-plain-object': 8 }, ], 2: [ function (require, module, exports) { /*! * array-each * * Copyright (c) 2015, 2017, Jon Schlinkert. * Released under the MIT License. */ 'use strict'; /** * Loop over each item in an array and call the given function on every element. * * ```js * each(['a', 'b', 'c'], function(ele) { * return ele + ele; * }); * //=> ['aa', 'bb', 'cc'] * * each(['a', 'b', 'c'], function(ele, i) { * return i + ele; * }); * //=> ['0a', '1b', '2c'] * ``` * * @name each * @alias forEach * @param {Array} `array` * @param {Function} `fn` * @param {Object} `thisArg` (optional) pass a `thisArg` to be used as the context in which to call the function. * @return {undefined} * @api public */ module.exports = function each(arr, cb, thisArg) { if (arr == null) return; var len = arr.length; var idx = -1; while (++idx < len) { var ele = arr[idx]; if (cb.call(thisArg, ele, idx, arr) === false) { break; } } }; }, {}, ], 3: [ function (require, module, exports) { /*! * array-slice * * Copyright (c) 2014-2017, Jon Schlinkert. * Released under the MIT License. */ 'use strict'; module.exports = function slice(arr, start, end) { var len = arr.length; var range = []; start = idx(len, start); end = idx(len, end, len); while (start < end) { range.push(arr[start++]); } return range; }; function idx(len, pos, end) { if (pos == null) { pos = end || 0; } else if (pos < 0) { pos = Math.max(len + pos, 0); } else { pos = Math.min(pos, len); } return pos; } }, {}, ], 4: [ function (require, module, exports) { 'use strict'; var isPlainObject = require('is-plain-object'); var defaults = require('object.defaults/immutable'); module.exports = function (obj, fn, opts) { if (!isObject(obj)) { return; } if (typeof fn !== 'function') { return; } if (!isPlainObject(opts)) { opts = {}; } forEachChild(obj, '', fn, 0, opts); }; function forEachChild(node, baseKey, fn, depth, opts) { var keys = Object.keys(node); if (typeof opts.sort === 'function') { var sortedKeys = opts.sort(keys); if (Array.isArray(sortedKeys)) { keys = sortedKeys; } } depth += 1; for (var i = 0, n = keys.length; i < n; i++) { var key = keys[i]; var keyChain = baseKey + '.' + key; var value = node[key]; var nodeInfo = defaults(opts); nodeInfo.name = key; nodeInfo.index = i; nodeInfo.count = n; nodeInfo.depth = depth; nodeInfo.parent = node; var notDigg = fn(value, keyChain.slice(1), nodeInfo); if (notDigg || !isPlainObject(value)) { continue; } forEachChild(value, keyChain, fn, depth, opts); } } function isObject(v) { return Object.prototype.toString.call(v) === '[object Object]'; } }, { 'is-plain-object': 5, 'object.defaults/immutable': 10 }, ], 5: [ function (require, module, exports) { /*! * is-plain-object * * Copyright (c) 2014-2017, Jon Schlinkert. * Released under the MIT License. */ 'use strict'; var isObject = require('isobject'); function isObjectObject(o) { return ( isObject(o) === true && Object.prototype.toString.call(o) === '[object Object]' ); } module.exports = function isPlainObject(o) { var ctor, prot; if (isObjectObject(o) === false) return false; // If has modified constructor ctor = o.constructor; if (typeof ctor !== 'function') return false; // If has modified prototype prot = ctor.prototype; if (isObjectObject(prot) === false) return false; // If constructor does not have an Object-specific method if (prot.hasOwnProperty('isPrototypeOf') === false) { return false; } // Most likely a plain Object return true; }; }, { isobject: 9 }, ], 6: [ function (require, module, exports) { /*! * for-in * * Copyright (c) 2014-2017, Jon Schlinkert. * Released under the MIT License. */ 'use strict'; module.exports = function forIn(obj, fn, thisArg) { for (var key in obj) { if (fn.call(thisArg, obj[key], key, obj) === false) { break; } } }; }, {}, ], 7: [ function (require, module, exports) { /*! * for-own * * Copyright (c) 2014-2017, Jon Schlinkert. * Released under the MIT License. */ 'use strict'; var forIn = require('for-in'); var hasOwn = Object.prototype.hasOwnProperty; module.exports = function forOwn(obj, fn, thisArg) { forIn(obj, function (val, key) { if (hasOwn.call(obj, key)) { return fn.call(thisArg, obj[key], key, obj); } }); }; }, { 'for-in': 6 }, ], 8: [ function (require, module, exports) { 'use strict'; Object.defineProperty(exports, '__esModule', { value: true }); /*! * is-plain-object * * Copyright (c) 2014-2017, Jon Schlinkert. * Released under the MIT License. */ function isObject(o) { return Object.prototype.toString.call(o) === '[object Object]'; } function isPlainObject(o) { var ctor, prot; if (isObject(o) === false) return false; // If has modified constructor ctor = o.constructor; if (ctor === undefined) return true; // If has modified prototype prot = ctor.prototype; if (isObject(prot) === false) return false; // If constructor does not have an Object-specific method if (prot.hasOwnProperty('isPrototypeOf') === false) { return false; } // Most likely a plain Object return true; } exports.isPlainObject = isPlainObject; }, {}, ], 9: [ function (require, module, exports) { /*! * isobject * * Copyright (c) 2014-2017, Jon Schlinkert. * Released under the MIT License. */ 'use strict'; module.exports = function isObject(val) { return ( val != null && typeof val === 'object' && Array.isArray(val) === false ); }; }, {}, ], 10: [ function (require, module, exports) { 'use strict'; var slice = require('array-slice'); var defaults = require('./mutable'); /** * Extends an empty object with properties of one or * more additional `objects` * * @name .defaults.immutable * @param {Object} `objects` * @return {Object} * @api public */ module.exports = function immutableDefaults() { var args = slice(arguments); return defaults.apply(null, [{}].concat(args)); }; }, { './mutable': 11, 'array-slice': 3 }, ], 11: [ function (require, module, exports) { 'use strict'; var each = require('array-each'); var slice = require('array-slice'); var forOwn = require('for-own'); var isObject = require('isobject'); /** * Extends the `target` object with properties of one or * more additional `objects` * * @name .defaults * @param {Object} `target` The target object. Pass an empty object to shallow clone. * @param {Object} `objects` * @return {Object} * @api public */ module.exports = function defaults(target, objects) { if (target == null) { return {}; } each(slice(arguments, 1), function (obj) { if (isObject(obj)) { forOwn(obj, function (val, key) { if (target[key] == null) { target[key] = val; } }); } }); return target; }; }, { 'array-each': 2, 'array-slice': 3, 'for-own': 7, isobject: 9 }, ], }, {}, [1] )(1); }); copy-props-3.0.1/web/copy-props.min.js000066400000000000000000000251601413760552600176530ustar00rootroot00000000000000!(function (t) { 'object' == typeof exports && 'undefined' != typeof module ? (module.exports = t()) : 'function' == typeof define && define.amd ? define([], t) : (('undefined' != typeof window ? window : 'undefined' != typeof global ? global : 'undefined' != typeof self ? self : this ).copyProps = t()); })(function () { return (function e(o, i, u) { function c(n, t) { if (!i[n]) { if (!o[n]) { var r = 'function' == typeof require && require; if (!t && r) return r(n, !0); if (f) return f(n, !0); throw ( (((r = new Error("Cannot find module '" + n + "'")).code = 'MODULE_NOT_FOUND'), r) ); } (r = i[n] = { exports: {} }), o[n][0].call( r.exports, function (t) { return c(o[n][1][t] || t); }, r, r.exports, e, o, i, u ); } return i[n].exports; } for ( var f = 'function' == typeof require && require, t = 0; t < u.length; t++ ) c(u[t]); return c; })( { 1: [ function (t, n, r) { 'use strict'; var i = t('each-props'), c = t('is-plain-object').isPlainObject; function u(t, n, e) { if (!c(t)) { var o = e.fromto[n]; if (o) { delete e.fromto[n], Array.isArray(o) || (o = [o]); for ( var i = { keyChain: n, value: t, key: e.name, depth: e.depth, parent: e.parent, }, u = 0, r = o.length; u < r; u++ ) p(e.dest, o[u], function (t, n, r) { t = { keyChain: o[u], value: t[n], key: n, depth: r, parent: t, }; return e.convert(i, t); }); } } } function f(t, e, o) { if (c(t)) { for (var n in t) return; p(o.dest, e, a); } else { var i = { keyChain: e, value: t, key: o.name, depth: o.depth, parent: o.parent, }; p(o.dest, e, function (t, n, r) { t = { keyChain: e, value: t[n], key: n, depth: r, parent: t }; return o.convert(i, t); }); } } function a() { return {}; } function s(t) { return t.value; } function p(t, n, r) { !(function t(n, r, e, o) { var i = r.shift(); if (v(i)) return; if (!r.length) { var u = o(n, i, e); return void 0 === u ? void 0 : c(u) && c(n[i]) ? void 0 : void (n[i] = u); } c(n[i]) || (n[i] = {}); t(n[i], r, e + 1, o); })(t, n.split('.'), 1, r); } function l() {} function y(t) { return '[object Object]' === Object.prototype.toString.call(t); } function v(t) { return '__proto__' === t || 'constructor' === t; } n.exports = function (t, n, r, e, o) { y(t) || (t = {}), y(n) || (n = {}), (r = c(r) ? (function (t) { var n, r = {}; for (n in t) { var e = t[n]; 'string' == typeof e && (r[n] = e); } return r; })(r) : Array.isArray(r) ? (function (t) { for (var n = {}, r = 0, e = t.length; r < e; r++) { var o = t[r]; 'string' == typeof o && (n[o] = o); } return n; })(r) : ('boolean' == typeof r ? ((o = r), (e = s)) : 'function' == typeof r && ((o = e), (e = r)), null)), 'function' != typeof e && (e = ('boolean' == typeof e && (o = e), s)), (o = 'boolean' != typeof o ? !1 : o) && ((o = t), (t = n), (n = o), (r = r && (function (t) { var n, r = {}; for (n in t) { var e = t[n]; r[e] || (r[e] = []), r[e].push(n); } return r; })(r))); e = { dest: n, fromto: r, convert: e }; return ( r ? (i(t, u, e), (function (t, n) { for (var r in n) { var e = n[r]; Array.isArray(e) || (e = [e]); for (var o = 0, i = e.length; o < i; o++) p(t, e[o], l); } })(n, r)) : i(t, f, e), n ); }; }, { 'each-props': 4, 'is-plain-object': 8 }, ], 2: [ function (t, n, r) { 'use strict'; n.exports = function (t, n, r) { if (null != t) for (var e = t.length, o = -1; ++o < e; ) { var i = t[o]; if (!1 === n.call(r, i, o, t)) break; } }; }, {}, ], 3: [ function (t, n, r) { 'use strict'; function i(t, n, r) { return (n = null == n ? r || 0 : n < 0 ? Math.max(t + n, 0) : Math.min(n, t)); } n.exports = function (t, n, r) { var e = t.length, o = []; for (n = i(e, n), r = i(e, r, e); n < r; ) o.push(t[n++]); return o; }; }, {}, ], 4: [ function (t, n, r) { 'use strict'; var v = t('is-plain-object'), d = t('object.defaults/immutable'); n.exports = function (t, n, r) { '[object Object]' !== Object.prototype.toString.call(t) || ('function' == typeof n && (function t(n, r, e, o, i) { var u = Object.keys(n); { var c; 'function' == typeof i.sort && ((c = i.sort(u)), Array.isArray(c) && (u = c)); } o += 1; for (var f = 0, a = u.length; f < a; f++) { var s = u[f], p = r + '.' + s, l = n[s], y = d(i); (y.name = s), (y.index = f), (y.count = a), (y.depth = o), (y.parent = n); y = e(l, p.slice(1), y); !y && v(l) && t(l, p, e, o, i); } })(t, '', n, 0, (r = !v(r) ? {} : r))); }; }, { 'is-plain-object': 5, 'object.defaults/immutable': 10 }, ], 5: [ function (t, n, r) { 'use strict'; var e = t('isobject'); function o(t) { return ( !0 === e(t) && '[object Object]' === Object.prototype.toString.call(t) ); } n.exports = function (t) { return ( !1 !== o(t) && 'function' == typeof (t = t.constructor) && !1 !== o((t = t.prototype)) && !1 !== t.hasOwnProperty('isPrototypeOf') ); }; }, { isobject: 9 }, ], 6: [ function (t, n, r) { 'use strict'; n.exports = function (t, n, r) { for (var e in t) if (!1 === n.call(r, t[e], e, t)) break; }; }, {}, ], 7: [ function (t, n, r) { 'use strict'; var i = t('for-in'), u = Object.prototype.hasOwnProperty; n.exports = function (r, e, o) { i(r, function (t, n) { if (u.call(r, n)) return e.call(o, r[n], n, r); }); }; }, { 'for-in': 6 }, ], 8: [ function (t, n, r) { 'use strict'; function e(t) { return '[object Object]' === Object.prototype.toString.call(t); } Object.defineProperty(r, '__esModule', { value: !0 }), (r.isPlainObject = function (t) { return ( !1 !== e(t) && (void 0 === (t = t.constructor) || (!1 !== e((t = t.prototype)) && !1 !== t.hasOwnProperty('isPrototypeOf'))) ); }); }, {}, ], 9: [ function (t, n, r) { 'use strict'; n.exports = function (t) { return null != t && 'object' == typeof t && !1 === Array.isArray(t); }; }, {}, ], 10: [ function (t, n, r) { 'use strict'; var e = t('array-slice'), o = t('./mutable'); n.exports = function () { var t = e(arguments); return o.apply(null, [{}].concat(t)); }; }, { './mutable': 11, 'array-slice': 3 }, ], 11: [ function (t, n, r) { 'use strict'; var e = t('array-each'), o = t('array-slice'), i = t('for-own'), u = t('isobject'); n.exports = function (r, t) { return null == r ? {} : (e(o(arguments, 1), function (t) { u(t) && i(t, function (t, n) { null == r[n] && (r[n] = t); }); }), r); }; }, { 'array-each': 2, 'array-slice': 3, 'for-own': 7, isobject: 9 }, ], }, {}, [1] )(1); }); //# sourceMappingURL=copy-props.min.js.map copy-props-3.0.1/web/copy-props.min.js.map000066400000000000000000000175061413760552600204340ustar00rootroot00000000000000{"version":3,"sources":["copy-props.js"],"names":["f","exports","module","define","amd","window","global","self","this","copyProps","r","e","n","t","o","i","c","require","u","a","Error","code","p","call","length","1","eachProps","isPlainObject","copyWithFromto","value","keyChain","nodeInfo","dstKeyChains","fromto","Array","isArray","srcInfo","key","name","depth","parent","setDeep","dest","dstInfo","convert","copyWithoutFromto","k","newObject","noop","obj","valueCreator","_setDeep","keyElems","shift","isPossibilityOfPrototypePollution","undefined","split","newUndefined","isObject","v","Object","prototype","toString","src","dst","converter","reverse","newObj","val","onlyValueIsString","arr","elm","arrayToObject","tmp","inv","push","invert","opts","srcKeyChain","setParentEmptyObject","each-props","is-plain-object","2","cb","thisArg","len","idx","ele","3","pos","end","Math","max","min","start","range","4","defaults","fn","forEachChild","node","baseKey","keys","sortedKeys","sort","index","count","notDigg","slice","object.defaults/immutable","5","isObjectObject","ctor","constructor","prot","hasOwnProperty","isobject","6","7","forIn","hasOwn","for-in","8","defineProperty","9","10","args","arguments","apply","concat","./mutable","array-slice","11","each","forOwn","target","objects","array-each","for-own"],"mappings":"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"}