nanoid 1.0.7 → 1.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,6 +1,23 @@
1
1
  # Change Log
2
2
  This project adheres to [Semantic Versioning](http://semver.org/).
3
3
 
4
+ ## 1.2.1
5
+ * Fix old Node.js support.
6
+
7
+ ## 1.2
8
+ * Add `nanoid/async`.
9
+ * Fix `nanoid/non-secure` JSDoc.
10
+ * Add Chinese documentation (by Wenliang Dai).
11
+ * Speed up and reduce size of `nanoid/non-secure` (by Ori Livni).
12
+
13
+ ## 1.1.1
14
+ * Improve performance and reduce size of non-secure ID generator.
15
+
16
+ ## 1.1
17
+ * Add non-secure ID generator.
18
+ * Suggest to use non-secure ID generator for React Native developers.
19
+ * Reduce size.
20
+
4
21
  ## 1.0.7
5
22
  * Fix documentation.
6
23
 
package/README.md CHANGED
@@ -3,23 +3,23 @@
3
3
  <img src="https://ai.github.io/nanoid/logo.svg" align="right"
4
4
  alt="Nano ID logo by Anton Lovchikov" width="180" height="94">
5
5
 
6
- A tiny, secure, URL-friendly, unique string ID generator for JavaScript.
6
+ A tiny, secure, URL-friendly, unique string ID generator for JavaScript.
7
7
 
8
8
  **Safe.** It uses cryptographically strong random APIs
9
- and tests distribution of symbols.
9
+ and tests distribution of symbols.
10
10
 
11
- **Small.** 146 bytes (minified and gzipped). No dependencies.
12
- It uses [Size Limit] to control size.
11
+ **Small.** 145 bytes (minified and gzipped). No dependencies.
12
+ It uses [Size Limit] to control size.
13
13
 
14
- **Compact.** It uses a larger alphabet than UUID (`A-Za-z0-9_~`).
15
- As result it could reduce ID size from 36 to 21 symbols.
14
+ **Compact.** It uses a larger alphabet than UUID (`A-Za-z0-9_~`).
15
+ As result it could reduce ID size from 36 to 21 symbols.
16
16
 
17
17
  ```js
18
18
  var nanoid = require('nanoid')
19
19
  model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B~myT"
20
20
  ```
21
21
 
22
- The generator supports Node.js and [all browsers] starting from IE 11.
22
+ The generator supports Node.js, React Native, and [all browsers].
23
23
 
24
24
  [all browsers]: http://caniuse.com/#feat=getrandomvalues
25
25
  [Size Limit]: https://github.com/ai/size-limit
@@ -50,7 +50,7 @@ The spread will not be even; there will be a lower chance for some symbols
50
50
  to appear compared to others—so it will reduce the number of tries
51
51
  when brute-forcing.
52
52
 
53
- Nano ID uses a [better algorithm] and is tested for uniformity:
53
+ Nano ID uses a [better algorithm] and is tested for uniformity.
54
54
 
55
55
  <img src="img/distribution.png" alt="Nano ID uniformity"
56
56
  width="340" height="135">
@@ -73,17 +73,26 @@ There are two main differences between Nano ID and UUID v4:
73
73
  1. Nano ID uses a bigger alphabet, so a similar number of random bits
74
74
  are packed in just 21 symbols instead of 36.
75
75
  2. Nano ID code is 3 times less than `uuid/v4` package:
76
- 146 bytes instead of 435.
76
+ 145 bytes instead of 435.
77
77
 
78
78
 
79
79
  ## Benchmark
80
80
 
81
81
  ```
82
- $ ./benchmark
83
- nanoid 332,991 ops/sec
84
- nanoid/generate 326,636 ops/sec
85
- uuid/v4 315,344 ops/sec
86
- shortid 33,717 ops/sec
82
+ $ ./test/benchmark
83
+ nanoid 354,201 ops/sec
84
+ nanoid/generate 348,467 ops/sec
85
+ uid.sync 325,347 ops/sec
86
+ uuid/v4 322,328 ops/sec
87
+ shortid 33,277 ops/sec
88
+
89
+ Async:
90
+ uid 71,998 ops/sec
91
+ nanoid/async 72,836 ops/sec
92
+
93
+ Non-secure:
94
+ rndm 2,495,324 ops/sec
95
+ nanoid/non-secure 2,746,033 ops/sec
87
96
  ```
88
97
 
89
98
 
@@ -95,7 +104,7 @@ The main module uses URL-friendly symbols (`A-Za-z0-9_~`) and returns an ID
95
104
  with 21 characters (to have a collision probability similar to UUID v4).
96
105
 
97
106
  ```js
98
- var nanoid = require('nanoid')
107
+ const nanoid = require('nanoid')
99
108
  model.id = nanoid() //=> "Uakgb_J5m9g~0JDMbcJqLJ"
100
109
  ```
101
110
 
@@ -103,7 +112,7 @@ Symbols `-,.()` are not encoded in the URL. If used at the end of a link
103
112
  they could be identified as a punctuation symbol.
104
113
 
105
114
  If you want to reduce ID length (and increase collisions probability),
106
- you can pass the length as an argument:
115
+ you can pass the length as an argument.
107
116
 
108
117
  ```js
109
118
  nanoid(10) //=> "IRFa~VaY2b"
@@ -112,7 +121,41 @@ nanoid(10) //=> "IRFa~VaY2b"
112
121
  Don’t forget to check safety of your ID length
113
122
  in our [ID collision probability] calculator.
114
123
 
115
- [ID collision probability]: https://alex7kom.github.io/nano-nanoid-cc/
124
+ [ID collision probability]: https://zelark.github.io/nano-id-cc/
125
+
126
+
127
+ ### React Native and Web Workers
128
+
129
+ React Native and Web Worker don’t have access to secure random generator.
130
+
131
+ Security is important in ID, when ID should be unpredictable. For instance,
132
+ in “access by URL” link generation.
133
+
134
+ If you don’t need unpredictable IDs, but you need React Native
135
+ or Web Workers support, you can use non‑secure ID generator.
136
+
137
+ ```js
138
+ const nanoid = require('nanoid/non-secure')
139
+ model.id = nanoid() //=> "Uakgb_J5m9g~0JDMbcJqLJ"
140
+ ```
141
+
142
+
143
+ ## Async
144
+
145
+ To generate hardware random bytes, CPU will collect electromagnetic noise.
146
+ During the collection, CPU doesn’t work. So if we will use asynchronous API
147
+ for hardware random generator, your other code could be executed during
148
+ the entropy collection.
149
+
150
+ ```js
151
+ const nanoid = require('nanoid/async')
152
+ nanoid.then(id => {
153
+ model.id = id
154
+ })
155
+ ```
156
+
157
+ Unfortunately, you will not have any benefits in browser, since Web Crypto API
158
+ doesn’t have asynchronous API.
116
159
 
117
160
 
118
161
  ### Custom Alphabet or Length
@@ -121,18 +164,17 @@ If you want to change the ID's alphabet or length
121
164
  you can use the low-level `generate` module.
122
165
 
123
166
  ```js
124
- var generate = require('nanoid/generate')
167
+ const generate = require('nanoid/generate')
125
168
  model.id = generate('1234567890abcdef', 10) //=> "4f90d13a42"
126
169
  ```
127
170
 
128
171
  Check safety of your custom alphabet and ID length
129
172
  in our [ID collision probability] calculator.
173
+ You can find popular alphabets in [`nanoid-dictionary`].
130
174
 
131
175
  Alphabet must contain 256 symbols or less.
132
176
  Otherwise, the generator will not be secure.
133
177
 
134
- You can find popular alphabets in [`nanoid-dictionary`].
135
-
136
178
  [ID collision probability]: https://alex7kom.github.io/nano-nanoid-cc/
137
179
  [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary
138
180
 
@@ -143,11 +185,13 @@ You can replace the default safe random generator using the `format` module.
143
185
  For instance, to use a seed-based generator.
144
186
 
145
187
  ```js
146
- var format = require('nanoid/format')
188
+ const format = require('nanoid/format')
147
189
 
148
190
  function random (size) {
149
- var result = []
150
- for (var i = 0; i < size; i++) result.push(randomByte())
191
+ const result = []
192
+ for (let i = 0; i < size; i++) {
193
+ result.push(randomByte())
194
+ }
151
195
  return result
152
196
  }
153
197
 
@@ -158,10 +202,10 @@ format(random, "abcdef", 10) //=> "fbaefaadeb"
158
202
  with random numbers.
159
203
 
160
204
  If you want to use the same URL-friendly symbols with `format`,
161
- you can get the default alphabet from the `url` module:
205
+ you can get the default alphabet from the `url` file.
162
206
 
163
207
  ```js
164
- var url = require('nanoid/url')
208
+ const url = require('nanoid/url')
165
209
  format(random, url, 10) //=> "93ce_Ltuub"
166
210
  ```
167
211
 
@@ -171,10 +215,12 @@ format(random, url, 10) //=> "93ce_Ltuub"
171
215
  * [ID size calculator] to choice smaller ID size depends on your case.
172
216
  * [`nanoid-dictionary`] with popular alphabets to use with `nanoid/generate`.
173
217
  * [`nanoid-cli`] to generate ID from CLI.
218
+ * [`nanoid-good`] to be sure that your ID doesn't contain any obscene words.
174
219
 
175
220
  [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary
176
- [ID size calculator]: https://alex7kom.github.io/nano-nanoid-cc/
221
+ [ID size calculator]: https://zelark.github.io/nano-id-cc/
177
222
  [`nanoid-cli`]: https://github.com/twhitbeck/nanoid-cli
223
+ [`nanoid-good`]: https://github.com/y-gagar1n/nanoid-good
178
224
 
179
225
 
180
226
  ## Other Programming Languages
@@ -0,0 +1,13 @@
1
+ var crypto = self.crypto || self.msCrypto
2
+
3
+ var url = '_~getRandomVcryp0123456789bfhijklqsuvwxzABCDEFGHIJKLMNOPQSTUWXYZ'
4
+
5
+ module.exports = function (size) {
6
+ size = size || 21
7
+ var id = ''
8
+ var bytes = crypto.getRandomValues(new Uint8Array(size))
9
+ while (0 < size--) {
10
+ id += url[bytes[size] & 63]
11
+ }
12
+ return Promise.resolve(id)
13
+ }
package/async.js ADDED
@@ -0,0 +1,54 @@
1
+ var crypto = require('crypto')
2
+
3
+ var url = require('./url')
4
+
5
+ /**
6
+ * Generate secure URL-friendly unique ID. Non-blocking version.
7
+ *
8
+ * By default, ID will have 21 symbols to have a collision probability similar
9
+ * to UUID v4.
10
+ *
11
+ * @param {number} [size=21] The number of symbols in ID.
12
+ * @param {function} callback for environments without `Promise`.
13
+ *
14
+ * @return {Promise} Promise with random string.
15
+ *
16
+ * @example
17
+ * const nanoidAsync = require('nanoid/async')
18
+ * nanoidAsync.then(id => {
19
+ * model.id = id
20
+ * })
21
+ *
22
+ * @name async
23
+ * @function
24
+ */
25
+ module.exports = function (size, callback) {
26
+ size = size || 21
27
+ if (callback) {
28
+ crypto.randomBytes(size, function (err, bytes) {
29
+ if (err) {
30
+ callback(err)
31
+ } else {
32
+ var id = ''
33
+ while (0 < size--) {
34
+ id += url[bytes[size] & 63]
35
+ }
36
+ callback(null, id)
37
+ }
38
+ })
39
+ } else {
40
+ return new Promise(function (resolve, reject) {
41
+ crypto.randomBytes(size, function (err, bytes) {
42
+ if (err) {
43
+ reject(err)
44
+ } else {
45
+ var id = ''
46
+ while (0 < size--) {
47
+ id += url[bytes[size] & 63]
48
+ }
49
+ resolve(id)
50
+ }
51
+ })
52
+ })
53
+ }
54
+ }
package/format.js CHANGED
@@ -11,11 +11,13 @@
11
11
  * @return {string} Random string.
12
12
  *
13
13
  * @example
14
- * var format = require('nanoid/format')
14
+ * const format = require('nanoid/format')
15
15
  *
16
16
  * function random (size) {
17
- * var result = []
18
- * for (var i = 0; i < size; i++) result.push(randomByte())
17
+ * const result = []
18
+ * for (let i = 0; i < size; i++) {
19
+ * result.push(randomByte())
20
+ * }
19
21
  * return result
20
22
  * }
21
23
  *
package/generate.js CHANGED
@@ -13,7 +13,7 @@ var format = require('./format')
13
13
  * @return {string} Unique ID.
14
14
  *
15
15
  * @example
16
- * var generate = require('nanoid/generate')
16
+ * const generate = require('nanoid/generate')
17
17
  * model.id = generate('0123456789абвгдеё', 5) //=> "8ё56а"
18
18
  *
19
19
  * @name generate
package/index.browser.js CHANGED
@@ -1,3 +1,12 @@
1
+ if (process.env.NODE_ENV !== 'production') {
2
+ if (typeof self === 'undefined' || (!self.crypto && !self.msCrypto)) {
3
+ throw new Error(
4
+ 'Your browser does not have secure random generator. ' +
5
+ 'If you don’t need unpredictable IDs, you can use nanoid/non-secure.'
6
+ )
7
+ }
8
+ }
9
+
1
10
  var crypto = self.crypto || self.msCrypto
2
11
 
3
12
  var url = '_~getRandomVcryp0123456789bfhijklqsuvwxzABCDEFGHIJKLMNOPQSTUWXYZ'
package/index.js CHANGED
@@ -12,7 +12,7 @@ var url = require('./url')
12
12
  * @return {string} Random string.
13
13
  *
14
14
  * @example
15
- * var nanoid = require('nanoid')
15
+ * const nanoid = require('nanoid')
16
16
  * model.id = nanoid() //=> "Uakgb_J5m9g~0JDMbcJqL"
17
17
  *
18
18
  * @name nanoid
package/non-secure.js ADDED
@@ -0,0 +1,28 @@
1
+ var url = '_~getRandomVcryp0123456789bfhijklqsuvwxzABCDEFGHIJKLMNOPQSTUWXYZ'
2
+
3
+ /**
4
+ * Generate URL-friendly unique ID. This method use non-secure predictable
5
+ * random generator.
6
+ *
7
+ * By default, ID will have 21 symbols to have a collision probability similar
8
+ * to UUID v4.
9
+ *
10
+ * @param {number} [size=21] The number of symbols in ID.
11
+ *
12
+ * @return {string} Random string.
13
+ *
14
+ * @example
15
+ * const nanoid = require('nanoid/non-secure')
16
+ * model.id = nanoid() //=> "Uakgb_J5m9g~0JDMbcJqL"
17
+ *
18
+ * @name nonSecure
19
+ * @function
20
+ */
21
+ module.exports = function (size) {
22
+ size = size || 21
23
+ var id = ''
24
+ while (0 < size--) {
25
+ id += url[Math.random() * 63 | 0]
26
+ }
27
+ return id
28
+ }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "nanoid",
3
- "version": "1.0.7",
4
- "description": "A tiny (146 bytes), secure URL-friendly unique string ID generator",
3
+ "version": "1.2.1",
4
+ "description": "A tiny (145 bytes), secure URL-friendly unique string ID generator",
5
5
  "keywords": [
6
6
  "uuid",
7
7
  "random",
@@ -13,49 +13,7 @@
13
13
  "repository": "ai/nanoid",
14
14
  "browser": {
15
15
  "./random.js": "./random.browser.js",
16
- "./index.js": "./index.browser.js"
17
- },
18
- "devDependencies": {
19
- "benchmark": "^2.1.4",
20
- "chalk": "^2.4.1",
21
- "docdash": "^0.4.0",
22
- "eslint": "^5.0.1",
23
- "eslint-ci": "^0.1.1",
24
- "eslint-config-logux": "^23.0.2",
25
- "eslint-config-standard": "^11.0.0",
26
- "eslint-plugin-es5": "^1.3.1",
27
- "eslint-plugin-import": "^2.13.0",
28
- "eslint-plugin-jest": "^21.17.0",
29
- "eslint-plugin-node": "^6.0.1",
30
- "eslint-plugin-promise": "^3.8.0",
31
- "eslint-plugin-security": "^1.4.0",
32
- "eslint-plugin-standard": "^3.1.0",
33
- "html-webpack-plugin": "^3.2.0",
34
- "jest": "^23.3.0",
35
- "jsdoc": "^3.5.5",
36
- "lint-staged": "^7.2.0",
37
- "microtime": "^2.1.8",
38
- "pre-commit": "^1.2.2",
39
- "rimraf": "^2.6.2",
40
- "shortid": "^2.2.9",
41
- "size-limit": "^0.18.3",
42
- "svgo": "^1.0.5",
43
- "uuid": "^3.3.2",
44
- "webpack": "^4.15.1",
45
- "webpack-cli": "^3.0.8",
46
- "webpack-dev-server": "^3.1.4",
47
- "yaspeller-ci": "^1.0.0"
48
- },
49
- "scripts": {
50
- "lint-staged": "lint-staged",
51
- "spellcheck": "yarn docs && yaspeller-ci *.md docs/*.html",
52
- "clean": "rimraf docs/ coverage/",
53
- "docs": "jsdoc --configure .jsdocrc *.js",
54
- "lint": "eslint-ci *.js test/*.js",
55
- "test": "jest --coverage && yarn lint && size-limit && yarn spellcheck",
56
- "start": "webpack-dev-server --config test/demo/webpack.config"
57
- },
58
- "pre-commit": [
59
- "lint-staged"
60
- ]
16
+ "./index.js": "./index.browser.js",
17
+ "./async.js": "./async.browser.js"
18
+ }
61
19
  }
package/url.js CHANGED
@@ -5,7 +5,7 @@
5
5
  * @type {string}
6
6
  *
7
7
  * @example
8
- * var url = require('nanoid/url')
8
+ * const url = require('nanoid/url')
9
9
  * generate(url, 10) //=> "Uakgb_J5m9"
10
10
  */
11
11
  module.exports =