diff --git a/.editorconfig b/.editorconfig new file mode 100644 index 0000000..ad211fb --- /dev/null +++ b/.editorconfig @@ -0,0 +1,15 @@ +root = true + +[*] +indent_style = space +indent_size = 4 +end_of_line = lf +charset = utf-8 +trim_trailing_whitespace = true +insert_final_newline = true + +[*.{json,remarkrc,eslintrc,sh}] +indent_size = 2 + +[*.md] +trim_trailing_whitespace = false diff --git a/.eslintignore b/.eslintignore new file mode 100644 index 0000000..05126b7 --- /dev/null +++ b/.eslintignore @@ -0,0 +1,4 @@ +coverage/ +example.js +space-separated-tokens.js +space-separated-tokens.min.js diff --git a/.eslintrc b/.eslintrc new file mode 100644 index 0000000..4426f37 --- /dev/null +++ b/.eslintrc @@ -0,0 +1,6 @@ +{ + "extends": "eslint:recommended", + "rules": { + "quotes": [2, "single"] + } +} diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..76e8b21 --- /dev/null +++ b/.gitignore @@ -0,0 +1,6 @@ +.DS_Store +*.log +coverage/ +node_modules/ +space-separated-tokens.js +space-separated-tokens.min.js diff --git a/.jscs.json b/.jscs.json new file mode 100644 index 0000000..1d7f4c2 --- /dev/null +++ b/.jscs.json @@ -0,0 +1,35 @@ +{ + "excludeFiles": [ + "coverage/", + "node_modules/", + "space-separated-tokens.js", + "space-separated-tokens.min.js" + ], + "preset": "yandex", + "requireQuotedKeysInObjects": true, + "disallowQuotedKeysInObjects": false, + "maximumLineLength": { + "value": 79, + "allExcept": [ + "regex", + "urlComments" + ] + }, + "jsDoc": { + "checkAnnotations": "jsdoc3", + "checkParamExistence": true, + "checkParamNames": true, + "checkRedundantAccess": true, + "checkRedundantParams": true, + "checkRedundantReturns": true, + "checkReturnTypes": true, + "checkTypes": "strictNativeCase", + "enforceExistence": true, + "requireHyphenBeforeDescription": true, + "requireNewlineAfterDescription": true, + "requireParamDescription": true, + "requireParamTypes": true, + "requireReturnDescription": true, + "requireReturnTypes": true + } +} diff --git a/.remarkrc b/.remarkrc new file mode 100644 index 0000000..ddb54b6 --- /dev/null +++ b/.remarkrc @@ -0,0 +1,13 @@ +{ + "output": true, + "plugins": [ + "lint", + "github", + "comment-config", + "usage", + "validate-links" + ], + "settings": { + "bullet": "*" + } +} diff --git a/.travis.yml b/.travis.yml new file mode 100644 index 0000000..739a565 --- /dev/null +++ b/.travis.yml @@ -0,0 +1,25 @@ +language: node_js +node_js: +- '0.10' +- '0.11' +- '0.12' +- '4.0' +- '5.0' +sudo: false +after_script: npm install codecov.io && cat ./coverage/lcov.info | codecov +deploy: + - provider: npm + email: tituswormer@gmail.com + api_key: + secure: Fmjc44swIvN12fiN++d+Rxdx3osdeI1d20ZrGbO9Pho4dKqAPpUasXOjb8kF9n0+6/9ZBbvORKxtcAvVn2i6m9zg47GEeGJGaiIjx8++ZDPW4WAyB5avoXawUmmKhR0pVGlJb91oo0EFlEAi2ePxquvxjeLPdfj3Jxbx0dPAOHxi4RUQh9YzQnrp0XxmH539lF/qHU/SPMiexyPkWCIaC+gnrxL4O8NZjUVMP2fRJNTz2JNjkyikrCGSBY9xs0uIJL5/IREjhOpUgzsoC5H4LZJtAu/HhZNC6jrkZEmrhjIlBUHStvo2ldcRX0kWSmEsFkioBcACxkHN69nZDQfia0fmF1nY3xWwcBg5OkBaEWo7QdTFCF9d2QLSk1nCEpgx1lzvMa9IT6SrT2wjkFiqLZZx3hyUwtOfTF2c4M/+CDO10RkAmZM4CGAeiBEKxVf/aM9GLrMnQDXDP2d/GcC4LccQM4XncMxqRXZKBdq6fUeglXdddP5HBzNCj1KK+QILmflgpMKRc0s9xPkZ53wKf4eswWZrJVu7suYuh/odQ1iW8Ssf3wdpVA6z8KORgsms/1QKA885Pm7jwUzJJFxeHcyABpHbvUt9AwsC00aIOULN8BojEKeauKDUfeOgioLw5XnRJ84ngZDCk0mf0kGHdN7uk7OrWKzsNG0k726cZ0A= + on: + tags: true + node: '5.0' + - provider: releases + api_key: + secure: gNF8ehUWqki0QZ2ZTIWHXcWcWtNFwr2+v2XhDTRt30tyM3QF3FYpoutnAkJa97XP4O/d0mB7UWu7MRlc8xzyS6MpyS0hgpbalk5q++lKQCpGkz0kPjyP4GUX8fYxIlTQwaMhU15BX8HKHHZSx8f/ufq3oH2wb4VZzqneHFnBOINVBZwvoEZBKcq2J+1G8WSQlFOz5I5NrWOgfoOOgLLmjFq2KfqK0wdg5IkBP4RvzJ4mRa+XJQKsXTC1Jwf/RwZLm+7yOSCs76CkPr6dD4T4VPsj7NVa3VjA/WQb7b94/1Ajzngpx8srtMUcFDQNGDMEeHUQWO93uEwyboik7mZXmbqvRIRBg5FWkFbQkfRHOHSgcC/FPMH1Iooupa9cH0x+YbqRj8SbA0vJQNn+OiuEQsMZWz96aShK3jZx6g61NN4EbjO3PtZ2wQKJLfJkDx11pu5K7CydAHu6Y8VyWu9TKF6sGFLDZHq9Baaov4wtfUxWnRX1KY5Ovhw218sgRTtIAD6f8jVsKSflttuIw7bSNHHnc9JvS5+mBTuR3e88EpuNuXjTwv0wmZdQC+h4sOdtWZlEYPfiFpwxPTn0VlNBUbaVM5pY5ba/pI9ICAKzSslo75C+hE61IHRNaSPv1lHqCtQqJxfjv/OJXFXB0TkJOVRHjvHeQtrjgjQ5Qd9Ie54= + file: + - "space-separated-tokens.js" + - "space-separated-tokens.min.js" + on: + tags: true diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..8d8660d --- /dev/null +++ b/LICENSE @@ -0,0 +1,22 @@ +(The MIT License) + +Copyright (c) 2016 Titus Wormer + +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/example.js b/example.js new file mode 100644 index 0000000..bd36de8 --- /dev/null +++ b/example.js @@ -0,0 +1,14 @@ +// Dependencies: +var spaceSeparated = require('./index.js'); + +// Parsing: +var values = spaceSeparated.parse(' foo\tbar\nbaz '); + +// Yields: +console.log('js', require('util').inspect(values)); + +// Compiling: +var value = spaceSeparated.stringify(values); + +// Yields: +console.log('js', require('util').inspect(value)); diff --git a/history.md b/history.md new file mode 100644 index 0000000..34cef91 --- /dev/null +++ b/history.md @@ -0,0 +1,6 @@ + + + + +0.0.0 / 2016-02-22 +================== diff --git a/index.js b/index.js new file mode 100644 index 0000000..1f0f2dd --- /dev/null +++ b/index.js @@ -0,0 +1,73 @@ +/** + * @author Titus Wormer + * @copyright 2016 Titus Wormer + * @license MIT + * @module space-separated-tokens + * @fileoverview Parse and stringify space-separated tokens. + */ + +'use strict'; + +/* eslint-env commonjs */ + +/* + * Dependencies. + */ + +var trim = require('trim'); + +/* + * Constants. + */ + +var EMPTY = ''; + +/* + * Characters. + */ + +var C_SPACE = ' '; + +/* + * Expressions. + * + * HTML white-space is slightly different from JavaScript’s + * `\s`, as the latter includes vertical tabs. + */ + +var RE_WHITE_SPACE = /[\ \t\n\r\f]+/g; + +/** + * Parse space-separated tokens to an array. + * + * @param {string} value - Attribute-value to parse. + * @return {Array.} - Tokens. + */ +function parse(value) { + var input = trim(String(value || EMPTY)); + + if (input === EMPTY) { + return []; + } + + return input.split(RE_WHITE_SPACE); +} + +/** + * Compile an array to space-separated tokens. + * + * @param {Array.} values - Tokens. + * @return {string} - Space-separated tokens. + */ +function stringify(values) { + return trim(values.join(C_SPACE)); +} + +/* + * Expose. + */ + +module.exports = { + 'parse': parse, + 'stringify': stringify +}; diff --git a/package.json b/package.json new file mode 100644 index 0000000..e9297ae --- /dev/null +++ b/package.json @@ -0,0 +1,57 @@ +{ + "name": "space-separated-tokens", + "version": "0.0.0", + "description": "Parse and stringify space-separated tokens", + "license": "MIT", + "keywords": [ + "dom", + "html", + "space", + "separated", + "tokens", + "parse", + "stringify" + ], + "dependencies": { + "trim": "0.0.1" + }, + "files": [ + "index.js" + ], + "repository": { + "type": "git", + "url": "https://github.com/wooorm/space-separated-tokens.git" + }, + "bugs": "https://github.com/wooorm/space-separated-tokens/issues", + "author": "Titus Wormer (http://wooorm.com)", + "contributors": [ + "Titus Wormer (http://wooorm.com)" + ], + "devDependencies": { + "browserify": "^13.0.0", + "eslint": "^2.0.0", + "esmangle": "^1.0.1", + "istanbul": "^0.4.0", + "jscs": "^2.0.0", + "jscs-jsdoc": "^1.0.0", + "remark": "^4.0.0", + "remark-comment-config": "^3.0.0", + "remark-github": "^4.0.1", + "remark-lint": "^3.0.0", + "remark-usage": "^3.0.0", + "remark-validate-links": "^3.0.0", + "tape": "^4.4.0" + }, + "scripts": { + "build-md": "remark . --quiet --frail", + "build-bundle": "browserify index.js --bare -s spaceSeparatedTokens > space-separated-tokens.js", + "build-mangle": "esmangle space-separated-tokens.js > space-separated-tokens.min.js", + "build": "npm run build-md && npm run build-bundle && npm run build-mangle", + "lint-api": "eslint .", + "lint-style": "jscs --reporter inline .", + "lint": "npm run lint-api && npm run lint-style", + "test-api": "node test.js", + "test-coverage": "istanbul cover test.js", + "test": "npm run build && npm run lint && npm run test-coverage" + } +} diff --git a/readme.md b/readme.md new file mode 100644 index 0000000..2125d16 --- /dev/null +++ b/readme.md @@ -0,0 +1,89 @@ +# space-separated-tokens [![Build Status][build-badge]][build-page] [![Coverage Status][coverage-badge]][coverage-page] + +Parse and stringify space-separated tokens according to the [spec][]. + +## Installation + +[npm][]: + +```bash +npm install space-separated-tokens +``` + +**space-separated-tokens** is also available as an AMD, CommonJS, and +globals module, [uncompressed and compressed][releases]. + +## Usage + +Dependencies: + +```javascript +var spaceSeparated = require('space-separated-tokens'); +``` + +Parsing: + +```javascript +var values = spaceSeparated.parse(' foo\tbar\nbaz '); +``` + +Yields: + +```js +[ 'foo', 'bar', 'baz' ] +``` + +Compiling: + +```javascript +var value = spaceSeparated.stringify(values); +``` + +Yields: + +```js +'foo bar baz' +``` + +## API + +### `spaceSeparated.parse(value)` + +Parse space-separated tokens to an array of strings, according to the [spec][]. + +* `value` (`string`) — space-separated tokens. + +**Returns**: `Array.` — List of tokens. + +### `spaceSeparated.stringify(values)` + +Compile an array of strings to space-separated tokens. +Note that it’s not possible to specify empty or white-space only values. + +* `values` (`Array.`) — List of tokens. + +**Returns**: `string` — Space-separated tokens. + +## License + +[MIT][license] © [Titus Wormer][author] + + + +[build-badge]: https://img.shields.io/travis/wooorm/space-separated-tokens.svg + +[build-page]: https://travis-ci.org/wooorm/space-separated-tokens + +[coverage-badge]: https://img.shields.io/codecov/c/github/wooorm/space-separated-tokens.svg + +[coverage-page]: https://codecov.io/github/wooorm/space-separated-tokens?branch=master + +[npm]: https://docs.npmjs.com/cli/install + +[releases]: https://github.com/wooorm/space-separated-tokens/releases + +[license]: LICENSE + +[author]: http://wooorm.com + +[spec]: https://html.spec.whatwg.org/#space-separated-tokens diff --git a/test.js b/test.js new file mode 100644 index 0000000..395fa31 --- /dev/null +++ b/test.js @@ -0,0 +1,112 @@ +/** + * @author Titus Wormer + * @copyright 2016 Titus Wormer + * @license MIT + * @module space-separated-tokens + * @fileoverview Test suite for `space-separated-tokens`. + */ + +'use strict'; + +/* eslint-env node */ + +/* + * Module dependencies. + */ + +var test = require('tape'); +var spaceSeparated = require('./index.js'); + +/* + * Tests. + */ + +test('space-separated-tokens', function (t) { + t.equal( + typeof spaceSeparated, + 'object', + 'should be an `object`' + ); + + t.test('.parse()', function (st) { + st.equal( + typeof spaceSeparated.parse, + 'function', + 'should be a method' + ); + + st.deepEqual( + spaceSeparated.parse(), + [], + 'should return an empty array for an empty value' + ); + + st.deepEqual( + spaceSeparated.parse(' '), + [], + 'should return an empty array for a white-space' + ); + + st.deepEqual( + spaceSeparated.parse('\n\t\t '), + [], + 'should return an empty array for a several white-spaces' + ); + + st.deepEqual( + spaceSeparated.parse(' foo bar 💩\t\n\t'), + ['foo', 'bar', '💩'], + 'should work' + ); + + st.end(); + }); + + t.test('.stringify()', function (st) { + st.equal( + typeof spaceSeparated.stringify, + 'function', + 'should be a method' + ); + + st.deepEqual( + spaceSeparated.stringify([]), + '', + 'should return an empty string for an empty array' + ); + + st.deepEqual( + spaceSeparated.stringify(['']), + '', + 'should return an empty string for an empty entry' + ); + + st.deepEqual( + spaceSeparated.stringify(['', '']), + '', + 'should return an empty string for two empty entries' + ); + + st.deepEqual( + spaceSeparated.stringify(['', 'foo']), + 'foo', + 'should ignore initial empty entries' + ); + + st.deepEqual( + spaceSeparated.stringify(['foo', '']), + 'foo', + 'should ignore final empty values' + ); + + st.deepEqual( + spaceSeparated.stringify(['a', 'b', 'd d']), + 'a b d d', + 'should do its best' + ); + + st.end(); + }); + + t.end(); +});