[Pkg-javascript-commits] [node-pathval] 01/02: New upstream version 1.1.0
Julien Puydt
julien.puydt at laposte.net
Fri Aug 18 12:37:13 UTC 2017
This is an automated email from the git hooks/post-receive script.
jpuydt-guest pushed a commit to branch master
in repository node-pathval.
commit 833371d26114028b3ff45d724c26674ea6c4e60b
Author: Julien Puydt <julien.puydt at laposte.net>
Date: Fri Aug 18 14:19:42 2017 +0200
New upstream version 1.1.0
---
.gitignore | 21 +++++
.npmignore | 4 +
.travis.yml | 37 ++++++++
CHANGELOG.md | 18 ++++
LICENSE | 16 ++++
MAINTAINERS | 5 +
README.md | 145 ++++++++++++++++++++++++++++
index.js | 291 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
karma.conf.js | 96 +++++++++++++++++++
package.json | 78 ++++++++++++++++
test/.eslintrc | 19 ++++
test/index.js | 225 ++++++++++++++++++++++++++++++++++++++++++++
12 files changed, 955 insertions(+)
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..64acddd
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,21 @@
+lib-cov
+*.seed
+*.log
+*.csv
+*.dat
+*.out
+*.pid
+*.gz
+
+pids
+logs
+results
+build
+components
+
+node_modules
+npm-debug.log
+
+coverage/
+
+pathval.js
diff --git a/.npmignore b/.npmignore
new file mode 100644
index 0000000..2ff24ec
--- /dev/null
+++ b/.npmignore
@@ -0,0 +1,4 @@
+test
+examples
+coverage
+*.sock
diff --git a/.travis.yml b/.travis.yml
new file mode 100644
index 0000000..826d840
--- /dev/null
+++ b/.travis.yml
@@ -0,0 +1,37 @@
+sudo: false
+
+language: node_js
+
+addons:
+ sauce_connect: true
+
+cache:
+ directories:
+ - node_modules
+
+node_js:
+ - 0.10 # to be removed 2016-10-01
+ - 0.12 # to be removed 2016-12-31
+ - 4 # to be removed 2018-04-01
+ - 6 # to be removed 2019-04-01
+ - lts/* # safety net; don't remove
+ - node # safety net; don't remove
+
+before_install:
+ - npm i -g npm at latest
+
+script:
+ - npm test
+
+after_success:
+ - 'travis-after-all && npm run semantic-release'
+
+env:
+ global:
+ - SAUCELABS_USERNAME=chaijs-pathval
+ # SAUCELABS_ACCESS_TOKEN
+ - secure: F2/lZDhFRxXOqLY3E5hWDJ00sTCl35AJnbJyFH32CvO5GZvP97qXmAfpgFVthX2xGp8KPXOT+QfUHACGuFXfBkCanXvn/ZLXYf/bt8ub87aZP7kwegE2i3pOBxzaG4qLVI/J6iOkxthguWTnTUpPtp+YvFksMYBIfQ5RG12wa2w=
+ # GH_TOKEN
+ - secure: PiIlToly+q4/51/Q7TMVcedVsY/AWef6uqXpPKDiiccFs7humrddFE7t21bZ3W08VG+s3dvrnM85xr0U3FQ5sGCZtT7te7s/qQ1TGS/PTb8ryxex2XbKWU2AlECNZbXmQzM7r+/lVcevE6t9xUclVZwavZnYPBEM5MSI0feHwxU=
+ # NPM_TOKEN (f005d1e5bce9)
+ - secure: b4OFWDUovFA327YwSfPxcJRUS9O0B7GyM4M96rEUcWtjatBrPnMqgkggn3K63Me6feiW1yi/sYKc8ovwmCNlm9QdI3s8i0AgAAaW2ZrctjNWX2uZSVukyLyNwpOxI92kV4CmQySsahs3ZCGPCRk8kdNM32z+qT4hvUhzcHYjRDg=
diff --git a/CHANGELOG.md b/CHANGELOG.md
new file mode 100644
index 0000000..804de5e
--- /dev/null
+++ b/CHANGELOG.md
@@ -0,0 +1,18 @@
+
+0.1.1 / 2013-12-30
+==================
+
+ * expose parse
+ * rename lib to index
+
+0.1.0 / 2013-12-28
+==================
+
+ * API BREAKING! `get` has been changed, see the README for migration path
+ * Add `set` method
+ * Start using simple-assert (closes #2)
+
+0.0.1 / 2013-11-24
+==================
+
+ * Initial implementation
diff --git a/LICENSE b/LICENSE
new file mode 100644
index 0000000..90d22da
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,16 @@
+MIT License
+
+Copyright (c) 2011-2013 Jake Luer jake at alogicalparadox.com
+
+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.
diff --git a/MAINTAINERS b/MAINTAINERS
new file mode 100644
index 0000000..46e56a4
--- /dev/null
+++ b/MAINTAINERS
@@ -0,0 +1,5 @@
+keithamus
+davelosert
+lucasfcosta
+meeber
+vesln
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..01abfd8
--- /dev/null
+++ b/README.md
@@ -0,0 +1,145 @@
+<h1 align=center>
+ <a href="http://chaijs.com" title="Chai Documentation">
+ <img alt="ChaiJS" src="http://chaijs.com/img/chai-logo.png"/> pathval
+ </a>
+</h1>
+
+<p align=center>
+ Tool for Object value retrieval given a string path for <a href="http://nodejs.org">node</a> and the browser.
+</p>
+
+<p align=center>
+ <a href="./LICENSE">
+ <img
+ alt="license:mit"
+ src="https://img.shields.io/badge/license-mit-green.svg?style=flat-square"
+ />
+ </a>
+ <a href="https://github.com/chaijs/pathval/releases">
+ <img
+ alt="tag:?"
+ src="https://img.shields.io/github/tag/chaijs/pathval.svg?style=flat-square"
+ />
+ </a>
+ <a href="https://travis-ci.org/chaijs/pathval">
+ <img
+ alt="build:?"
+ src="https://img.shields.io/travis/chaijs/pathval/master.svg?style=flat-square"
+ />
+ </a>
+ <a href="https://coveralls.io/r/chaijs/pathval">
+ <img
+ alt="coverage:?"
+ src="https://img.shields.io/coveralls/chaijs/pathval/master.svg?style=flat-square"
+ />
+ </a>
+ <a href="https://www.npmjs.com/packages/pathval">
+ <img
+ alt="npm:?"
+ src="https://img.shields.io/npm/v/pathval.svg?style=flat-square"
+ />
+ </a>
+ <a href="https://www.npmjs.com/packages/pathval">
+ <img
+ alt="dependencies:?"
+ src="https://img.shields.io/npm/dm/pathval.svg?style=flat-square"
+ />
+ </a>
+ <a href="">
+ <img
+ alt="devDependencies:?"
+ src="https://img.shields.io/david/chaijs/pathval.svg?style=flat-square"
+ />
+ </a>
+ <br/>
+ <a href="https://saucelabs.com/u/chaijs-pathval">
+ <img
+ alt="Selenium Test Status"
+ src="https://saucelabs.com/browser-matrix/chaijs-pathval.svg"
+ />
+ </a>
+ <br>
+ <a href="https://chai-slack.herokuapp.com/">
+ <img
+ alt="Join the Slack chat"
+ src="https://img.shields.io/badge/slack-join%20chat-E2206F.svg?style=flat-square"
+ />
+ </a>
+ <a href="https://gitter.im/chaijs/chai">
+ <img
+ alt="Join the Gitter chat"
+ src="https://img.shields.io/badge/gitter-join%20chat-D0104D.svg?style=flat-square"
+ />
+ </a>
+</p>
+
+## What is pathval?
+
+Pathval is a module which you can use to retrieve or set an Object's property for a given `String` path.
+
+## Installation
+
+### Node.js
+
+`pathval` is available on [npm](http://npmjs.org). To install it, type:
+
+ $ npm install pathval
+
+### Browsers
+
+You can also use it within the browser; install via npm and use the `pathval.js` file found within the download. For example:
+
+```html
+<script src="./node_modules/pathval/pathval.js"></script>
+```
+
+## Usage
+
+The primary export of `pathval` is an object which has the following methods:
+
+* `hasProperty(object, name)` - Checks whether an `object` has `name`d property or numeric array index.
+* `getPathInfo(object, path)` - Returns an object with info indicating the value of the `parent` of that path, the `name ` of the property we're retrieving and its `value`.
+* `getPathValue(object, path)` - Retrieves the value of a property at a given `path` inside an `object`'.
+* `setPathValue(object, path, value)` - Sets the `value` of a property at a given `path` inside an `object`'.
+
+```js
+var pathval = require('pathval');
+```
+
+#### .hasProperty(object, name)
+
+```js
+var pathval = require('pathval');
+
+var obj = { prop: 'a value' };
+pathval.hasProperty(obj, 'prop'); // true
+```
+
+#### .getPathInfo(object, path)
+
+```js
+var pathval = require('pathval');
+
+var obj = { earth: { country: 'Brazil' } };
+pathval.getPathInfo(obj, 'earth.country'); // { parent: { country: 'Brazil' }, name: 'country', value: 'Brazil', exists: true }
+```
+
+#### .getPathValue(object, path)
+
+```js
+var pathval = require('pathval');
+
+var obj = { earth: { country: 'Brazil' } };
+pathval.getPathValue(obj, 'earth.country'); // 'Brazil'
+```
+
+#### .setPathValue(object, path, value)
+
+```js
+var pathval = require('pathval');
+
+var obj = { earth: { country: 'Brazil' } };
+pathval.setPathValue(obj, 'earth.country', 'USA');
+
+obj.earth.country; // 'USA'
+```
diff --git a/index.js b/index.js
new file mode 100644
index 0000000..1ec2148
--- /dev/null
+++ b/index.js
@@ -0,0 +1,291 @@
+'use strict';
+
+/* !
+ * Chai - pathval utility
+ * Copyright(c) 2012-2014 Jake Luer <jake at alogicalparadox.com>
+ * @see https://github.com/logicalparadox/filtr
+ * MIT Licensed
+ */
+
+/**
+ * ### .hasProperty(object, name)
+ *
+ * This allows checking whether an object has own
+ * or inherited from prototype chain named property.
+ *
+ * Basically does the same thing as the `in`
+ * operator but works properly with null/undefined values
+ * and other primitives.
+ *
+ * var obj = {
+ * arr: ['a', 'b', 'c']
+ * , str: 'Hello'
+ * }
+ *
+ * The following would be the results.
+ *
+ * hasProperty(obj, 'str'); // true
+ * hasProperty(obj, 'constructor'); // true
+ * hasProperty(obj, 'bar'); // false
+ *
+ * hasProperty(obj.str, 'length'); // true
+ * hasProperty(obj.str, 1); // true
+ * hasProperty(obj.str, 5); // false
+ *
+ * hasProperty(obj.arr, 'length'); // true
+ * hasProperty(obj.arr, 2); // true
+ * hasProperty(obj.arr, 3); // false
+ *
+ * @param {Object} object
+ * @param {String|Symbol} name
+ * @returns {Boolean} whether it exists
+ * @namespace Utils
+ * @name hasProperty
+ * @api public
+ */
+
+function hasProperty(obj, name) {
+ if (typeof obj === 'undefined' || obj === null) {
+ return false;
+ }
+
+ // The `in` operator does not work with primitives.
+ return name in Object(obj);
+}
+
+/* !
+ * ## parsePath(path)
+ *
+ * Helper function used to parse string object
+ * paths. Use in conjunction with `internalGetPathValue`.
+ *
+ * var parsed = parsePath('myobject.property.subprop');
+ *
+ * ### Paths:
+ *
+ * * Can be infinitely deep and nested.
+ * * Arrays are also valid using the formal `myobject.document[3].property`.
+ * * Literal dots and brackets (not delimiter) must be backslash-escaped.
+ *
+ * @param {String} path
+ * @returns {Object} parsed
+ * @api private
+ */
+
+function parsePath(path) {
+ var str = path.replace(/([^\\])\[/g, '$1.[');
+ var parts = str.match(/(\\\.|[^.]+?)+/g);
+ return parts.map(function mapMatches(value) {
+ var regexp = /^\[(\d+)\]$/;
+ var mArr = regexp.exec(value);
+ var parsed = null;
+ if (mArr) {
+ parsed = { i: parseFloat(mArr[1]) };
+ } else {
+ parsed = { p: value.replace(/\\([.\[\]])/g, '$1') };
+ }
+
+ return parsed;
+ });
+}
+
+/* !
+ * ## internalGetPathValue(obj, parsed[, pathDepth])
+ *
+ * Helper companion function for `.parsePath` that returns
+ * the value located at the parsed address.
+ *
+ * var value = getPathValue(obj, parsed);
+ *
+ * @param {Object} object to search against
+ * @param {Object} parsed definition from `parsePath`.
+ * @param {Number} depth (nesting level) of the property we want to retrieve
+ * @returns {Object|Undefined} value
+ * @api private
+ */
+
+function internalGetPathValue(obj, parsed, pathDepth) {
+ var temporaryValue = obj;
+ var res = null;
+ pathDepth = (typeof pathDepth === 'undefined' ? parsed.length : pathDepth);
+
+ for (var i = 0; i < pathDepth; i++) {
+ var part = parsed[i];
+ if (temporaryValue) {
+ if (typeof part.p === 'undefined') {
+ temporaryValue = temporaryValue[part.i];
+ } else {
+ temporaryValue = temporaryValue[part.p];
+ }
+
+ if (i === (pathDepth - 1)) {
+ res = temporaryValue;
+ }
+ }
+ }
+
+ return res;
+}
+
+/* !
+ * ## internalSetPathValue(obj, value, parsed)
+ *
+ * Companion function for `parsePath` that sets
+ * the value located at a parsed address.
+ *
+ * internalSetPathValue(obj, 'value', parsed);
+ *
+ * @param {Object} object to search and define on
+ * @param {*} value to use upon set
+ * @param {Object} parsed definition from `parsePath`
+ * @api private
+ */
+
+function internalSetPathValue(obj, val, parsed) {
+ var tempObj = obj;
+ var pathDepth = parsed.length;
+ var part = null;
+ // Here we iterate through every part of the path
+ for (var i = 0; i < pathDepth; i++) {
+ var propName = null;
+ var propVal = null;
+ part = parsed[i];
+
+ // If it's the last part of the path, we set the 'propName' value with the property name
+ if (i === (pathDepth - 1)) {
+ propName = typeof part.p === 'undefined' ? part.i : part.p;
+ // Now we set the property with the name held by 'propName' on object with the desired val
+ tempObj[propName] = val;
+ } else if (typeof part.p !== 'undefined' && tempObj[part.p]) {
+ tempObj = tempObj[part.p];
+ } else if (typeof part.i !== 'undefined' && tempObj[part.i]) {
+ tempObj = tempObj[part.i];
+ } else {
+ // If the obj doesn't have the property we create one with that name to define it
+ var next = parsed[i + 1];
+ // Here we set the name of the property which will be defined
+ propName = typeof part.p === 'undefined' ? part.i : part.p;
+ // Here we decide if this property will be an array or a new object
+ propVal = typeof next.p === 'undefined' ? [] : {};
+ tempObj[propName] = propVal;
+ tempObj = tempObj[propName];
+ }
+ }
+}
+
+/**
+ * ### .getPathInfo(object, path)
+ *
+ * This allows the retrieval of property info in an
+ * object given a string path.
+ *
+ * The path info consists of an object with the
+ * following properties:
+ *
+ * * parent - The parent object of the property referenced by `path`
+ * * name - The name of the final property, a number if it was an array indexer
+ * * value - The value of the property, if it exists, otherwise `undefined`
+ * * exists - Whether the property exists or not
+ *
+ * @param {Object} object
+ * @param {String} path
+ * @returns {Object} info
+ * @namespace Utils
+ * @name getPathInfo
+ * @api public
+ */
+
+function getPathInfo(obj, path) {
+ var parsed = parsePath(path);
+ var last = parsed[parsed.length - 1];
+ var info = {
+ parent: parsed.length > 1 ? internalGetPathValue(obj, parsed, parsed.length - 1) : obj,
+ name: last.p || last.i,
+ value: internalGetPathValue(obj, parsed),
+ };
+ info.exists = hasProperty(info.parent, info.name);
+
+ return info;
+}
+
+/**
+ * ### .getPathValue(object, path)
+ *
+ * This allows the retrieval of values in an
+ * object given a string path.
+ *
+ * var obj = {
+ * prop1: {
+ * arr: ['a', 'b', 'c']
+ * , str: 'Hello'
+ * }
+ * , prop2: {
+ * arr: [ { nested: 'Universe' } ]
+ * , str: 'Hello again!'
+ * }
+ * }
+ *
+ * The following would be the results.
+ *
+ * getPathValue(obj, 'prop1.str'); // Hello
+ * getPathValue(obj, 'prop1.att[2]'); // b
+ * getPathValue(obj, 'prop2.arr[0].nested'); // Universe
+ *
+ * @param {Object} object
+ * @param {String} path
+ * @returns {Object} value or `undefined`
+ * @namespace Utils
+ * @name getPathValue
+ * @api public
+ */
+
+function getPathValue(obj, path) {
+ var info = getPathInfo(obj, path);
+ return info.value;
+}
+
+/**
+ * ### .setPathValue(object, path, value)
+ *
+ * Define the value in an object at a given string path.
+ *
+ * ```js
+ * var obj = {
+ * prop1: {
+ * arr: ['a', 'b', 'c']
+ * , str: 'Hello'
+ * }
+ * , prop2: {
+ * arr: [ { nested: 'Universe' } ]
+ * , str: 'Hello again!'
+ * }
+ * };
+ * ```
+ *
+ * The following would be acceptable.
+ *
+ * ```js
+ * var properties = require('tea-properties');
+ * properties.set(obj, 'prop1.str', 'Hello Universe!');
+ * properties.set(obj, 'prop1.arr[2]', 'B');
+ * properties.set(obj, 'prop2.arr[0].nested.value', { hello: 'universe' });
+ * ```
+ *
+ * @param {Object} object
+ * @param {String} path
+ * @param {Mixed} value
+ * @api private
+ */
+
+function setPathValue(obj, path, val) {
+ var parsed = parsePath(path);
+ internalSetPathValue(obj, val, parsed);
+ return obj;
+}
+
+module.exports = {
+ hasProperty: hasProperty,
+ getPathInfo: getPathInfo,
+ getPathValue: getPathValue,
+ setPathValue: setPathValue,
+};
diff --git a/karma.conf.js b/karma.conf.js
new file mode 100644
index 0000000..7ea23e2
--- /dev/null
+++ b/karma.conf.js
@@ -0,0 +1,96 @@
+'use strict';
+var packageJson = require('./package.json');
+var defaultTimeout = 120000;
+var browserifyIstanbul = require('browserify-istanbul');
+module.exports = function configureKarma(config) {
+ var localBrowsers = [
+ 'PhantomJS',
+ ];
+ var sauceLabsBrowsers = {
+ SauceChromeLatest: {
+ base: 'SauceLabs',
+ browserName: 'Chrome',
+ },
+ SauceFirefoxLatest: {
+ base: 'SauceLabs',
+ browserName: 'Firefox',
+ },
+ SauceSafariLatest: {
+ base: 'SauceLabs',
+ browserName: 'Safari',
+ platform: 'OS X 10.11',
+ },
+ SauceInternetExplorerLatest: {
+ base: 'SauceLabs',
+ browserName: 'Internet Explorer',
+ },
+ SauceInternetExplorerOldestSupported: {
+ base: 'SauceLabs',
+ browserName: 'Internet Explorer',
+ version: 9,
+ },
+ SauceEdgeLatest: {
+ base: 'SauceLabs',
+ browserName: 'MicrosoftEdge',
+ },
+ SauceAndroidLatest: {
+ base: 'SauceLabs',
+ browserName: 'Android',
+ },
+ };
+ config.set({
+ basePath: '',
+ browsers: localBrowsers,
+ logLevel: process.env.npm_config_debug ? config.LOG_DEBUG : config.LOG_INFO,
+ frameworks: [ 'browserify', 'mocha' ],
+ files: [ 'test/*.js' ],
+ exclude: [],
+ preprocessors: {
+ 'test/*.js': [ 'browserify' ],
+ },
+ browserify: {
+ debug: true,
+ bare: true,
+ transform: [
+ browserifyIstanbul({ ignore: [ '**/node_modules/**', '**/test/**' ] }),
+ ],
+ },
+ reporters: [ 'progress', 'coverage' ],
+ coverageReporter: {
+ type: 'lcov',
+ dir: 'coverage',
+ },
+ port: 9876,
+ colors: true,
+ concurrency: 3,
+ autoWatch: false,
+ captureTimeout: defaultTimeout,
+ browserDisconnectTimeout: defaultTimeout,
+ browserNoActivityTimeout: defaultTimeout,
+ singleRun: true,
+ });
+
+ if (process.env.SAUCE_ACCESS_KEY && process.env.SAUCE_USERNAME) {
+ var branch = process.env.TRAVIS_BRANCH || 'local';
+ var build = 'localbuild';
+ if (process.env.TRAVIS_JOB_NUMBER) {
+ build = 'travis@' + process.env.TRAVIS_JOB_NUMBER;
+ }
+ config.reporters.push('saucelabs');
+ config.set({
+ customLaunchers: sauceLabsBrowsers,
+ browsers: localBrowsers.concat(Object.keys(sauceLabsBrowsers)),
+ sauceLabs: {
+ testName: packageJson.name,
+ tunnelIdentifier: process.env.TRAVIS_JOB_NUMBER || new Date().getTime(),
+ recordVideo: true,
+ startConnect: ('TRAVIS' in process.env) === false,
+ tags: [
+ 'pathval_' + packageJson.version,
+ process.env.SAUCE_USERNAME + '@' + branch,
+ build,
+ ],
+ },
+ });
+ }
+};
diff --git a/package.json b/package.json
new file mode 100644
index 0000000..c0f7b67
--- /dev/null
+++ b/package.json
@@ -0,0 +1,78 @@
+{
+ "name": "pathval",
+ "description": "Object value retrieval given a string path",
+ "homepage": "https://github.com/chaijs/pathval",
+ "keywords": [
+ "pathval",
+ "value retrieval",
+ "chai util"
+ ],
+ "license": "MIT",
+ "author": "Veselin Todorov <hi at vesln.com>",
+ "files": [
+ "index.js",
+ "pathval.js"
+ ],
+ "main": "./index.js",
+ "repository": {
+ "type": "git",
+ "url": "git+ssh://git@github.com/chaijs/pathval.git"
+ },
+ "scripts": {
+ "build": "browserify --bare $npm_package_main --standalone pathval -o pathval.js",
+ "lint": "eslint --ignore-path .gitignore .",
+ "prepublish": "npm run build",
+ "semantic-release": "semantic-release pre && npm publish && semantic-release post",
+ "pretest": "npm run lint",
+ "test": "npm run test:node && npm run test:browser && npm run upload-coverage",
+ "test:browser": "karma start --singleRun=true",
+ "test:node": "istanbul cover _mocha",
+ "upload-coverage": "lcov-result-merger 'coverage/**/lcov.info' | coveralls; exit 0"
+ },
+ "config": {
+ "ghooks": {
+ "commit-msg": "validate-commit-msg"
+ }
+ },
+ "eslintConfig": {
+ "extends": [
+ "strict/es5"
+ ],
+ "env": {
+ "es6": true
+ },
+ "globals": {
+ "HTMLElement": false
+ },
+ "rules": {
+ "complexity": 0,
+ "max-statements": 0
+ }
+ },
+ "devDependencies": {
+ "browserify": "^13.0.0",
+ "browserify-istanbul": "^1.0.0",
+ "coveralls": "2.11.9",
+ "eslint": "^2.4.0",
+ "eslint-config-strict": "^8.5.0",
+ "eslint-plugin-filenames": "^0.2.0",
+ "ghooks": "^1.0.1",
+ "istanbul": "^0.4.2",
+ "karma": "^0.13.22",
+ "karma-browserify": "^5.0.2",
+ "karma-coverage": "^0.5.5",
+ "karma-mocha": "^0.2.2",
+ "karma-phantomjs-launcher": "^1.0.0",
+ "karma-sauce-launcher": "^0.3.1",
+ "lcov-result-merger": "^1.0.2",
+ "mocha": "^3.1.2",
+ "phantomjs-prebuilt": "^2.1.5",
+ "semantic-release": "^4.3.5",
+ "simple-assert": "^1.0.0",
+ "travis-after-all": "^1.4.4",
+ "validate-commit-msg": "^2.3.1"
+ },
+ "engines": {
+ "node": "*"
+ }
+}
diff --git a/test/.eslintrc b/test/.eslintrc
new file mode 100644
index 0000000..edffc56
--- /dev/null
+++ b/test/.eslintrc
@@ -0,0 +1,19 @@
+{
+ "extends": [ "strict/test" ],
+ "env": {
+ "node": true,
+ "browser": true,
+ "es6": true,
+ "mocha": true
+ },
+ "rules": {
+ "no-new-wrappers": 0,
+ "no-array-constructor": 0,
+ "no-new-object": 0,
+ "no-empty-function": 0,
+ "no-undefined": 0,
+ "complexity": 0,
+ "max-statements": 0,
+ "id-match": 0
+ }
+}
diff --git a/test/index.js b/test/index.js
new file mode 100644
index 0000000..ce0885c
--- /dev/null
+++ b/test/index.js
@@ -0,0 +1,225 @@
+'use strict';
+
+var assert = require('simple-assert');
+var pathval = require('..');
+describe('hasProperty', function () {
+ it('should handle array index', function () {
+ var arr = [ 1, 2, 'cheeseburger' ];
+ assert(pathval.hasProperty(arr, 1) === true);
+ assert(pathval.hasProperty(arr, 3) === false);
+ });
+
+ it('should handle primitives', function () {
+ var exampleString = 'string literal';
+ assert(pathval.hasProperty(exampleString, 'length') === true);
+ assert(pathval.hasProperty(exampleString, 3) === true);
+ assert(pathval.hasProperty(exampleString, 14) === false);
+
+ assert(pathval.hasProperty(1, 'foo') === false);
+ assert(pathval.hasProperty(false, 'bar') === false);
+ assert(pathval.hasProperty(true, 'toString') === true);
+
+ if (typeof Symbol === 'function') {
+ assert(pathval.hasProperty(Symbol(), 1) === false);
+ assert(pathval.hasProperty(Symbol.iterator, 'valueOf') === true);
+ }
+ });
+
+ it('should handle objects', function () {
+ var exampleObj = {
+ foo: 'bar',
+ };
+ assert(pathval.hasProperty(exampleObj, 'foo') === true);
+ assert(pathval.hasProperty(exampleObj, 'baz') === false);
+ assert(pathval.hasProperty(exampleObj, 0) === false);
+ });
+
+ it('should handle undefined', function () {
+ assert(pathval.hasProperty(undefined, 'foo') === false);
+ });
+
+ it('should handle null', function () {
+ assert(pathval.hasProperty(null, 'foo') === false);
+ });
+});
+
+describe('getPathInfo', function () {
+ var obj = {
+ id: '10702S300W',
+ primes: [ 2, 3, 5, 7, 11 ],
+ dimensions: {
+ units: 'mm',
+ lengths: [ [ 1.2, 3.5 ], [ 2.2, 1.5 ], [ 5, 7 ] ],
+ },
+ 'dimensions.lengths': {
+ '[2]': [ 1.2, 3.5 ],
+ },
+ };
+ var gpi = pathval.getPathInfo;
+ it('should handle simple property', function () {
+ var info = gpi(obj, 'dimensions.units');
+ assert(info.parent === obj.dimensions);
+ assert(info.value === obj.dimensions.units);
+ assert(info.name === 'units');
+ assert(info.exists === true);
+ });
+
+ it('should handle non-existent property', function () {
+ var info = gpi(obj, 'dimensions.size');
+ assert(info.parent === obj.dimensions);
+ assert(info.value === undefined);
+ assert(info.name === 'size');
+ assert(info.exists === false);
+ });
+
+ it('should handle array index', function () {
+ var info = gpi(obj, 'primes[2]');
+ assert(info.parent === obj.primes);
+ assert(info.value === obj.primes[2]);
+ assert(info.name === 2);
+ assert(info.exists === true);
+ });
+
+ it('should handle dimensional array', function () {
+ var info = gpi(obj, 'dimensions.lengths[2][1]');
+ assert(info.parent === obj.dimensions.lengths[2]);
+ assert(info.value === obj.dimensions.lengths[2][1]);
+ assert(info.name === 1);
+ assert(info.exists === true);
+ });
+
+ it('should handle out of bounds array index', function () {
+ var info = gpi(obj, 'dimensions.lengths[3]');
+ assert(info.parent === obj.dimensions.lengths);
+ assert(info.value === undefined);
+ assert(info.name === 3);
+ assert(info.exists === false);
+ });
+
+ it('should handle out of bounds dimensional array index', function () {
+ var info = gpi(obj, 'dimensions.lengths[2][5]');
+ assert(info.parent === obj.dimensions.lengths[2]);
+ assert(info.value === undefined);
+ assert(info.name === 5);
+ assert(info.exists === false);
+ });
+
+ it('should handle backslash-escaping for .[]', function () {
+ var info = gpi(obj, 'dimensions\\.lengths.\\[2\\][1]');
+ assert(info.parent === obj['dimensions.lengths']['[2]']);
+ assert(info.value === obj['dimensions.lengths']['[2]'][1]);
+ assert(info.name === 1);
+ assert(info.exists === true);
+ });
+});
+
+describe('getPathValue', function () {
+ it('returns the correct value', function () {
+ var object = {
+ hello: 'universe',
+ universe: {
+ hello: 'world',
+ },
+ world: [ 'hello', 'universe' ],
+ complex: [
+ { hello: 'universe' },
+ { universe: 'world' },
+ [ { hello: 'world' } ],
+ ],
+ };
+
+ var arr = [ [ true ] ];
+ assert(pathval.getPathValue(object, 'hello') === 'universe');
+ assert(pathval.getPathValue(object, 'universe.hello') === 'world');
+ assert(pathval.getPathValue(object, 'world[1]') === 'universe');
+ assert(pathval.getPathValue(object, 'complex[1].universe') === 'world');
+ assert(pathval.getPathValue(object, 'complex[2][0].hello') === 'world');
+ assert(pathval.getPathValue(arr, '[0][0]') === true);
+ });
+
+ it('handles undefined objects and properties', function () {
+ var object = {};
+ assert(pathval.getPathValue(undefined, 'this.should.work') === null);
+ assert(pathval.getPathValue(object, 'this.should.work') === null);
+ assert(pathval.getPathValue('word', 'length') === 4);
+ });
+});
+
+describe('setPathValue', function () {
+ it('allows value to be set in simple object', function () {
+ var obj = {};
+ pathval.setPathValue(obj, 'hello', 'universe');
+ assert(obj.hello === 'universe');
+ });
+
+ it('allows nested object value to be set', function () {
+ var obj = {};
+ pathval.setPathValue(obj, 'hello.universe', 'properties');
+ assert(obj.hello.universe === 'properties');
+ });
+
+ it('allows nested array value to be set', function () {
+ var obj = {};
+ pathval.setPathValue(obj, 'hello.universe[1].properties', 'galaxy');
+ assert(obj.hello.universe[1].properties === 'galaxy');
+ });
+
+ it('allows value to be REset in simple object', function () {
+ var obj = { hello: 'world' };
+ pathval.setPathValue(obj, 'hello', 'universe');
+ assert(obj.hello === 'universe');
+ });
+
+ it('allows value to be set in complex object', function () {
+ var obj = { hello: { } };
+ pathval.setPathValue(obj, 'hello.universe', 42);
+ assert(obj.hello.universe === 42);
+ });
+
+ it('allows value to be REset in complex object', function () {
+ var obj = { hello: { universe: 100 } };
+ pathval.setPathValue(obj, 'hello.universe', 42);
+ assert(obj.hello.universe === 42);
+ });
+
+ it('allows for value to be set in array', function () {
+ var obj = { hello: [] };
+ pathval.setPathValue(obj, 'hello[0]', 1);
+ pathval.setPathValue(obj, 'hello[2]', 3);
+
+ assert(obj.hello[0] === 1);
+ assert(obj.hello[1] === undefined);
+ assert(obj.hello[2] === 3);
+ });
+
+ it('allows setting a value into an object inside an array', function () {
+ var obj = { hello: [ { anObject: 'obj' } ] };
+ pathval.setPathValue(obj, 'hello[0].anotherKey', 'anotherValue');
+
+ assert(obj.hello[0].anotherKey === 'anotherValue');
+ });
+
+ it('allows for value to be REset in array', function () {
+ var obj = { hello: [ 1, 2, 4 ] };
+ pathval.setPathValue(obj, 'hello[2]', 3);
+
+ assert(obj.hello[0] === 1);
+ assert(obj.hello[1] === 2);
+ assert(obj.hello[2] === 3);
+ });
+
+ it('allows for value to be REset in array', function () {
+ var obj = { hello: [ 1, 2, 4 ] };
+ pathval.setPathValue(obj, 'hello[2]', 3);
+
+ assert(obj.hello[0] === 1);
+ assert(obj.hello[1] === 2);
+ assert(obj.hello[2] === 3);
+ });
+
+ it('returns the object in which the value was set', function () {
+ var obj = { hello: [ 1, 2, 4 ] };
+ var valueReturned = pathval.setPathValue(obj, 'hello[2]', 3);
+ assert(obj === valueReturned);
+ });
+});
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-javascript/node-pathval.git
More information about the Pkg-javascript-commits
mailing list