-
-
Notifications
You must be signed in to change notification settings - Fork 35.5k
Expand file tree
/
Copy pathcrypto.md
More file actions
2916 lines (2440 loc) Β· 99.1 KB
/
crypto.md
File metadata and controls
2916 lines (2440 loc) Β· 99.1 KB
Edit and raw actions
OlderNewer
Β
1
# Crypto
2
3
<!--introduced_in=v0.3.6-->
4
5
> Stability: 2 - Stable
6
7
The `crypto` module provides cryptographic functionality that includes a set of
8
wrappers for OpenSSL's hash, HMAC, cipher, decipher, sign, and verify functions.
9
10
Use `require('crypto')` to access this module.
11
12
```js
13
const crypto = require('crypto');
14
15
const secret = 'abcdefg';
16
const hash = crypto.createHmac('sha256', secret)
17
.update('I love cupcakes')
18
.digest('hex');
19
console.log(hash);
20
// Prints:
21
// c0fa1bc00531bd78ef38c628449c5102aeabd49b5dc3a2a516ea6ea959d6658e
22
```
23
24
## Determining if crypto support is unavailable
25
26
It is possible for Node.js to be built without including support for the
27
`crypto` module. In such cases, calling `require('crypto')` will result in an
28
error being thrown.
29
30
```js
31
let crypto;
32
try {
33
crypto = require('crypto');
34
} catch (err) {
35
console.log('crypto support is disabled!');
36
}
37
```
38
39
## Class: Certificate
40
<!-- YAML
41
added: v0.11.8
42
-->
43
44
SPKAC is a Certificate Signing Request mechanism originally implemented by
45
Netscape and was specified formally as part of [HTML5's `keygen` element][].
46
47
Note that `<keygen>` is deprecated since [HTML 5.2][] and new projects
48
should not use this element anymore.
49
50
The `crypto` module provides the `Certificate` class for working with SPKAC
51
data. The most common usage is handling output generated by the HTML5
52
`<keygen>` element. Node.js uses [OpenSSL's SPKAC implementation][] internally.
53
54
### Certificate.exportChallenge(spkac)
55
<!-- YAML
56
added: v9.0.0
57
-->
58
* `spkac` {string | Buffer | TypedArray | DataView}
59
* Returns: {Buffer} The challenge component of the `spkac` data structure, which
60
includes a public key and a challenge.
61
62
```js
63
const { Certificate } = require('crypto');
64
const spkac = getSpkacSomehow();
65
const challenge = Certificate.exportChallenge(spkac);
66
console.log(challenge.toString('utf8'));
67
// Prints: the challenge as a UTF8 string
68
```
69
70
### Certificate.exportPublicKey(spkac[, encoding])
71
<!-- YAML
72
added: v9.0.0
73
-->
74
* `spkac` {string | Buffer | TypedArray | DataView}
75
* `encoding` {string}
76
* Returns: {Buffer} The public key component of the `spkac` data structure,
77
which includes a public key and a challenge.
78
79
```js
80
const { Certificate } = require('crypto');
81
const spkac = getSpkacSomehow();
82
const publicKey = Certificate.exportPublicKey(spkac);
83
console.log(publicKey);
84
// Prints: the public key as <Buffer ...>
85
```
86
87
### Certificate.verifySpkac(spkac)
88
<!-- YAML
89
added: v9.0.0
90
-->
91
* `spkac` {Buffer | TypedArray | DataView}
92
* Returns: {boolean} `true` if the given `spkac` data structure is valid,
93
`false` otherwise.
94
95
```js
96
const { Certificate } = require('crypto');
97
const spkac = getSpkacSomehow();
98
console.log(Certificate.verifySpkac(Buffer.from(spkac)));
99
// Prints: true or false
100
```
101
102
### Legacy API
103
104
As a still supported legacy interface, it is possible (but not recommended) to
105
create new instances of the `crypto.Certificate` class as illustrated in the
106
examples below.
107
108
#### new crypto.Certificate()
109
110
Instances of the `Certificate` class can be created using the `new` keyword
111
or by calling `crypto.Certificate()` as a function:
112
113
```js
114
const crypto = require('crypto');
115
116
const cert1 = new crypto.Certificate();
117
const cert2 = crypto.Certificate();
118
```
119
120
#### certificate.exportChallenge(spkac)
121
<!-- YAML
122
added: v0.11.8
123
-->
124
* `spkac` {string | Buffer | TypedArray | DataView}
125
* Returns: {Buffer} The challenge component of the `spkac` data structure, which
126
includes a public key and a challenge.
127
128
```js
129
const cert = require('crypto').Certificate();
130
const spkac = getSpkacSomehow();
131
const challenge = cert.exportChallenge(spkac);
132
console.log(challenge.toString('utf8'));
133
// Prints: the challenge as a UTF8 string
134
```
135
136
#### certificate.exportPublicKey(spkac)
137
<!-- YAML
138
added: v0.11.8
139
-->
140
* `spkac` {string | Buffer | TypedArray | DataView}
141
* Returns: {Buffer} The public key component of the `spkac` data structure,
142
which includes a public key and a challenge.
143
144
```js
145
const cert = require('crypto').Certificate();
146
const spkac = getSpkacSomehow();
147
const publicKey = cert.exportPublicKey(spkac);
148
console.log(publicKey);
149
// Prints: the public key as <Buffer ...>
150
```
151
152
#### certificate.verifySpkac(spkac)
153
<!-- YAML
154
added: v0.11.8
155
-->
156
* `spkac` {Buffer | TypedArray | DataView}
157
* Returns: {boolean} `true` if the given `spkac` data structure is valid,
158
`false` otherwise.
159
160
```js
161
const cert = require('crypto').Certificate();
162
const spkac = getSpkacSomehow();
163
console.log(cert.verifySpkac(Buffer.from(spkac)));
164
// Prints: true or false
165
```
166
167
## Class: Cipher
168
<!-- YAML
169
added: v0.1.94
170
-->
171
172
Instances of the `Cipher` class are used to encrypt data. The class can be
173
used in one of two ways:
174
175
- As a [stream][] that is both readable and writable, where plain unencrypted
176
data is written to produce encrypted data on the readable side, or
177
- Using the [`cipher.update()`][] and [`cipher.final()`][] methods to produce
178
the encrypted data.
179
180
The [`crypto.createCipher()`][] or [`crypto.createCipheriv()`][] methods are
181
used to create `Cipher` instances. `Cipher` objects are not to be created
182
directly using the `new` keyword.
183
184
Example: Using `Cipher` objects as streams:
185
186
```js
187
const crypto = require('crypto');
188
const cipher = crypto.createCipher('aes192', 'a password');
189
190
let encrypted = '';
191
cipher.on('readable', () => {
192
const data = cipher.read();
193
if (data)
194
encrypted += data.toString('hex');
195
});
196
cipher.on('end', () => {
197
console.log(encrypted);
198
// Prints: ca981be48e90867604588e75d04feabb63cc007a8f8ad89b10616ed84d815504
199
});
200
201
cipher.write('some clear text data');
202
cipher.end();
203
```
204
205
Example: Using `Cipher` and piped streams:
206
207
```js
208
const crypto = require('crypto');
209
const fs = require('fs');
210
const cipher = crypto.createCipher('aes192', 'a password');
211
212
const input = fs.createReadStream('test.js');
213
const output = fs.createWriteStream('test.enc');
214
215
input.pipe(cipher).pipe(output);
216
```
217
218
Example: Using the [`cipher.update()`][] and [`cipher.final()`][] methods:
219
220
```js
221
const crypto = require('crypto');
222
const cipher = crypto.createCipher('aes192', 'a password');
223
224
let encrypted = cipher.update('some clear text data', 'utf8', 'hex');
225
encrypted += cipher.final('hex');
226
console.log(encrypted);
227
// Prints: ca981be48e90867604588e75d04feabb63cc007a8f8ad89b10616ed84d815504
228
```
229
230
### cipher.final([outputEncoding])
231
<!-- YAML
232
added: v0.1.94
233
-->
234
* `outputEncoding` {string}
235
* Returns: {Buffer | string} Any remaining enciphered contents.
236
If `outputEncoding` is one of `'latin1'`, `'base64'` or `'hex'`, a string is
237
returned. If an `outputEncoding` is not provided, a [`Buffer`][] is returned.
238
239
Once the `cipher.final()` method has been called, the `Cipher` object can no
240
longer be used to encrypt data. Attempts to call `cipher.final()` more than
241
once will result in an error being thrown.
242
243
### cipher.setAAD(buffer[, options])
244
<!-- YAML
245
added: v1.0.0
246
-->
247
* `buffer` {Buffer}
248
* `options` {Object} [`stream.transform` options][]
249
- `plaintextLength` {number}
250
* Returns: {Cipher} for method chaining.
251
252
When using an authenticated encryption mode (`GCM`, `CCM` and `OCB` are
253
currently supported), the `cipher.setAAD()` method sets the value used for the
254
_additional authenticated data_ (AAD) input parameter.
255
256
The `options` argument is optional for `GCM` and `OCB`. When using `CCM`, the
257
`plaintextLength` option must be specified and its value must match the length
258
of the plaintext in bytes. See [CCM mode][].
259
260
The `cipher.setAAD()` method must be called before [`cipher.update()`][].
261
262
### cipher.getAuthTag()
263
<!-- YAML
264
added: v1.0.0
265
-->
266
* Returns: {Buffer} When using an authenticated encryption mode (`GCM`, `CCM`
267
and `OCB` are currently supported), the `cipher.getAuthTag()` method returns a
268
[`Buffer`][] containing the _authentication tag_ that has been computed from
269
the given data.
270
271
The `cipher.getAuthTag()` method should only be called after encryption has
272
been completed using the [`cipher.final()`][] method.
273
274
### cipher.setAutoPadding([autoPadding])
275
<!-- YAML
276
added: v0.7.1
277
-->
278
* `autoPadding` {boolean} **Default:** `true`
279
* Returns: {Cipher} for method chaining.
280
281
When using block encryption algorithms, the `Cipher` class will automatically
282
add padding to the input data to the appropriate block size. To disable the
283
default padding call `cipher.setAutoPadding(false)`.
284
285
When `autoPadding` is `false`, the length of the entire input data must be a
286
multiple of the cipher's block size or [`cipher.final()`][] will throw an error.
287
Disabling automatic padding is useful for non-standard padding, for instance
288
using `0x0` instead of PKCS padding.
289
290
The `cipher.setAutoPadding()` method must be called before
291
[`cipher.final()`][].
292
293
### cipher.update(data[, inputEncoding][, outputEncoding])
294
<!-- YAML
295
added: v0.1.94
296
changes:
297
- version: v6.0.0
298
pr-url: https://github.com/nodejs/node/pull/5522
299
description: The default `inputEncoding` changed from `binary` to `utf8`.
300
-->
301
* `data` {string | Buffer | TypedArray | DataView}
302
* `inputEncoding` {string}
303
* `outputEncoding` {string}
304
* Returns: {Buffer | string}
305
306
Updates the cipher with `data`. If the `inputEncoding` argument is given,
307
its value must be one of `'utf8'`, `'ascii'`, or `'latin1'` and the `data`
308
argument is a string using the specified encoding. If the `inputEncoding`
309
argument is not given, `data` must be a [`Buffer`][], `TypedArray`, or
310
`DataView`. If `data` is a [`Buffer`][], `TypedArray`, or `DataView`, then
311
`inputEncoding` is ignored.
312
313
The `outputEncoding` specifies the output format of the enciphered
314
data, and can be `'latin1'`, `'base64'` or `'hex'`. If the `outputEncoding`
315
is specified, a string using the specified encoding is returned. If no
316
`outputEncoding` is provided, a [`Buffer`][] is returned.
317
318
The `cipher.update()` method can be called multiple times with new data until
319
[`cipher.final()`][] is called. Calling `cipher.update()` after
320
[`cipher.final()`][] will result in an error being thrown.
321
322
## Class: Decipher
323
<!-- YAML
324
added: v0.1.94
325
-->
326
327
Instances of the `Decipher` class are used to decrypt data. The class can be
328
used in one of two ways:
329
330
- As a [stream][] that is both readable and writable, where plain encrypted
331
data is written to produce unencrypted data on the readable side, or
332
- Using the [`decipher.update()`][] and [`decipher.final()`][] methods to
333
produce the unencrypted data.
334
335
The [`crypto.createDecipher()`][] or [`crypto.createDecipheriv()`][] methods are
336
used to create `Decipher` instances. `Decipher` objects are not to be created
337
directly using the `new` keyword.
338
339
Example: Using `Decipher` objects as streams:
340
341
```js
342
const crypto = require('crypto');
343
const decipher = crypto.createDecipher('aes192', 'a password');
344
345
let decrypted = '';
346
decipher.on('readable', () => {
347
const data = decipher.read();
348
if (data)
349
decrypted += data.toString('utf8');
350
});
351
decipher.on('end', () => {
352
console.log(decrypted);
353
// Prints: some clear text data
354
});
355
356
const encrypted =
357
'ca981be48e90867604588e75d04feabb63cc007a8f8ad89b10616ed84d815504';
358
decipher.write(encrypted, 'hex');
359
decipher.end();
360
```
361
362
Example: Using `Decipher` and piped streams:
363
364
```js
365
const crypto = require('crypto');
366
const fs = require('fs');
367
const decipher = crypto.createDecipher('aes192', 'a password');
368
369
const input = fs.createReadStream('test.enc');
370
const output = fs.createWriteStream('test.js');
371
372
input.pipe(decipher).pipe(output);
373
```
374
375
Example: Using the [`decipher.update()`][] and [`decipher.final()`][] methods:
376
377
```js
378
const crypto = require('crypto');
379
const decipher = crypto.createDecipher('aes192', 'a password');
380
381
const encrypted =
382
'ca981be48e90867604588e75d04feabb63cc007a8f8ad89b10616ed84d815504';
383
let decrypted = decipher.update(encrypted, 'hex', 'utf8');
384
decrypted += decipher.final('utf8');
385
console.log(decrypted);
386
// Prints: some clear text data
387
```
388
389
### decipher.final([outputEncoding])
390
<!-- YAML
391
added: v0.1.94
392
-->
393
* `outputEncoding` {string}
394
* Returns: {Buffer | string} Any remaining deciphered contents.
395
If `outputEncoding` is one of `'latin1'`, `'ascii'` or `'utf8'`, a string is
396
returned. If an `outputEncoding` is not provided, a [`Buffer`][] is returned.
397
398
Once the `decipher.final()` method has been called, the `Decipher` object can
399
no longer be used to decrypt data. Attempts to call `decipher.final()` more
400
than once will result in an error being thrown.
401
402
### decipher.setAAD(buffer[, options])
403
<!-- YAML
404
added: v1.0.0
405
changes:
406
- version: v7.2.0
407
pr-url: https://github.com/nodejs/node/pull/9398
408
description: This method now returns a reference to `decipher`.
409
-->
410
* `buffer` {Buffer | TypedArray | DataView}
411
* `options` {Object} [`stream.transform` options][]
412
- `plaintextLength` {number}
413
* Returns: {Decipher} for method chaining.
414
415
When using an authenticated encryption mode (`GCM`, `CCM` and `OCB` are
416
currently supported), the `decipher.setAAD()` method sets the value used for the
417
_additional authenticated data_ (AAD) input parameter.
418
419
The `options` argument is optional for `GCM`. When using `CCM`, the
420
`plaintextLength` option must be specified and its value must match the length
421
of the plaintext in bytes. See [CCM mode][].
422
423
The `decipher.setAAD()` method must be called before [`decipher.update()`][].
424
425
### decipher.setAuthTag(buffer)
426
<!-- YAML
427
added: v1.0.0
428
changes:
429
- version: v11.0.0
430
pr-url: https://github.com/nodejs/node/pull/17825
431
description: This method now throws if the GCM tag length is invalid.
432
- version: v7.2.0
433
pr-url: https://github.com/nodejs/node/pull/9398
434
description: This method now returns a reference to `decipher`.
435
-->
436
* `buffer` {Buffer | TypedArray | DataView}
437
* Returns: {Decipher} for method chaining.
438
439
When using an authenticated encryption mode (`GCM`, `CCM` and `OCB` are
440
currently supported), the `decipher.setAuthTag()` method is used to pass in the
441
received _authentication tag_. If no tag is provided, or if the cipher text
442
has been tampered with, [`decipher.final()`][] will throw, indicating that the
443
cipher text should be discarded due to failed authentication. If the tag length
444
is invalid according to [NIST SP 800-38D][] or does not match the value of the
445
`authTagLength` option, `decipher.setAuthTag()` will throw an error.
446
447
The `decipher.setAuthTag()` method must be called before
448
[`decipher.final()`][] and can only be called once.
449
450
### decipher.setAutoPadding([autoPadding])
451
<!-- YAML
452
added: v0.7.1
453
-->
454
* `autoPadding` {boolean} **Default:** `true`
455
* Returns: {Decipher} for method chaining.
456
457
When data has been encrypted without standard block padding, calling
458
`decipher.setAutoPadding(false)` will disable automatic padding to prevent
459
[`decipher.final()`][] from checking for and removing padding.
460
461
Turning auto padding off will only work if the input data's length is a
462
multiple of the ciphers block size.
463
464
The `decipher.setAutoPadding()` method must be called before
465
[`decipher.final()`][].
466
467
### decipher.update(data[, inputEncoding][, outputEncoding])
468
<!-- YAML
469
added: v0.1.94
470
changes:
471
- version: v6.0.0
472
pr-url: https://github.com/nodejs/node/pull/5522
473
description: The default `inputEncoding` changed from `binary` to `utf8`.
474
-->
475
* `data` {string | Buffer | TypedArray | DataView}
476
* `inputEncoding` {string}
477
* `outputEncoding` {string}
478
* Returns: {Buffer | string}
479
480
Updates the decipher with `data`. If the `inputEncoding` argument is given,
481
its value must be one of `'latin1'`, `'base64'`, or `'hex'` and the `data`
482
argument is a string using the specified encoding. If the `inputEncoding`
483
argument is not given, `data` must be a [`Buffer`][]. If `data` is a
484
[`Buffer`][] then `inputEncoding` is ignored.
485
486
The `outputEncoding` specifies the output format of the enciphered
487
data, and can be `'latin1'`, `'ascii'` or `'utf8'`. If the `outputEncoding`
488
is specified, a string using the specified encoding is returned. If no
489
`outputEncoding` is provided, a [`Buffer`][] is returned.
490
491
The `decipher.update()` method can be called multiple times with new data until
492
[`decipher.final()`][] is called. Calling `decipher.update()` after
493
[`decipher.final()`][] will result in an error being thrown.
494
495
## Class: DiffieHellman
496
<!-- YAML
497
added: v0.5.0
498
-->
499
500
The `DiffieHellman` class is a utility for creating Diffie-Hellman key
501
exchanges.
502
503
Instances of the `DiffieHellman` class can be created using the
504
[`crypto.createDiffieHellman()`][] function.
505
506
```js
507
const crypto = require('crypto');
508
const assert = require('assert');
509
510
// Generate Alice's keys...
511
const alice = crypto.createDiffieHellman(2048);
512
const aliceKey = alice.generateKeys();
513
514
// Generate Bob's keys...
515
const bob = crypto.createDiffieHellman(alice.getPrime(), alice.getGenerator());
516
const bobKey = bob.generateKeys();
517
518
// Exchange and generate the secret...
519
const aliceSecret = alice.computeSecret(bobKey);
520
const bobSecret = bob.computeSecret(aliceKey);
521
522
// OK
523
assert.strictEqual(aliceSecret.toString('hex'), bobSecret.toString('hex'));
524
```
525
526
### diffieHellman.computeSecret(otherPublicKey[, inputEncoding][, outputEncoding])
527
<!-- YAML
528
added: v0.5.0
529
-->
530
* `otherPublicKey` {string | Buffer | TypedArray | DataView}
531
* `inputEncoding` {string}
532
* `outputEncoding` {string}
533
* Returns: {Buffer | string}
534
535
Computes the shared secret using `otherPublicKey` as the other
536
party's public key and returns the computed shared secret. The supplied
537
key is interpreted using the specified `inputEncoding`, and secret is
538
encoded using specified `outputEncoding`. Encodings can be
539
`'latin1'`, `'hex'`, or `'base64'`. If the `inputEncoding` is not
540
provided, `otherPublicKey` is expected to be a [`Buffer`][],
541
`TypedArray`, or `DataView`.
542
543
If `outputEncoding` is given a string is returned; otherwise, a
544
[`Buffer`][] is returned.
545
546
### diffieHellman.generateKeys([encoding])
547
<!-- YAML
548
added: v0.5.0
549
-->
550
* `encoding` {string}
551
* Returns: {Buffer | string}
552
553
Generates private and public Diffie-Hellman key values, and returns
554
the public key in the specified `encoding`. This key should be
555
transferred to the other party. Encoding can be `'latin1'`, `'hex'`,
556
or `'base64'`. If `encoding` is provided a string is returned; otherwise a
557
[`Buffer`][] is returned.
558
559
### diffieHellman.getGenerator([encoding])
560
<!-- YAML
561
added: v0.5.0
562
-->
563
* `encoding` {string}
564
* Returns: {Buffer | string}
565
566
Returns the Diffie-Hellman generator in the specified `encoding`, which can
567
be `'latin1'`, `'hex'`, or `'base64'`. If `encoding` is provided a string is
568
returned; otherwise a [`Buffer`][] is returned.
569
570
### diffieHellman.getPrime([encoding])
571
<!-- YAML
572
added: v0.5.0
573
-->
574
* `encoding` {string}
575
* Returns: {Buffer | string}
576
577
Returns the Diffie-Hellman prime in the specified `encoding`, which can
578
be `'latin1'`, `'hex'`, or `'base64'`. If `encoding` is provided a string is
579
returned; otherwise a [`Buffer`][] is returned.
580
581
### diffieHellman.getPrivateKey([encoding])
582
<!-- YAML
583
added: v0.5.0
584
-->
585
* `encoding` {string}
586
* Returns: {Buffer | string}
587
588
Returns the Diffie-Hellman private key in the specified `encoding`,
589
which can be `'latin1'`, `'hex'`, or `'base64'`. If `encoding` is provided a
590
string is returned; otherwise a [`Buffer`][] is returned.
591
592
### diffieHellman.getPublicKey([encoding])
593
<!-- YAML
594
added: v0.5.0
595
-->
596
* `encoding` {string}
597
* Returns: {Buffer | string}
598
599
Returns the Diffie-Hellman public key in the specified `encoding`, which
600
can be `'latin1'`, `'hex'`, or `'base64'`. If `encoding` is provided a
601
string is returned; otherwise a [`Buffer`][] is returned.
602
603
### diffieHellman.setPrivateKey(privateKey[, encoding])
604
<!-- YAML
605
added: v0.5.0
606
-->
607
* `privateKey` {string | Buffer | TypedArray | DataView}
608
* `encoding` {string}
609
610
Sets the Diffie-Hellman private key. If the `encoding` argument is provided
611
and is either `'latin1'`, `'hex'`, or `'base64'`, `privateKey` is expected
612
to be a string. If no `encoding` is provided, `privateKey` is expected
613
to be a [`Buffer`][], `TypedArray`, or `DataView`.
614
615
### diffieHellman.setPublicKey(publicKey[, encoding])
616
<!-- YAML
617
added: v0.5.0
618
-->
619
* `publicKey` {string | Buffer | TypedArray | DataView}
620
* `encoding` {string}
621
622
Sets the Diffie-Hellman public key. If the `encoding` argument is provided
623
and is either `'latin1'`, `'hex'` or `'base64'`, `publicKey` is expected
624
to be a string. If no `encoding` is provided, `publicKey` is expected
625
to be a [`Buffer`][], `TypedArray`, or `DataView`.
626
627
### diffieHellman.verifyError
628
<!-- YAML
629
added: v0.11.12
630
-->
631
632
A bit field containing any warnings and/or errors resulting from a check
633
performed during initialization of the `DiffieHellman` object.
634
635
The following values are valid for this property (as defined in `constants`
636
module):
637
638
* `DH_CHECK_P_NOT_SAFE_PRIME`
639
* `DH_CHECK_P_NOT_PRIME`
640
* `DH_UNABLE_TO_CHECK_GENERATOR`
641
* `DH_NOT_SUITABLE_GENERATOR`
642
643
## Class: ECDH
644
<!-- YAML
645
added: v0.11.14
646
-->
647
648
The `ECDH` class is a utility for creating Elliptic Curve Diffie-Hellman (ECDH)
649
key exchanges.
650
651
Instances of the `ECDH` class can be created using the
652
[`crypto.createECDH()`][] function.
653
654
```js
655
const crypto = require('crypto');
656
const assert = require('assert');
657
658
// Generate Alice's keys...
659
const alice = crypto.createECDH('secp521r1');
660
const aliceKey = alice.generateKeys();
661
662
// Generate Bob's keys...
663
const bob = crypto.createECDH('secp521r1');
664
const bobKey = bob.generateKeys();
665
666
// Exchange and generate the secret...
667
const aliceSecret = alice.computeSecret(bobKey);
668
const bobSecret = bob.computeSecret(aliceKey);
669
670
assert.strictEqual(aliceSecret.toString('hex'), bobSecret.toString('hex'));
671
// OK
672
```
673
674
### Class Method: ECDH.convertKey(key, curve[, inputEncoding[, outputEncoding[, format]]])
675
<!-- YAML
676
added: v10.0.0
677
-->
678
679
* `key` {string | Buffer | TypedArray | DataView}
680
* `curve` {string}
681
* `inputEncoding` {string}
682
* `outputEncoding` {string}
683
* `format` {string} **Default:** `'uncompressed'`
684
* Returns: {Buffer | string}
685
686
Converts the EC Diffie-Hellman public key specified by `key` and `curve` to the
687
format specified by `format`. The `format` argument specifies point encoding
688
and can be `'compressed'`, `'uncompressed'` or `'hybrid'`. The supplied key is
689
interpreted using the specified `inputEncoding`, and the returned key is encoded
690
using the specified `outputEncoding`. Encodings can be `'latin1'`, `'hex'`,
691
or `'base64'`.
692
693
Use [`crypto.getCurves()`][] to obtain a list of available curve names.
694
On recent OpenSSL releases, `openssl ecparam -list_curves` will also display
695
the name and description of each available elliptic curve.
696
697
If `format` is not specified the point will be returned in `'uncompressed'`
698
format.
699
700
If the `inputEncoding` is not provided, `key` is expected to be a [`Buffer`][],
701
`TypedArray`, or `DataView`.
702
703
Example (uncompressing a key):
704
705
```js
706
const { createECDH, ECDH } = require('crypto');
707
708
const ecdh = createECDH('secp256k1');
709
ecdh.generateKeys();
710
711
const compressedKey = ecdh.getPublicKey('hex', 'compressed');
712
713
const uncompressedKey = ECDH.convertKey(compressedKey,
714
'secp256k1',
715
'hex',
716
'hex',
717
'uncompressed');
718
719
// the converted key and the uncompressed public key should be the same
720
console.log(uncompressedKey === ecdh.getPublicKey('hex'));
721
```
722
723
### ecdh.computeSecret(otherPublicKey[, inputEncoding][, outputEncoding])
724
<!-- YAML
725
added: v0.11.14
726
changes:
727
- version: v6.0.0
728
pr-url: https://github.com/nodejs/node/pull/5522
729
description: The default `inputEncoding` changed from `binary` to `utf8`
730
- version: v10.0.0
731
pr-url: https://github.com/nodejs/node/pull/16849
732
description: Changed error format to better support invalid public key
733
error
734
-->
735
* `otherPublicKey` {string | Buffer | TypedArray | DataView}
736
* `inputEncoding` {string}
737
* `outputEncoding` {string}
738
* Returns: {Buffer | string}
739
740
Computes the shared secret using `otherPublicKey` as the other
741
party's public key and returns the computed shared secret. The supplied
742
key is interpreted using specified `inputEncoding`, and the returned secret
743
is encoded using the specified `outputEncoding`. Encodings can be
744
`'latin1'`, `'hex'`, or `'base64'`. If the `inputEncoding` is not
745
provided, `otherPublicKey` is expected to be a [`Buffer`][], `TypedArray`, or
746
`DataView`.
747
748
If `outputEncoding` is given a string will be returned; otherwise a
749
[`Buffer`][] is returned.
750
751
`ecdh.computeSecret` will throw an
752
`ERR_CRYPTO_ECDH_INVALID_PUBLIC_KEY` error when `otherPublicKey`
753
lies outside of the elliptic curve. Since `otherPublicKey` is
754
usually supplied from a remote user over an insecure network,
755
its recommended for developers to handle this exception accordingly.
756
757
### ecdh.generateKeys([encoding[, format]])
758
<!-- YAML
759
added: v0.11.14
760
-->
761
* `encoding` {string}
762
* `format` {string} **Default:** `'uncompressed'`
763
* Returns: {Buffer | string}
764
765
Generates private and public EC Diffie-Hellman key values, and returns
766
the public key in the specified `format` and `encoding`. This key should be
767
transferred to the other party.
768
769
The `format` argument specifies point encoding and can be `'compressed'` or
770
`'uncompressed'`. If `format` is not specified, the point will be returned in
771
`'uncompressed'` format.
772
773
The `encoding` argument can be `'latin1'`, `'hex'`, or `'base64'`. If
774
`encoding` is provided a string is returned; otherwise a [`Buffer`][]
775
is returned.
776
777
### ecdh.getPrivateKey([encoding])
778
<!-- YAML
779
added: v0.11.14
780
-->
781
* `encoding` {string}
782
* Returns: {Buffer | string} The EC Diffie-Hellman private key in the specified
783
`encoding`, which can be `'latin1'`, `'hex'`, or `'base64'`. If `encoding`
784
is provided a string is returned; otherwise a [`Buffer`][] is returned.
785
786
### ecdh.getPublicKey([encoding][, format])
787
<!-- YAML
788
added: v0.11.14
789
-->
790
* `encoding` {string}
791
* `format` {string} **Default:** `'uncompressed'`
792
* Returns: {Buffer | string} The EC Diffie-Hellman public key in the specified
793
`encoding` and `format`.
794
795
The `format` argument specifies point encoding and can be `'compressed'` or
796
`'uncompressed'`. If `format` is not specified the point will be returned in
797
`'uncompressed'` format.
798
799
The `encoding` argument can be `'latin1'`, `'hex'`, or `'base64'`. If
800
`encoding` is specified, a string is returned; otherwise a [`Buffer`][] is
801
returned.
802
803
### ecdh.setPrivateKey(privateKey[, encoding])
804
<!-- YAML
805
added: v0.11.14
806
-->
807
* `privateKey` {string | Buffer | TypedArray | DataView}
808
* `encoding` {string}
809
810
Sets the EC Diffie-Hellman private key. The `encoding` can be `'latin1'`,
811
`'hex'` or `'base64'`. If `encoding` is provided, `privateKey` is expected
812
to be a string; otherwise `privateKey` is expected to be a [`Buffer`][],
813
`TypedArray`, or `DataView`.
814
815
If `privateKey` is not valid for the curve specified when the `ECDH` object was
816
created, an error is thrown. Upon setting the private key, the associated
817
public point (key) is also generated and set in the `ECDH` object.
818
819
### ecdh.setPublicKey(publicKey[, encoding])
820
<!-- YAML
821
added: v0.11.14
822
deprecated: v5.2.0
823
-->
824
825
> Stability: 0 - Deprecated
826
827
* `publicKey` {string | Buffer | TypedArray | DataView}
828
* `encoding` {string}
829
830
Sets the EC Diffie-Hellman public key. Key encoding can be `'latin1'`,
831
`'hex'` or `'base64'`. If `encoding` is provided `publicKey` is expected to
832
be a string; otherwise a [`Buffer`][], `TypedArray`, or `DataView` is expected.
833
834
Note that there is not normally a reason to call this method because `ECDH`
835
only requires a private key and the other party's public key to compute the
836
shared secret. Typically either [`ecdh.generateKeys()`][] or
837
[`ecdh.setPrivateKey()`][] will be called. The [`ecdh.setPrivateKey()`][] method
838
attempts to generate the public point/key associated with the private key being
839
set.
840
841
Example (obtaining a shared secret):
842
843
```js
844
const crypto = require('crypto');
845
const alice = crypto.createECDH('secp256k1');
846
const bob = crypto.createECDH('secp256k1');
847
848
// This is a shortcut way of specifying one of Alice's previous private
849
// keys. It would be unwise to use such a predictable private key in a real
850
// application.
851
alice.setPrivateKey(
852
crypto.createHash('sha256').update('alice', 'utf8').digest()
853
);
854
855
// Bob uses a newly generated cryptographically strong
856
// pseudorandom key pair
857
bob.generateKeys();
858
859
const aliceSecret = alice.computeSecret(bob.getPublicKey(), null, 'hex');
860
const bobSecret = bob.computeSecret(alice.getPublicKey(), null, 'hex');
861
862
// aliceSecret and bobSecret should be the same shared secret value
863
console.log(aliceSecret === bobSecret);
864
```
865
866
## Class: Hash
867
<!-- YAML
868
added: v0.1.92
869
-->
870
871
The `Hash` class is a utility for creating hash digests of data. It can be
872
used in one of two ways:
873
874
- As a [stream][] that is both readable and writable, where data is written
875
to produce a computed hash digest on the readable side, or
876
- Using the [`hash.update()`][] and [`hash.digest()`][] methods to produce the
877
computed hash.
878
879
The [`crypto.createHash()`][] method is used to create `Hash` instances. `Hash`
880
objects are not to be created directly using the `new` keyword.
881
882
Example: Using `Hash` objects as streams:
883
884
```js
885
const crypto = require('crypto');
886
const hash = crypto.createHash('sha256');
887
888
hash.on('readable', () => {
889
const data = hash.read();
890
if (data) {
891
console.log(data.toString('hex'));
892
// Prints:
893
// 6a2da20943931e9834fc12cfe5bb47bbd9ae43489a30726962b576f4e3993e50
894
}
895
});
896
897
hash.write('some data to hash');
898
hash.end();
899
```
900
901
Example: Using `Hash` and piped streams:
902
903
```js
904
const crypto = require('crypto');
905
const fs = require('fs');
906
const hash = crypto.createHash('sha256');
907
908
const input = fs.createReadStream('test.js');
909
input.pipe(hash).pipe(process.stdout);
910
```
911
912
Example: Using the [`hash.update()`][] and [`hash.digest()`][] methods:
913
914
```js
915
const crypto = require('crypto');
916
const hash = crypto.createHash('sha256');
917
918
hash.update('some data to hash');
919
console.log(hash.digest('hex'));
920
// Prints:
921
// 6a2da20943931e9834fc12cfe5bb47bbd9ae43489a30726962b576f4e3993e50
922
```
923
924
### hash.digest([encoding])
925
<!-- YAML
926
added: v0.1.92
927
-->
928
* `encoding` {string}
929
* Returns: {Buffer | string}
930
931
Calculates the digest of all of the data passed to be hashed (using the
932
[`hash.update()`][] method). The `encoding` can be `'hex'`, `'latin1'` or
933
`'base64'`. If `encoding` is provided a string will be returned; otherwise
934
a [`Buffer`][] is returned.
935
936
The `Hash` object can not be used again after `hash.digest()` method has been
937
called. Multiple calls will cause an error to be thrown.
938
939
### hash.update(data[, inputEncoding])
940
<!-- YAML
941
added: v0.1.92
942
changes:
943
- version: v6.0.0
944
pr-url: https://github.com/nodejs/node/pull/5522
945
description: The default `inputEncoding` changed from `binary` to `utf8`.
946
-->
947
* `data` {string | Buffer | TypedArray | DataView}
948
* `inputEncoding` {string}
949
950
Updates the hash content with the given `data`, the encoding of which
951
is given in `inputEncoding` and can be `'utf8'`, `'ascii'` or
952
`'latin1'`. If `encoding` is not provided, and the `data` is a string, an
953
encoding of `'utf8'` is enforced. If `data` is a [`Buffer`][], `TypedArray`, or
954
`DataView`, then `inputEncoding` is ignored.
955
956
This can be called many times with new data as it is streamed.
957
958
## Class: Hmac
959
<!-- YAML
960
added: v0.1.94
961
-->
962
963
The `Hmac` Class is a utility for creating cryptographic HMAC digests. It can
964
be used in one of two ways:
965
966
- As a [stream][] that is both readable and writable, where data is written
967
to produce a computed HMAC digest on the readable side, or
968
- Using the [`hmac.update()`][] and [`hmac.digest()`][] methods to produce the
969
computed HMAC digest.
970
971
The [`crypto.createHmac()`][] method is used to create `Hmac` instances. `Hmac`
972
objects are not to be created directly using the `new` keyword.
973
974
Example: Using `Hmac` objects as streams:
975
976
```js
977
const crypto = require('crypto');
978
const hmac = crypto.createHmac('sha256', 'a secret');
979
980
hmac.on('readable', () => {
981
const data = hmac.read();
982
if (data) {
983
console.log(data.toString('hex'));
984
// Prints:
985
// 7fd04df92f636fd450bc841c9418e5825c17f33ad9c87c518115a45971f7f77e
986
}
987
});
988
989
hmac.write('some data to hash');
990
hmac.end();
991
```
992
993
Example: Using `Hmac` and piped streams:
994
995
```js
996
const crypto = require('crypto');
997
const fs = require('fs');
998
const hmac = crypto.createHmac('sha256', 'a secret');
999
1000
const input = fs.createReadStream('test.js');