uuid 1.4.0 → 2.0.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/.travis.yml ADDED
@@ -0,0 +1,5 @@
1
+ language: node_js
2
+ node_js:
3
+ - "0.6"
4
+ - "0.8"
5
+ - "0.10"
package/README.md CHANGED
@@ -1,4 +1,6 @@
1
- # node-uuid
1
+ # uuid [![Build Status](https://secure.travis-ci.org/defunctzombie/node-uuid.png?branch=master)](http://travis-ci.org/defunctzombie/node-uuid) #
2
+
3
+ [![browser support](https://ci.testling.com/defunctzombie/node-uuid.png)](https://ci.testling.com/defunctzombie/node-uuid)
2
4
 
3
5
  Simple, fast generation of [RFC4122](http://www.ietf.org/rfc/rfc4122.txt) UUIDS.
4
6
 
@@ -7,7 +9,7 @@ Features:
7
9
  * Generate RFC4122 version 1 or version 4 UUIDs
8
10
  * Runs in node.js and all browsers.
9
11
  * Cryptographically strong random # generation on supporting platforms
10
- * 1.1K minified and gzip'ed (Want something smaller? Check this [crazy shit](https://gist.github.com/982883) out! )
12
+ * 1185 bytes minified and gzip'ed (Want something smaller? Check this [crazy shit](https://gist.github.com/982883) out! )
11
13
  * [Annotated source code](http://broofa.github.com/node-uuid/docs/uuid.html)
12
14
 
13
15
  ## Getting Started
@@ -21,16 +23,12 @@ Install it in your browser:
21
23
  Or in node.js:
22
24
 
23
25
  ```
24
- npm install node-uuid
26
+ npm install uuid
25
27
  ```
26
28
 
27
29
  ```javascript
28
- var uuid = require('node-uuid');
29
- ```
30
+ var uuid = require('uuid');
30
31
 
31
- Then create some ids ...
32
-
33
- ```javascript
34
32
  // Generate a v1 (time-based) id
35
33
  uuid.v1(); // -> '6c84fb90-12c4-11e1-840d-7b25c5ee775a'
36
34
 
@@ -138,7 +136,7 @@ var string = uuid.unparse(bytes); // -> '797ff043-11eb-11e1-80d6-510998755d10'
138
136
 
139
137
  (Browsers only) Set `uuid` property back to it's previous value.
140
138
 
141
- Returns the node-uuid object.
139
+ Returns the uuid object.
142
140
 
143
141
  Example:
144
142
 
@@ -179,11 +177,12 @@ open test/test.html
179
177
  Requires node.js
180
178
 
181
179
  ```
182
- npm install uuid uuid-js
183
- node benchmark/benchmark.js
180
+ cd benchmark/
181
+ npm install
182
+ node benchmark.js
184
183
  ```
185
184
 
186
- For a more complete discussion of node-uuid performance, please see the `benchmark/README.md` file, and the [benchmark wiki](https://github.com/broofa/node-uuid/wiki/Benchmark)
185
+ For a more complete discussion of uuid performance, please see the `benchmark/README.md` file, and the [benchmark wiki](https://github.com/broofa/uuid/wiki/Benchmark)
187
186
 
188
187
  For browser performance [checkout the JSPerf tests](http://jsperf.com/node-uuid-performance).
189
188
 
@@ -0,0 +1,9 @@
1
+ {
2
+ "name": "benchmark-uuid",
3
+ "private": true,
4
+ "description": "Benchmarks for node-uuid",
5
+ "dependencies": {
6
+ "uuid": "1.4.1",
7
+ "uuid-js": "0.7.4"
8
+ }
9
+ }
@@ -1,7 +1,6 @@
1
1
  var assert = require('assert'),
2
- nodeuuid = require('../uuid'),
2
+ nodeuuid = require('../'),
3
3
  uuidjs = require('uuid-js'),
4
- libuuid = require('uuid').generate,
5
4
  util = require('util'),
6
5
  exec = require('child_process').exec,
7
6
  os = require('os');
package/misc/perf.js ADDED
@@ -0,0 +1,102 @@
1
+ var assert = require('assert');
2
+
3
+ var uuid = require('../');
4
+
5
+ var log = console.log;
6
+
7
+ var generators = {
8
+ v1: uuid.v1,
9
+ v4: uuid.v4
10
+ };
11
+
12
+ var UUID_FORMAT = {
13
+ v1: /[0-9a-f]{8}-[0-9a-f]{4}-1[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}/i,
14
+ v4: /[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}/i
15
+ };
16
+
17
+ var N = 1e4;
18
+
19
+ // Get %'age an actual value differs from the ideal value
20
+ function divergence(actual, ideal) {
21
+ return Math.round(100*100*(actual - ideal)/ideal)/100;
22
+ }
23
+
24
+ function rate(msg, t) {
25
+ log(msg + ': ' + (N / (Date.now() - t) * 1e3 | 0) + ' uuids\/second');
26
+ }
27
+
28
+ for (var version in generators) {
29
+ var counts = {}, max = 0;
30
+ var generator = generators[version];
31
+ var format = UUID_FORMAT[version];
32
+
33
+ log('\nSanity check ' + N + ' ' + version + ' uuids');
34
+ for (var i = 0, ok = 0; i < N; i++) {
35
+ id = generator();
36
+ if (!format.test(id)) {
37
+ throw Error(id + ' is not a valid UUID string');
38
+ }
39
+
40
+ if (id != uuid.unparse(uuid.parse(id))) {
41
+ assert(fail, id + ' is not a valid id');
42
+ }
43
+
44
+ // Count digits for our randomness check
45
+ if (version == 'v4') {
46
+ var digits = id.replace(/-/g, '').split('');
47
+ for (var j = digits.length-1; j >= 0; j--) {
48
+ var c = digits[j];
49
+ max = Math.max(max, counts[c] = (counts[c] || 0) + 1);
50
+ }
51
+ }
52
+ }
53
+
54
+ // Check randomness for v4 UUIDs
55
+ if (version == 'v4') {
56
+ // Limit that we get worried about randomness. (Purely empirical choice, this!)
57
+ var limit = 2*100*Math.sqrt(1/N);
58
+
59
+ log('\nChecking v4 randomness. Distribution of Hex Digits (% deviation from ideal)');
60
+
61
+ for (var i = 0; i < 16; i++) {
62
+ var c = i.toString(16);
63
+ var bar = '', n = counts[c], p = Math.round(n/max*100|0);
64
+
65
+ // 1-3,5-8, and D-F: 1:16 odds over 30 digits
66
+ var ideal = N*30/16;
67
+ if (i == 4) {
68
+ // 4: 1:1 odds on 1 digit, plus 1:16 odds on 30 digits
69
+ ideal = N*(1 + 30/16);
70
+ } else if (i >= 8 && i <= 11) {
71
+ // 8-B: 1:4 odds on 1 digit, plus 1:16 odds on 30 digits
72
+ ideal = N*(1/4 + 30/16);
73
+ } else {
74
+ // Otherwise: 1:16 odds on 30 digits
75
+ ideal = N*30/16;
76
+ }
77
+ var d = divergence(n, ideal);
78
+
79
+ // Draw bar using UTF squares (just for grins)
80
+ var s = n/max*50 | 0;
81
+ while (s--) bar += '=';
82
+
83
+ assert(Math.abs(d) < limit, c + ' |' + bar + '| ' + counts[c] + ' (' + d + '% < ' + limit + '%)');
84
+ }
85
+ }
86
+ }
87
+
88
+ // Perf tests
89
+ for (var version in generators) {
90
+ log('\nPerformance testing ' + version + ' UUIDs');
91
+ var generator = generators[version];
92
+ var buf = new uuid.BufferClass(16);
93
+
94
+ for (var i = 0, t = Date.now(); i < N; i++) generator();
95
+ rate('uuid.' + version + '()', t);
96
+
97
+ for (var i = 0, t = Date.now(); i < N; i++) generator('binary');
98
+ rate('uuid.' + version + '(\'binary\')', t);
99
+
100
+ for (var i = 0, t = Date.now(); i < N; i++) generator('binary', buf);
101
+ rate('uuid.' + version + '(\'binary\', buffer)', t);
102
+ }
package/package.json CHANGED
@@ -1,14 +1,45 @@
1
1
  {
2
- "name" : "uuid",
3
- "description" : "Rigorous implementation of RFC4122 (v1 and v4) UUIDs.",
4
- "url" : "http://github.com/broofa/node-uuid",
5
- "keywords" : ["uuid", "guid", "rfc4122"],
6
- "author" : "Robert Kieffer <robert@broofa.com>",
7
- "contributors" : [
8
- {"name": "Christoph Tavan <dev@tavan.de>", "github": "https://github.com/ctavan"}
2
+ "name": "uuid",
3
+ "version": "2.0.1",
4
+ "description": "Rigorous implementation of RFC4122 (v1 and v4) UUIDs.",
5
+ "keywords": [
6
+ "uuid",
7
+ "guid",
8
+ "rfc4122"
9
9
  ],
10
- "lib" : ".",
11
- "main" : "./uuid.js",
12
- "repository" : { "type" : "git", "url" : "https://github.com/broofa/node-uuid.git" },
13
- "version" : "1.4.0"
10
+ "author": "Robert Kieffer <robert@broofa.com>",
11
+ "contributors": [
12
+ {
13
+ "name": "Christoph Tavan <dev@tavan.de>",
14
+ "github": "https://github.com/ctavan"
15
+ },
16
+ {
17
+ "name": "Vincent Voyer <vincent@zeroload.net>",
18
+ "github": "https://github.com/vvo"
19
+ }
20
+ ],
21
+ "main": "./uuid.js",
22
+ "devDependencies": {
23
+ "mocha": "1.8.0"
24
+ },
25
+ "scripts": {
26
+ "test": "mocha test/test.js"
27
+ },
28
+ "browser": {
29
+ "./rng.js": "./rng-browser.js"
30
+ },
31
+ "repository": {
32
+ "type": "git",
33
+ "url": "https://github.com/shtylman/node-uuid.git"
34
+ },
35
+ "testling": {
36
+ "browsers": [
37
+ "ie6..latest",
38
+ "firefox/3.6..latest",
39
+ "chrome/22..latest",
40
+ "safari/5.1..latest"
41
+ ],
42
+ "harness": "mocha-tdd",
43
+ "files": "test/*.js"
44
+ }
14
45
  }
package/rng-browser.js ADDED
@@ -0,0 +1,31 @@
1
+
2
+ var rng;
3
+
4
+ if (global.crypto && crypto.getRandomValues) {
5
+ // WHATWG crypto-based RNG - http://wiki.whatwg.org/wiki/Crypto
6
+ // Moderately fast, high quality
7
+ var _rnds8 = new Uint8Array(16);
8
+ rng = function whatwgRNG() {
9
+ crypto.getRandomValues(_rnds8);
10
+ return _rnds8;
11
+ };
12
+ }
13
+
14
+ if (!rng) {
15
+ // Math.random()-based (RNG)
16
+ //
17
+ // If all else fails, use Math.random(). It's fast, but is of unspecified
18
+ // quality.
19
+ var _rnds = new Array(16);
20
+ rng = function() {
21
+ for (var i = 0, r; i < 16; i++) {
22
+ if ((i & 0x03) === 0) r = Math.random() * 0x100000000;
23
+ _rnds[i] = r >>> ((i & 0x03) << 3) & 0xff;
24
+ }
25
+
26
+ return _rnds;
27
+ };
28
+ }
29
+
30
+ module.exports = rng;
31
+
package/rng.js ADDED
@@ -0,0 +1,4 @@
1
+ var rb = require('crypto').randomBytes;
2
+ module.exports = function() {
3
+ return rb(16);
4
+ };
@@ -0,0 +1 @@
1
+ --ui qunit
package/test/test.js CHANGED
@@ -1,54 +1,21 @@
1
- if (!this.uuid) {
2
- // node.js
3
- uuid = require('../uuid');
4
- }
5
-
6
- //
7
- // x-platform log/assert shims
8
- //
9
-
10
- function _log(msg, type) {
11
- type = type || 'log';
12
-
13
- if (typeof(document) != 'undefined') {
14
- document.write('<div class="' + type + '">' + msg.replace(/\n/g, '<br />') + '</div>');
15
- }
16
- if (typeof(console) != 'undefined') {
17
- var color = {
18
- log: '\033[39m',
19
- warn: '\033[33m',
20
- error: '\033[31m'
21
- };
22
- console[type](color[type] + msg + color.log);
23
- }
24
- }
25
-
26
- function log(msg) {_log(msg, 'log');}
27
- function warn(msg) {_log(msg, 'warn');}
28
- function error(msg) {_log(msg, 'error');}
29
-
30
- function assert(res, msg) {
31
- if (!res) {
32
- error('FAIL: ' + msg);
33
- } else {
34
- log('Pass: ' + msg);
35
- }
36
- }
1
+ var assert = require('assert');
37
2
 
38
- //
39
- // Unit tests
40
- //
3
+ var uuid = require('../');
41
4
 
42
5
  // Verify ordering of v1 ids created with explicit times
43
6
  var TIME = 1321644961388; // 2011-11-18 11:36:01.388-08:00
44
7
 
45
8
  function compare(name, ids) {
46
- ids = ids.map(function(id) {
47
- return id.split('-').reverse().join('-');
48
- }).sort();
49
- var sorted = ([].concat(ids)).sort();
9
+ test(name, function() {
10
+ // avoid .map for older browsers
11
+ for (var i=0 ; i<ids.length ; ++i) {
12
+ ids[i] = ids[i].split('-').reverse().join('-');
13
+ }
14
+ ids = ids.sort();
15
+ var sorted = ([].concat(ids)).sort();
50
16
 
51
- assert(sorted.toString() == ids.toString(), name + ' have expected order');
17
+ assert(sorted.toString() == ids.toString(), name + ' have expected order');
18
+ });
52
19
  }
53
20
 
54
21
  // Verify ordering of v1 ids created using default behavior
@@ -69,160 +36,70 @@ compare('uuids with time option', [
69
36
  uuid.v1({msecs: TIME + 28*24*3600*1000})
70
37
  ]);
71
38
 
72
- assert(
73
- uuid.v1({msecs: TIME}) != uuid.v1({msecs: TIME}),
74
- 'IDs created at same msec are different'
75
- );
76
-
77
- // Verify throw if too many ids created
78
- var thrown = false;
79
- try {
80
- uuid.v1({msecs: TIME, nsecs: 10000});
81
- } catch (e) {
82
- thrown = true;
83
- }
84
- assert(thrown, 'Exception thrown when > 10K ids created in 1 ms');
85
-
86
- // Verify clock regression bumps clockseq
87
- var uidt = uuid.v1({msecs: TIME});
88
- var uidtb = uuid.v1({msecs: TIME - 1});
89
- assert(
90
- parseInt(uidtb.split('-')[3], 16) - parseInt(uidt.split('-')[3], 16) === 1,
91
- 'Clock regression by msec increments the clockseq'
92
- );
93
-
94
- // Verify clock regression bumps clockseq
95
- var uidtn = uuid.v1({msecs: TIME, nsecs: 10});
96
- var uidtnb = uuid.v1({msecs: TIME, nsecs: 9});
97
- assert(
98
- parseInt(uidtnb.split('-')[3], 16) - parseInt(uidtn.split('-')[3], 16) === 1,
99
- 'Clock regression by nsec increments the clockseq'
100
- );
101
-
102
- // Verify explicit options produce expected id
103
- var id = uuid.v1({
104
- msecs: 1321651533573,
105
- nsecs: 5432,
106
- clockseq: 0x385c,
107
- node: [ 0x61, 0xcd, 0x3c, 0xbb, 0x32, 0x10 ]
39
+ test('msec', function() {
40
+ assert(
41
+ uuid.v1({msecs: TIME}) != uuid.v1({msecs: TIME}),
42
+ 'IDs created at same msec are different'
43
+ );
108
44
  });
109
- assert(id == 'd9428888-122b-11e1-b85c-61cd3cbb3210', 'Explicit options produce expected id');
110
-
111
- // Verify adjacent ids across a msec boundary are 1 time unit apart
112
- var u0 = uuid.v1({msecs: TIME, nsecs: 9999});
113
- var u1 = uuid.v1({msecs: TIME + 1, nsecs: 0});
114
-
115
- var before = u0.split('-')[0], after = u1.split('-')[0];
116
- var dt = parseInt(after, 16) - parseInt(before, 16);
117
- assert(dt === 1, 'Ids spanning 1ms boundary are 100ns apart');
118
-
119
- //
120
- // Test parse/unparse
121
- //
122
-
123
- id = '00112233445566778899aabbccddeeff';
124
- assert(uuid.unparse(uuid.parse(id.substr(0,10))) ==
125
- '00112233-4400-0000-0000-000000000000', 'Short parse');
126
- assert(uuid.unparse(uuid.parse('(this is the uuid -> ' + id + id)) ==
127
- '00112233-4455-6677-8899-aabbccddeeff', 'Dirty parse');
128
-
129
- //
130
- // Perf tests
131
- //
132
-
133
- var generators = {
134
- v1: uuid.v1,
135
- v4: uuid.v4
136
- };
137
-
138
- var UUID_FORMAT = {
139
- v1: /[0-9a-f]{8}-[0-9a-f]{4}-1[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}/i,
140
- v4: /[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}/i
141
- };
142
45
 
143
- var N = 1e4;
144
-
145
- // Get %'age an actual value differs from the ideal value
146
- function divergence(actual, ideal) {
147
- return Math.round(100*100*(actual - ideal)/ideal)/100;
148
- }
149
-
150
- function rate(msg, t) {
151
- log(msg + ': ' + (N / (Date.now() - t) * 1e3 | 0) + ' uuids\/second');
152
- }
153
-
154
- for (var version in generators) {
155
- var counts = {}, max = 0;
156
- var generator = generators[version];
157
- var format = UUID_FORMAT[version];
158
-
159
- log('\nSanity check ' + N + ' ' + version + ' uuids');
160
- for (var i = 0, ok = 0; i < N; i++) {
161
- id = generator();
162
- if (!format.test(id)) {
163
- throw Error(id + ' is not a valid UUID string');
164
- }
165
-
166
- if (id != uuid.unparse(uuid.parse(id))) {
167
- assert(fail, id + ' is not a valid id');
168
- }
169
-
170
- // Count digits for our randomness check
171
- if (version == 'v4') {
172
- var digits = id.replace(/-/g, '').split('');
173
- for (var j = digits.length-1; j >= 0; j--) {
174
- var c = digits[j];
175
- max = Math.max(max, counts[c] = (counts[c] || 0) + 1);
176
- }
177
- }
46
+ test('exception thrown when > 10k ids created in 1ms', function() {
47
+ // Verify throw if too many ids created
48
+ var thrown = false;
49
+ try {
50
+ uuid.v1({msecs: TIME, nsecs: 10000});
51
+ } catch (e) {
52
+ thrown = true;
178
53
  }
54
+ assert(thrown, 'Exception thrown when > 10K ids created in 1 ms');
55
+ });
179
56
 
180
- // Check randomness for v4 UUIDs
181
- if (version == 'v4') {
182
- // Limit that we get worried about randomness. (Purely empirical choice, this!)
183
- var limit = 2*100*Math.sqrt(1/N);
184
-
185
- log('\nChecking v4 randomness. Distribution of Hex Digits (% deviation from ideal)');
186
-
187
- for (var i = 0; i < 16; i++) {
188
- var c = i.toString(16);
189
- var bar = '', n = counts[c], p = Math.round(n/max*100|0);
190
-
191
- // 1-3,5-8, and D-F: 1:16 odds over 30 digits
192
- var ideal = N*30/16;
193
- if (i == 4) {
194
- // 4: 1:1 odds on 1 digit, plus 1:16 odds on 30 digits
195
- ideal = N*(1 + 30/16);
196
- } else if (i >= 8 && i <= 11) {
197
- // 8-B: 1:4 odds on 1 digit, plus 1:16 odds on 30 digits
198
- ideal = N*(1/4 + 30/16);
199
- } else {
200
- // Otherwise: 1:16 odds on 30 digits
201
- ideal = N*30/16;
202
- }
203
- var d = divergence(n, ideal);
57
+ test('clock regression by msec', function() {
58
+ // Verify clock regression bumps clockseq
59
+ var uidt = uuid.v1({msecs: TIME});
60
+ var uidtb = uuid.v1({msecs: TIME - 1});
61
+ assert(
62
+ parseInt(uidtb.split('-')[3], 16) - parseInt(uidt.split('-')[3], 16) === 1,
63
+ 'Clock regression by msec increments the clockseq'
64
+ );
65
+ });
204
66
 
205
- // Draw bar using UTF squares (just for grins)
206
- var s = n/max*50 | 0;
207
- while (s--) bar += '=';
67
+ test('clock regression by nsec', function() {
68
+ // Verify clock regression bumps clockseq
69
+ var uidtn = uuid.v1({msecs: TIME, nsecs: 10});
70
+ var uidtnb = uuid.v1({msecs: TIME, nsecs: 9});
71
+ assert(
72
+ parseInt(uidtnb.split('-')[3], 16) - parseInt(uidtn.split('-')[3], 16) === 1,
73
+ 'Clock regression by nsec increments the clockseq'
74
+ );
75
+ });
208
76
 
209
- assert(Math.abs(d) < limit, c + ' |' + bar + '| ' + counts[c] + ' (' + d + '% < ' + limit + '%)');
210
- }
211
- }
212
- }
77
+ test('explicit options product expected id', function() {
78
+ // Verify explicit options produce expected id
79
+ var id = uuid.v1({
80
+ msecs: 1321651533573,
81
+ nsecs: 5432,
82
+ clockseq: 0x385c,
83
+ node: [ 0x61, 0xcd, 0x3c, 0xbb, 0x32, 0x10 ]
84
+ });
85
+ assert(id == 'd9428888-122b-11e1-b85c-61cd3cbb3210', 'Explicit options produce expected id');
86
+ });
213
87
 
214
- // Perf tests
215
- for (var version in generators) {
216
- log('\nPerformance testing ' + version + ' UUIDs');
217
- var generator = generators[version];
218
- var buf = new uuid.BufferClass(16);
88
+ test('ids spanning 1ms boundary are 100ns apart', function() {
89
+ // Verify adjacent ids across a msec boundary are 1 time unit apart
90
+ var u0 = uuid.v1({msecs: TIME, nsecs: 9999});
91
+ var u1 = uuid.v1({msecs: TIME + 1, nsecs: 0});
219
92
 
220
- for (var i = 0, t = Date.now(); i < N; i++) generator();
221
- rate('uuid.' + version + '()', t);
93
+ var before = u0.split('-')[0], after = u1.split('-')[0];
94
+ var dt = parseInt(after, 16) - parseInt(before, 16);
95
+ assert(dt === 1, 'Ids spanning 1ms boundary are 100ns apart');
96
+ });
222
97
 
223
- for (var i = 0, t = Date.now(); i < N; i++) generator('binary');
224
- rate('uuid.' + version + '(\'binary\')', t);
98
+ test('parse/unparse', function() {
99
+ var id = '00112233445566778899aabbccddeeff';
100
+ assert(uuid.unparse(uuid.parse(id.substr(0,10))) ==
101
+ '00112233-4400-0000-0000-000000000000', 'Short parse');
102
+ assert(uuid.unparse(uuid.parse('(this is the uuid -> ' + id + id)) ==
103
+ '00112233-4455-6677-8899-aabbccddeeff', 'Dirty parse');
104
+ });
225
105
 
226
- for (var i = 0, t = Date.now(); i < N; i++) generator('binary', buf);
227
- rate('uuid.' + version + '(\'binary\', buffer)', t);
228
- }
package/uuid.js CHANGED
@@ -3,243 +3,181 @@
3
3
  // Copyright (c) 2010-2012 Robert Kieffer
4
4
  // MIT License - http://opensource.org/licenses/mit-license.php
5
5
 
6
- (function() {
7
- var _global = this;
8
-
9
- // Unique ID creation requires a high quality random # generator. We feature
10
- // detect to determine the best RNG source, normalizing to a function that
11
- // returns 128-bits of randomness, since that's what's usually required
12
- var _rng;
13
-
14
- // Node.js crypto-based RNG - http://nodejs.org/docs/v0.6.2/api/crypto.html
15
- //
16
- // Moderately fast, high quality
17
- if (typeof(require) == 'function') {
18
- try {
19
- var _rb = require('crypto').randomBytes;
20
- _rng = _rb && function() {return _rb(16);};
21
- } catch(e) {}
22
- }
23
-
24
- if (!_rng && _global.crypto && crypto.getRandomValues) {
25
- // WHATWG crypto-based RNG - http://wiki.whatwg.org/wiki/Crypto
26
- //
27
- // Moderately fast, high quality
28
- var _rnds8 = new Uint8Array(16);
29
- _rng = function whatwgRNG() {
30
- crypto.getRandomValues(_rnds8);
31
- return _rnds8;
32
- };
33
- }
34
-
35
- if (!_rng) {
36
- // Math.random()-based (RNG)
37
- //
38
- // If all else fails, use Math.random(). It's fast, but is of unspecified
39
- // quality.
40
- var _rnds = new Array(16);
41
- _rng = function() {
42
- for (var i = 0, r; i < 16; i++) {
43
- if ((i & 0x03) === 0) r = Math.random() * 0x100000000;
44
- _rnds[i] = r >>> ((i & 0x03) << 3) & 0xff;
45
- }
46
-
47
- return _rnds;
48
- };
49
- }
50
-
51
- // Buffer class to use
52
- var BufferClass = typeof(Buffer) == 'function' ? Buffer : Array;
6
+ // Unique ID creation requires a high quality random # generator. We feature
7
+ // detect to determine the best RNG source, normalizing to a function that
8
+ // returns 128-bits of randomness, since that's what's usually required
9
+ var _rng = require('./rng');
10
+
11
+ // Maps for number <-> hex string conversion
12
+ var _byteToHex = [];
13
+ var _hexToByte = {};
14
+ for (var i = 0; i < 256; i++) {
15
+ _byteToHex[i] = (i + 0x100).toString(16).substr(1);
16
+ _hexToByte[_byteToHex[i]] = i;
17
+ }
18
+
19
+ // **`parse()` - Parse a UUID into it's component bytes**
20
+ function parse(s, buf, offset) {
21
+ var i = (buf && offset) || 0, ii = 0;
22
+
23
+ buf = buf || [];
24
+ s.toLowerCase().replace(/[0-9a-f]{2}/g, function(oct) {
25
+ if (ii < 16) { // Don't overflow!
26
+ buf[i + ii++] = _hexToByte[oct];
27
+ }
28
+ });
53
29
 
54
- // Maps for number <-> hex string conversion
55
- var _byteToHex = [];
56
- var _hexToByte = {};
57
- for (var i = 0; i < 256; i++) {
58
- _byteToHex[i] = (i + 0x100).toString(16).substr(1);
59
- _hexToByte[_byteToHex[i]] = i;
30
+ // Zero out remaining bytes if string was short
31
+ while (ii < 16) {
32
+ buf[i + ii++] = 0;
60
33
  }
61
34
 
62
- // **`parse()` - Parse a UUID into it's component bytes**
63
- function parse(s, buf, offset) {
64
- var i = (buf && offset) || 0, ii = 0;
35
+ return buf;
36
+ }
37
+
38
+ // **`unparse()` - Convert UUID byte array (ala parse()) into a string**
39
+ function unparse(buf, offset) {
40
+ var i = offset || 0, bth = _byteToHex;
41
+ return bth[buf[i++]] + bth[buf[i++]] +
42
+ bth[buf[i++]] + bth[buf[i++]] + '-' +
43
+ bth[buf[i++]] + bth[buf[i++]] + '-' +
44
+ bth[buf[i++]] + bth[buf[i++]] + '-' +
45
+ bth[buf[i++]] + bth[buf[i++]] + '-' +
46
+ bth[buf[i++]] + bth[buf[i++]] +
47
+ bth[buf[i++]] + bth[buf[i++]] +
48
+ bth[buf[i++]] + bth[buf[i++]];
49
+ }
50
+
51
+ // **`v1()` - Generate time-based UUID**
52
+ //
53
+ // Inspired by https://github.com/LiosK/UUID.js
54
+ // and http://docs.python.org/library/uuid.html
65
55
 
66
- buf = buf || [];
67
- s.toLowerCase().replace(/[0-9a-f]{2}/g, function(oct) {
68
- if (ii < 16) { // Don't overflow!
69
- buf[i + ii++] = _hexToByte[oct];
70
- }
71
- });
56
+ // random #'s we need to init node and clockseq
57
+ var _seedBytes = _rng();
72
58
 
73
- // Zero out remaining bytes if string was short
74
- while (ii < 16) {
75
- buf[i + ii++] = 0;
76
- }
59
+ // Per 4.5, create and 48-bit node id, (47 random bits + multicast bit = 1)
60
+ var _nodeId = [
61
+ _seedBytes[0] | 0x01,
62
+ _seedBytes[1], _seedBytes[2], _seedBytes[3], _seedBytes[4], _seedBytes[5]
63
+ ];
77
64
 
78
- return buf;
79
- }
65
+ // Per 4.2.2, randomize (14 bit) clockseq
66
+ var _clockseq = (_seedBytes[6] << 8 | _seedBytes[7]) & 0x3fff;
80
67
 
81
- // **`unparse()` - Convert UUID byte array (ala parse()) into a string**
82
- function unparse(buf, offset) {
83
- var i = offset || 0, bth = _byteToHex;
84
- return bth[buf[i++]] + bth[buf[i++]] +
85
- bth[buf[i++]] + bth[buf[i++]] + '-' +
86
- bth[buf[i++]] + bth[buf[i++]] + '-' +
87
- bth[buf[i++]] + bth[buf[i++]] + '-' +
88
- bth[buf[i++]] + bth[buf[i++]] + '-' +
89
- bth[buf[i++]] + bth[buf[i++]] +
90
- bth[buf[i++]] + bth[buf[i++]] +
91
- bth[buf[i++]] + bth[buf[i++]];
92
- }
68
+ // Previous uuid creation time
69
+ var _lastMSecs = 0, _lastNSecs = 0;
93
70
 
94
- // **`v1()` - Generate time-based UUID**
95
- //
96
- // Inspired by https://github.com/LiosK/UUID.js
97
- // and http://docs.python.org/library/uuid.html
71
+ // See https://github.com/broofa/node-uuid for API details
72
+ function v1(options, buf, offset) {
73
+ var i = buf && offset || 0;
74
+ var b = buf || [];
98
75
 
99
- // random #'s we need to init node and clockseq
100
- var _seedBytes = _rng();
76
+ options = options || {};
101
77
 
102
- // Per 4.5, create and 48-bit node id, (47 random bits + multicast bit = 1)
103
- var _nodeId = [
104
- _seedBytes[0] | 0x01,
105
- _seedBytes[1], _seedBytes[2], _seedBytes[3], _seedBytes[4], _seedBytes[5]
106
- ];
78
+ var clockseq = options.clockseq !== undefined ? options.clockseq : _clockseq;
107
79
 
108
- // Per 4.2.2, randomize (14 bit) clockseq
109
- var _clockseq = (_seedBytes[6] << 8 | _seedBytes[7]) & 0x3fff;
80
+ // UUID timestamps are 100 nano-second units since the Gregorian epoch,
81
+ // (1582-10-15 00:00). JSNumbers aren't precise enough for this, so
82
+ // time is handled internally as 'msecs' (integer milliseconds) and 'nsecs'
83
+ // (100-nanoseconds offset from msecs) since unix epoch, 1970-01-01 00:00.
84
+ var msecs = options.msecs !== undefined ? options.msecs : new Date().getTime();
110
85
 
111
- // Previous uuid creation time
112
- var _lastMSecs = 0, _lastNSecs = 0;
86
+ // Per 4.2.1.2, use count of uuid's generated during the current clock
87
+ // cycle to simulate higher resolution clock
88
+ var nsecs = options.nsecs !== undefined ? options.nsecs : _lastNSecs + 1;
113
89
 
114
- // See https://github.com/broofa/node-uuid for API details
115
- function v1(options, buf, offset) {
116
- var i = buf && offset || 0;
117
- var b = buf || [];
90
+ // Time since last uuid creation (in msecs)
91
+ var dt = (msecs - _lastMSecs) + (nsecs - _lastNSecs)/10000;
118
92
 
119
- options = options || {};
120
-
121
- var clockseq = options.clockseq != null ? options.clockseq : _clockseq;
122
-
123
- // UUID timestamps are 100 nano-second units since the Gregorian epoch,
124
- // (1582-10-15 00:00). JSNumbers aren't precise enough for this, so
125
- // time is handled internally as 'msecs' (integer milliseconds) and 'nsecs'
126
- // (100-nanoseconds offset from msecs) since unix epoch, 1970-01-01 00:00.
127
- var msecs = options.msecs != null ? options.msecs : new Date().getTime();
93
+ // Per 4.2.1.2, Bump clockseq on clock regression
94
+ if (dt < 0 && options.clockseq === undefined) {
95
+ clockseq = clockseq + 1 & 0x3fff;
96
+ }
128
97
 
129
- // Per 4.2.1.2, use count of uuid's generated during the current clock
130
- // cycle to simulate higher resolution clock
131
- var nsecs = options.nsecs != null ? options.nsecs : _lastNSecs + 1;
98
+ // Reset nsecs if clock regresses (new clockseq) or we've moved onto a new
99
+ // time interval
100
+ if ((dt < 0 || msecs > _lastMSecs) && options.nsecs === undefined) {
101
+ nsecs = 0;
102
+ }
132
103
 
133
- // Time since last uuid creation (in msecs)
134
- var dt = (msecs - _lastMSecs) + (nsecs - _lastNSecs)/10000;
104
+ // Per 4.2.1.2 Throw error if too many uuids are requested
105
+ if (nsecs >= 10000) {
106
+ throw new Error('uuid.v1(): Can\'t create more than 10M uuids/sec');
107
+ }
135
108
 
136
- // Per 4.2.1.2, Bump clockseq on clock regression
137
- if (dt < 0 && options.clockseq == null) {
138
- clockseq = clockseq + 1 & 0x3fff;
139
- }
109
+ _lastMSecs = msecs;
110
+ _lastNSecs = nsecs;
111
+ _clockseq = clockseq;
140
112
 
141
- // Reset nsecs if clock regresses (new clockseq) or we've moved onto a new
142
- // time interval
143
- if ((dt < 0 || msecs > _lastMSecs) && options.nsecs == null) {
144
- nsecs = 0;
145
- }
113
+ // Per 4.1.4 - Convert from unix epoch to Gregorian epoch
114
+ msecs += 12219292800000;
146
115
 
147
- // Per 4.2.1.2 Throw error if too many uuids are requested
148
- if (nsecs >= 10000) {
149
- throw new Error('uuid.v1(): Can\'t create more than 10M uuids/sec');
150
- }
116
+ // `time_low`
117
+ var tl = ((msecs & 0xfffffff) * 10000 + nsecs) % 0x100000000;
118
+ b[i++] = tl >>> 24 & 0xff;
119
+ b[i++] = tl >>> 16 & 0xff;
120
+ b[i++] = tl >>> 8 & 0xff;
121
+ b[i++] = tl & 0xff;
151
122
 
152
- _lastMSecs = msecs;
153
- _lastNSecs = nsecs;
154
- _clockseq = clockseq;
123
+ // `time_mid`
124
+ var tmh = (msecs / 0x100000000 * 10000) & 0xfffffff;
125
+ b[i++] = tmh >>> 8 & 0xff;
126
+ b[i++] = tmh & 0xff;
155
127
 
156
- // Per 4.1.4 - Convert from unix epoch to Gregorian epoch
157
- msecs += 12219292800000;
128
+ // `time_high_and_version`
129
+ b[i++] = tmh >>> 24 & 0xf | 0x10; // include version
130
+ b[i++] = tmh >>> 16 & 0xff;
158
131
 
159
- // `time_low`
160
- var tl = ((msecs & 0xfffffff) * 10000 + nsecs) % 0x100000000;
161
- b[i++] = tl >>> 24 & 0xff;
162
- b[i++] = tl >>> 16 & 0xff;
163
- b[i++] = tl >>> 8 & 0xff;
164
- b[i++] = tl & 0xff;
132
+ // `clock_seq_hi_and_reserved` (Per 4.2.2 - include variant)
133
+ b[i++] = clockseq >>> 8 | 0x80;
165
134
 
166
- // `time_mid`
167
- var tmh = (msecs / 0x100000000 * 10000) & 0xfffffff;
168
- b[i++] = tmh >>> 8 & 0xff;
169
- b[i++] = tmh & 0xff;
135
+ // `clock_seq_low`
136
+ b[i++] = clockseq & 0xff;
170
137
 
171
- // `time_high_and_version`
172
- b[i++] = tmh >>> 24 & 0xf | 0x10; // include version
173
- b[i++] = tmh >>> 16 & 0xff;
138
+ // `node`
139
+ var node = options.node || _nodeId;
140
+ for (var n = 0; n < 6; n++) {
141
+ b[i + n] = node[n];
142
+ }
174
143
 
175
- // `clock_seq_hi_and_reserved` (Per 4.2.2 - include variant)
176
- b[i++] = clockseq >>> 8 | 0x80;
144
+ return buf ? buf : unparse(b);
145
+ }
177
146
 
178
- // `clock_seq_low`
179
- b[i++] = clockseq & 0xff;
147
+ // **`v4()` - Generate random UUID**
180
148
 
181
- // `node`
182
- var node = options.node || _nodeId;
183
- for (var n = 0; n < 6; n++) {
184
- b[i + n] = node[n];
185
- }
149
+ // See https://github.com/broofa/node-uuid for API details
150
+ function v4(options, buf, offset) {
151
+ // Deprecated - 'format' argument, as supported in v1.2
152
+ var i = buf && offset || 0;
186
153
 
187
- return buf ? buf : unparse(b);
154
+ if (typeof(options) == 'string') {
155
+ buf = options == 'binary' ? new Array(16) : null;
156
+ options = null;
188
157
  }
158
+ options = options || {};
189
159
 
190
- // **`v4()` - Generate random UUID**
160
+ var rnds = options.random || (options.rng || _rng)();
191
161
 
192
- // See https://github.com/broofa/node-uuid for API details
193
- function v4(options, buf, offset) {
194
- // Deprecated - 'format' argument, as supported in v1.2
195
- var i = buf && offset || 0;
162
+ // Per 4.4, set bits for version and `clock_seq_hi_and_reserved`
163
+ rnds[6] = (rnds[6] & 0x0f) | 0x40;
164
+ rnds[8] = (rnds[8] & 0x3f) | 0x80;
196
165
 
197
- if (typeof(options) == 'string') {
198
- buf = options == 'binary' ? new BufferClass(16) : null;
199
- options = null;
166
+ // Copy bytes to buffer, if provided
167
+ if (buf) {
168
+ for (var ii = 0; ii < 16; ii++) {
169
+ buf[i + ii] = rnds[ii];
200
170
  }
201
- options = options || {};
202
-
203
- var rnds = options.random || (options.rng || _rng)();
204
-
205
- // Per 4.4, set bits for version and `clock_seq_hi_and_reserved`
206
- rnds[6] = (rnds[6] & 0x0f) | 0x40;
207
- rnds[8] = (rnds[8] & 0x3f) | 0x80;
171
+ }
208
172
 
209
- // Copy bytes to buffer, if provided
210
- if (buf) {
211
- for (var ii = 0; ii < 16; ii++) {
212
- buf[i + ii] = rnds[ii];
213
- }
214
- }
173
+ return buf || unparse(rnds);
174
+ }
215
175
 
216
- return buf || unparse(rnds);
217
- }
176
+ // Export public API
177
+ var uuid = v4;
178
+ uuid.v1 = v1;
179
+ uuid.v4 = v4;
180
+ uuid.parse = parse;
181
+ uuid.unparse = unparse;
218
182
 
219
- // Export public API
220
- var uuid = v4;
221
- uuid.v1 = v1;
222
- uuid.v4 = v4;
223
- uuid.parse = parse;
224
- uuid.unparse = unparse;
225
- uuid.BufferClass = BufferClass;
226
-
227
- if (_global.define && define.amd) {
228
- // Publish as AMD module
229
- define(function() {return uuid;});
230
- } else if (typeof(module) != 'undefined' && module.exports) {
231
- // Publish as node.js module
232
- module.exports = uuid;
233
- } else {
234
- // Publish as global (in browsers)
235
- var _previousRoot = _global.uuid;
236
-
237
- // **`noConflict()` - (browser only) to reset global 'uuid' var**
238
- uuid.noConflict = function() {
239
- _global.uuid = _previousRoot;
240
- return uuid;
241
- };
242
-
243
- _global.uuid = uuid;
244
- }
245
- }).call(this);
183
+ module.exports = uuid;
package/test/test.html DELETED
@@ -1,17 +0,0 @@
1
- <html>
2
- <head>
3
- <style>
4
- div {
5
- font-family: monospace;
6
- font-size: 8pt;
7
- }
8
- div.log {color: #444;}
9
- div.warn {color: #550;}
10
- div.error {color: #800; font-weight: bold;}
11
- </style>
12
- <script src="../uuid.js"></script>
13
- </head>
14
- <body>
15
- <script src="./test.js"></script>
16
- </body>
17
- </html>