otplib 12.0.0-1 → 12.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/README.md +115 -388
- package/core.d.ts +1 -0
- package/core.js +23 -0
- package/index.d.ts +1 -0
- package/index.js +23 -0
- package/package.json +16 -98
- package/v11.d.ts +1 -0
- package/v11.js +23 -0
- package/authenticator/authenticator.d.ts +0 -145
- package/authenticator/index.d.ts +0 -1
- package/authenticator/index.js +0 -92
- package/authenticator-async/authenticator.d.ts +0 -34
- package/authenticator-async/index.d.ts +0 -1
- package/authenticator-async/index.js +0 -62
- package/core/index.d.ts +0 -3
- package/core/index.js +0 -41
- package/core-async/index.d.ts +0 -11
- package/core-async/index.js +0 -62
- package/hotp/hotp.d.ts +0 -128
- package/hotp/index.d.ts +0 -2
- package/hotp/index.js +0 -224
- package/hotp/utils.d.ts +0 -208
- package/hotp-async/hotp.d.ts +0 -33
- package/hotp-async/index.d.ts +0 -1
- package/hotp-async/index.js +0 -55
- package/plugin-base32-enc-dec/index.d.ts +0 -9
- package/plugin-base32-enc-dec/index.js +0 -28
- package/plugin-crypto/index.d.ts +0 -4
- package/plugin-crypto/index.js +0 -26
- package/plugin-crypto-async-ronomon/index.d.ts +0 -4
- package/plugin-crypto-async-ronomon/index.js +0 -34
- package/plugin-crypto-js/index.d.ts +0 -4
- package/plugin-crypto-js/index.js +0 -831
- package/plugin-thirty-two/index.d.ts +0 -9
- package/plugin-thirty-two/index.js +0 -24
- package/preset-browser/buffer.js +0 -1
- package/preset-browser/index.d.ts +0 -4
- package/preset-browser/index.js +0 -9
- package/preset-browser/index.js.map +0 -1
- package/preset-default/index.d.ts +0 -4
- package/preset-default/index.js +0 -31
- package/preset-default-async/index.d.ts +0 -4
- package/preset-default-async/index.js +0 -31
- package/preset-v11/index.js +0 -134
- package/totp/index.d.ts +0 -1
- package/totp/index.js +0 -202
- package/totp/totp.d.ts +0 -201
- package/totp-async/index.d.ts +0 -1
- package/totp-async/index.js +0 -98
- package/totp-async/totp.d.ts +0 -46
package/README.md
CHANGED
|
@@ -6,7 +6,7 @@
|
|
|
6
6
|
[![Build Status][badge-circle]][project-circle]
|
|
7
7
|
[![Coverage Status][badge-coveralls]][project-coveralls]
|
|
8
8
|
[![npm downloads][badge-npm-downloads]][project-npm]
|
|
9
|
-
[![TypeScript Support][badge-type-ts]][project-
|
|
9
|
+
[![TypeScript Support][badge-type-ts]][project-v-api]
|
|
10
10
|
|
|
11
11
|
---
|
|
12
12
|
|
|
@@ -17,44 +17,27 @@
|
|
|
17
17
|
- [Quick Start](#quick-start)
|
|
18
18
|
- [In Node.js](#in-nodejs)
|
|
19
19
|
- [In Browser](#in-browser)
|
|
20
|
-
- [
|
|
20
|
+
- [References](#references)
|
|
21
|
+
- [API / Demo Website](#api--demo-website)
|
|
22
|
+
- [Versioning](#versioning)
|
|
21
23
|
- [Migrating from v11.x](#migrating-from-v11x)
|
|
22
|
-
- [
|
|
23
|
-
- [
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
- [Adding Crypto](#adding-crypto)
|
|
27
|
-
- [Adding Base32](#adding-base32)
|
|
28
|
-
- [Initialise your Instance](#initialise-your-instance)
|
|
29
|
-
- [Using Classes](#using-classes)
|
|
30
|
-
- [Using Functions](#using-functions)
|
|
31
|
-
- [Available Options](#available-options)
|
|
32
|
-
- [HOTP Options](#hotp-options)
|
|
33
|
-
- [TOTP Options](#totp-options)
|
|
34
|
-
- [Authenticator Options](#authenticator-options)
|
|
35
|
-
- [Async Options](#async-options)
|
|
36
|
-
- [Available Packages](#available-packages)
|
|
37
|
-
- [Core](#core)
|
|
38
|
-
- [Core (Async)](#core-async)
|
|
39
|
-
- [Plugins](#plugins)
|
|
40
|
-
- [Crypto Plugins](#crypto-plugins)
|
|
41
|
-
- [Base32 Plugins](#base32-plugins)
|
|
42
|
-
- [Presets](#presets)
|
|
24
|
+
- [Available Options](#available-options)
|
|
25
|
+
- [HOTP Options](#hotp-options)
|
|
26
|
+
- [TOTP Options](#totp-options)
|
|
27
|
+
- [Authenticator Options](#authenticator-options)
|
|
43
28
|
- [Appendix](#appendix)
|
|
44
29
|
- [Type Definitions](#type-definitions)
|
|
45
30
|
- [Async Support](#async-support)
|
|
46
|
-
- [Using Async Replacements](#using-async-replacements)
|
|
47
|
-
- [Async over Sync Methods](#async-over-sync-methods)
|
|
48
31
|
- [Browser Compatiblity](#browser-compatiblity)
|
|
49
|
-
- [Browser bundle size](#browser-bundle-size)
|
|
50
32
|
- [Length of Secrets](#length-of-secrets)
|
|
51
33
|
- [Google Authenticator](#google-authenticator)
|
|
52
34
|
- [Difference between Authenticator and TOTP](#difference-between-authenticator-and-totp)
|
|
53
35
|
- [RFC3548 Base32](#rfc3548-base32)
|
|
54
36
|
- [Displaying a QR code](#displaying-a-qr-code)
|
|
55
|
-
|
|
37
|
+
- [Getting Time Remaining / Time Used](#getting-time-remaining--time-used)
|
|
56
38
|
- [Using with Expo](#using-with-expo)
|
|
57
39
|
- [Exploring with local-repl](#exploring-with-local-repl)
|
|
40
|
+
- [OTP Backup Codes](#otp-backup-codes)
|
|
58
41
|
- [Contributors](#contributors)
|
|
59
42
|
- [License](#license)
|
|
60
43
|
|
|
@@ -67,7 +50,7 @@
|
|
|
67
50
|
It implements both [HOTP][rfc-4226-wiki] - [RFC 4226][rfc-4226]
|
|
68
51
|
and [TOTP][rfc-6238-wiki] - [RFC 6238][rfc-6238],
|
|
69
52
|
and are tested against the test vectors provided in their respective RFC specifications.
|
|
70
|
-
These datasets can be found in the `
|
|
53
|
+
These datasets can be found in the `tests/data` folder.
|
|
71
54
|
|
|
72
55
|
- [RFC 4226 Dataset][rfc-4226-dataset]
|
|
73
56
|
- [RFC 6238 Dataset][rfc-6238-dataset]
|
|
@@ -95,19 +78,17 @@ and includes additional methods to allow you to work with Google Authenticator.
|
|
|
95
78
|
|
|
96
79
|
## Quick Start
|
|
97
80
|
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
- [API Documentation][project-api]
|
|
101
|
-
- [Demo Website][project-web]
|
|
81
|
+
> If you need to customise your base32 or crypto libraries,
|
|
82
|
+
> check out the [In-Depth Guide][docs-in-depth] and [Available Packages][docs-available-packages]
|
|
102
83
|
|
|
103
84
|
### In Node.js
|
|
104
85
|
|
|
105
86
|
```bash
|
|
106
|
-
npm install otplib
|
|
87
|
+
npm install otplib --save
|
|
107
88
|
```
|
|
108
89
|
|
|
109
90
|
```js
|
|
110
|
-
import { authenticator } from 'otplib
|
|
91
|
+
import { authenticator } from 'otplib';
|
|
111
92
|
|
|
112
93
|
const secret = 'KVKFKRCPNZQUYMLXOVYDSQKJKZDTSRLD';
|
|
113
94
|
// Alternative:
|
|
@@ -128,32 +109,37 @@ try {
|
|
|
128
109
|
}
|
|
129
110
|
```
|
|
130
111
|
|
|
131
|
-
Please replace "authenticator" with totp or hotp depending on your requirements.
|
|
112
|
+
Please replace "authenticator" with "totp" or "hotp" depending on your requirements.
|
|
132
113
|
|
|
133
114
|
```js
|
|
134
115
|
// For TOTP
|
|
135
|
-
import { totp } from 'otplib
|
|
116
|
+
import { totp } from 'otplib';
|
|
136
117
|
const token = totp.generate(secret);
|
|
137
118
|
const isValid = totp.check(token, secret);
|
|
138
119
|
const isValid = totp.verify({ token, secret });
|
|
139
120
|
|
|
140
121
|
// For HOTP
|
|
141
|
-
import { hotp } from 'otplib
|
|
122
|
+
import { hotp } from 'otplib';
|
|
142
123
|
const token = hotp.generate(secret, counter);
|
|
143
124
|
const isValid = hotp.check(token, secret, counter);
|
|
144
125
|
const isValid = hotp.verify({ token, secret, counter });
|
|
145
126
|
```
|
|
146
127
|
|
|
147
|
-
For all available APIs, please refer to [API Documentation][project-api].
|
|
128
|
+
For all available APIs, please refer to [API Documentation][project-v-api].
|
|
148
129
|
|
|
149
130
|
### In Browser
|
|
150
131
|
|
|
151
|
-
The browser preset is a self
|
|
152
|
-
|
|
132
|
+
The browser preset is a self-contained `umd` module, and it is provided in a separate bundle.
|
|
133
|
+
|
|
134
|
+
```bash
|
|
135
|
+
npm install @otplib/preset-browser --save
|
|
136
|
+
```
|
|
137
|
+
|
|
138
|
+
The following is an example, where we are using the scripts hosted by `unpkg.com`.
|
|
153
139
|
|
|
154
140
|
```html
|
|
155
|
-
<script src="https://unpkg.com/
|
|
156
|
-
<script src="https://unpkg.com/
|
|
141
|
+
<script src="https://unpkg.com/@otplib/preset-browser@^12.0.0/buffer.js"></script>
|
|
142
|
+
<script src="https://unpkg.com/@otplib/preset-browser@^12.0.0/index.js"></script>
|
|
157
143
|
|
|
158
144
|
<script type="text/javascript">
|
|
159
145
|
// window.otplib.authenticator
|
|
@@ -162,173 +148,51 @@ As such, there are 2 scripts required: `preset-browser/index.js` and `preset-bro
|
|
|
162
148
|
</script>
|
|
163
149
|
```
|
|
164
150
|
|
|
165
|
-
|
|
166
|
-
from [https://www.npmjs.com/package/buffer][link-npm-buffer].
|
|
167
|
-
You can also download and include the latest version via their project page.
|
|
151
|
+
For more details, please refer to the [@otplib/preset-browser documentation][docs-preset-browser].
|
|
168
152
|
|
|
169
|
-
|
|
170
|
-
You can also `npm install otplib` and get a copy from the `node_modules/otplib/preset-browser` folder.
|
|
153
|
+
## References
|
|
171
154
|
|
|
172
|
-
|
|
155
|
+
### API / Demo Website
|
|
156
|
+
|
|
157
|
+
| Version | Links |
|
|
158
|
+
| --------------- | ----------------------------------------------------------------------------------- |
|
|
159
|
+
| v12.x | [Website][project-v-site] / [API][project-v-api] / [Readme][project-v-readme] |
|
|
160
|
+
| v11.x | [API][project-v11-api] / [Readme][project-v11-readme] |
|
|
161
|
+
| v10.x and below | Available via git history |
|
|
162
|
+
|
|
163
|
+
### Versioning
|
|
173
164
|
|
|
174
165
|
This library follows `semver`. As such, major version bumps usually mean API changes or behavior changes.
|
|
175
166
|
Please check [upgrade notes](https://github.com/yeojz/otplib/wiki/upgrade-notes) for more information,
|
|
176
167
|
especially before making any major upgrades.
|
|
177
168
|
|
|
169
|
+
To simplify releases, all packages within this repository have their versions synced.
|
|
170
|
+
Therefore, if there are any releases or updates to a package, we will bump all packages.
|
|
171
|
+
|
|
178
172
|
Check out the release notes associated with each tagged versions
|
|
179
173
|
in the [releases](https://github.com/yeojz/otplib/releases) page.
|
|
180
174
|
|
|
181
|
-
| Release Type
|
|
182
|
-
|
|
|
183
|
-
| Current / Stable
|
|
184
|
-
| Release Candidate
|
|
185
|
-
| Master Branch Builds | 0.0.0-ci.{hash} | See: [Downloading Master Builds][docs-downloading-master-builds] | |
|
|
175
|
+
| Release Type | Version Pattern | Command | |
|
|
176
|
+
| :---------------- | --------------- | ------------------------- | :------------------------------------ |
|
|
177
|
+
| Current / Stable | 0.0.0 | `npm install otplib` | [![npm][badge-npm]][project-npm] |
|
|
178
|
+
| Release Candidate | 0.0.0-0 | `npm install otplib@next` | [![npm][badge-npm-next]][project-npm] |
|
|
186
179
|
|
|
187
180
|
### Migrating from v11.x
|
|
188
181
|
|
|
189
182
|
> v12.x is a huge architectural and language rewrite. Please check out the docs if you are migrating.
|
|
190
183
|
> A preset adapter is available to provide methods that behave like `v11.x` of `otplib`.
|
|
191
184
|
|
|
192
|
-
Link to [v11.x README.md][project-v11-readme] and [v11.x API Docs][project-v11-api].
|
|
193
|
-
|
|
194
185
|
```js
|
|
195
186
|
// Update
|
|
196
187
|
import { authenticator } from 'otplib'; // v11.x
|
|
197
188
|
// to
|
|
198
|
-
import { authenticator } from 'otplib/preset-v11';
|
|
189
|
+
import { authenticator } from '@otplib/preset-v11';
|
|
199
190
|
|
|
200
191
|
// There should be no changes to your current code.
|
|
201
192
|
// However, deprecated or modified class methods will have console.warn.
|
|
202
193
|
```
|
|
203
194
|
|
|
204
|
-
###
|
|
205
|
-
|
|
206
|
-
From 12.x onwards, pre-release builds of master is also uploaded as an artifact on GitHub Actions.
|
|
207
|
-
|
|
208
|
-
To download:
|
|
209
|
-
|
|
210
|
-
1. Go to otplib's [Github Actions][project-github-actions].
|
|
211
|
-
2. Click on `dev-builds`.
|
|
212
|
-
3. Select the latest `master` workflow run.
|
|
213
|
-
4. Click on the `Artifacts` dropdown near the top-right.
|
|
214
|
-
5. Download `otplib-ci-package.zip`.
|
|
215
|
-
6. Unzip the zip file, you should see a `otplib-ci-{hash}.tar.gz` file.
|
|
216
|
-
7. You can now run `npm install ./otplib-ci-{hash}.tar.gz` to install it into your project.
|
|
217
|
-
|
|
218
|
-
## Getting Started
|
|
219
|
-
|
|
220
|
-
This is a more in-depth setup guide for installing, configuring and customising
|
|
221
|
-
your dependencies for the library.
|
|
222
|
-
|
|
223
|
-
Check out the [Quick Start][docs-quick-start] guide if you do need / want
|
|
224
|
-
to customise any dependencies from the presets.
|
|
225
|
-
|
|
226
|
-
### Install the Package
|
|
227
|
-
|
|
228
|
-
```bash
|
|
229
|
-
npm install otplib
|
|
230
|
-
```
|
|
231
|
-
|
|
232
|
-
### Choose Your Plugins
|
|
233
|
-
|
|
234
|
-
#### Adding Crypto
|
|
235
|
-
|
|
236
|
-
The crypto modules are used to generate the digest used to derive the OTP tokens from.
|
|
237
|
-
By default, Node.js has inbuilt `crypto` functionality, but you might want to replace it
|
|
238
|
-
for certain environments that do not support it.
|
|
239
|
-
|
|
240
|
-
Currently out-of-the-box, there are some [Crypto Plugins][docs-plugins-crypto] included.
|
|
241
|
-
Install the dependencies for one of them.
|
|
242
|
-
|
|
243
|
-
```bash
|
|
244
|
-
# Choose either
|
|
245
|
-
# Node.js crypto (you don't need to install anything else - http://nodejs.org/api/crypto.html)
|
|
246
|
-
|
|
247
|
-
# or
|
|
248
|
-
npm install crypto-js
|
|
249
|
-
```
|
|
250
|
-
|
|
251
|
-
#### Adding Base32
|
|
252
|
-
|
|
253
|
-
If you're using Google Authenticator, you'll need a base32 module for
|
|
254
|
-
encoding and decoding your secrets.
|
|
255
|
-
|
|
256
|
-
Currently out-of-the-box, there are some [Base32 Plugins][docs-plugins-base32] included.
|
|
257
|
-
Install the dependencies for one of them.
|
|
258
|
-
|
|
259
|
-
```bash
|
|
260
|
-
# Choose either
|
|
261
|
-
npm install thirty-two
|
|
262
|
-
|
|
263
|
-
# or
|
|
264
|
-
npm install base32-encode base32-decode
|
|
265
|
-
```
|
|
266
|
-
|
|
267
|
-
### Initialise your Instance
|
|
268
|
-
|
|
269
|
-
#### Using Classes
|
|
270
|
-
|
|
271
|
-
```js
|
|
272
|
-
import { HOTP, TOTP, Authenticator } from 'otplib';
|
|
273
|
-
|
|
274
|
-
// Base32 Plugin
|
|
275
|
-
// for thirty-two
|
|
276
|
-
import { keyDecoder, keyEncoder } from 'otplib/plugin-thirty-two';
|
|
277
|
-
// for base32-encode and base32-decode
|
|
278
|
-
import { keyDecoder, keyEncoder } from 'otplib/plugin-base32-enc-dec';
|
|
279
|
-
|
|
280
|
-
// Crypto Plugin
|
|
281
|
-
// for node crypto
|
|
282
|
-
import { createDigest, createRandomBytes } from 'otplib/plugin-crypto';
|
|
283
|
-
// for crypto-js
|
|
284
|
-
import { createDigest, createRandomBytes } from 'otplib/plugin-crypto-js';
|
|
285
|
-
|
|
286
|
-
// Setup an OTP instance which you need
|
|
287
|
-
const hotp = new HOTP({ createDigest });
|
|
288
|
-
const totp = new TOTP({ createDigest });
|
|
289
|
-
const authenticator = new Authenticator({
|
|
290
|
-
createDigest,
|
|
291
|
-
createRandomBytes,
|
|
292
|
-
keyDecoder,
|
|
293
|
-
keyEncoder
|
|
294
|
-
});
|
|
295
|
-
|
|
296
|
-
// Go forth and generate tokens
|
|
297
|
-
const token = hotp.generate(YOUR_SECRET, 0);
|
|
298
|
-
const token = totp.generate(YOUR_SECRET);
|
|
299
|
-
const token = authenticator.generate(YOUR_SECRET);
|
|
300
|
-
```
|
|
301
|
-
|
|
302
|
-
#### Using Functions
|
|
303
|
-
|
|
304
|
-
Alternatively, if you are using the functions directly instead of the classes,
|
|
305
|
-
pass these as options into the functions.
|
|
306
|
-
|
|
307
|
-
```js
|
|
308
|
-
import {
|
|
309
|
-
hotpOptions,
|
|
310
|
-
hotpToken,
|
|
311
|
-
totpOptions,
|
|
312
|
-
totpToken,
|
|
313
|
-
authenticatorOptions,
|
|
314
|
-
authenticatorToken
|
|
315
|
-
} from 'otplib/core';
|
|
316
|
-
|
|
317
|
-
// As with classes, import your desired Base32 Plugin and Crypto Plugin.
|
|
318
|
-
// import ...
|
|
319
|
-
|
|
320
|
-
// Go forth and generate tokens
|
|
321
|
-
const token = hotpToken(YOUR_SECRET, 0, hotpOptions({ createDigest));
|
|
322
|
-
const token = totpToken(YOUR_SECRET, totpOptions({ createDigest));
|
|
323
|
-
const token = authenticatorToken(YOUR_SECRET, authenticatorOptions({
|
|
324
|
-
createDigest,
|
|
325
|
-
createRandomBytes,
|
|
326
|
-
keyDecoder,
|
|
327
|
-
keyEncoder
|
|
328
|
-
));
|
|
329
|
-
```
|
|
330
|
-
|
|
331
|
-
## Available Options
|
|
195
|
+
### Available Options
|
|
332
196
|
|
|
333
197
|
All instantiated classes will have their options inherited from their respective options
|
|
334
198
|
generator. i.e. HOTP from `hotpOptions`, TOTP from `totpOptions`
|
|
@@ -339,7 +203,7 @@ All OTP classes have an object setter and getter method to override these defaul
|
|
|
339
203
|
For example,
|
|
340
204
|
|
|
341
205
|
```js
|
|
342
|
-
import { authenticator, totp, hotp } from 'otplib
|
|
206
|
+
import { authenticator, totp, hotp } from 'otplib';
|
|
343
207
|
|
|
344
208
|
// setting
|
|
345
209
|
authenticator.options = { digits: 6 };
|
|
@@ -363,7 +227,7 @@ const opts = totp.allOptions();
|
|
|
363
227
|
const opts = hotp.allOptions();
|
|
364
228
|
```
|
|
365
229
|
|
|
366
|
-
|
|
230
|
+
#### HOTP Options
|
|
367
231
|
|
|
368
232
|
| Option | Type | Description |
|
|
369
233
|
| ------------- | -------- | ------------------------------------------------------------------------------------------------------------------------------- |
|
|
@@ -378,14 +242,14 @@ const opts = hotp.allOptions();
|
|
|
378
242
|
// HOTP defaults
|
|
379
243
|
{
|
|
380
244
|
algorithm: 'sha1'
|
|
381
|
-
createDigest: undefined, // to be provided via a otplib
|
|
245
|
+
createDigest: undefined, // to be provided via a @otplib/plugin-*
|
|
382
246
|
createHmacKey: hotpCreateHmacKey,
|
|
383
247
|
digits: 6,
|
|
384
248
|
encoding: 'ascii',
|
|
385
249
|
}
|
|
386
250
|
```
|
|
387
251
|
|
|
388
|
-
|
|
252
|
+
#### TOTP Options
|
|
389
253
|
|
|
390
254
|
> Note: Includes all HOTP Options
|
|
391
255
|
|
|
@@ -406,7 +270,7 @@ const opts = hotp.allOptions();
|
|
|
406
270
|
}
|
|
407
271
|
```
|
|
408
272
|
|
|
409
|
-
|
|
273
|
+
#### Authenticator Options
|
|
410
274
|
|
|
411
275
|
> Note: Includes all HOTP + TOTP Options
|
|
412
276
|
|
|
@@ -421,101 +285,12 @@ const opts = hotp.allOptions();
|
|
|
421
285
|
{
|
|
422
286
|
// ...includes all HOTP + TOTP defaults
|
|
423
287
|
encoding: 'hex',
|
|
424
|
-
createRandomBytes: undefined, // to be provided via a otplib
|
|
425
|
-
keyEncoder: undefined, // to be provided via a otplib
|
|
426
|
-
keyDecoder: undefined, // to be provided via a otplib
|
|
427
|
-
}
|
|
428
|
-
```
|
|
429
|
-
|
|
430
|
-
### Async Options
|
|
431
|
-
|
|
432
|
-
The following options are modified for `functions` and `classes` which are suffixed with `Async`.
|
|
433
|
-
|
|
434
|
-
eg: `AuthenticatorAsync`, `totpDigestAsync`, `hotpTokenAsync` etc.
|
|
435
|
-
|
|
436
|
-
| Option | Type | Output |
|
|
437
|
-
| ----------------- | -------------- | --------------------------------------------------- |
|
|
438
|
-
| createDigest | async function | function returns Promise<string\> instead of string |
|
|
439
|
-
| createHmacKey | async function | function returns Promise<string\> instead of string |
|
|
440
|
-
| createRandomBytes | async function | function returns Promise<string\> instead of string |
|
|
441
|
-
| keyEncoder | async function | function returns Promise<string\> instead of string |
|
|
442
|
-
| keyDecoder | async function | function returns Promise<string\> instead of string |
|
|
443
|
-
|
|
444
|
-
## Available Packages
|
|
445
|
-
|
|
446
|
-
This library has been split into 3 categories: `core`, `plugin` and `preset`.
|
|
447
|
-
|
|
448
|
-
### Core
|
|
449
|
-
|
|
450
|
-
Provides the core functionality of the library. Parts of the logic
|
|
451
|
-
has been separated out in order to provide flexibility to the library via
|
|
452
|
-
available plugins.
|
|
453
|
-
|
|
454
|
-
| file | description |
|
|
455
|
-
| -------------------- | ---------------------------------------------------- |
|
|
456
|
-
| otplib/hotp | HOTP functions + class |
|
|
457
|
-
| otplib/hotp | TOTP functions + class |
|
|
458
|
-
| otplib/authenticator | Google Authenticator functions + class |
|
|
459
|
-
| otplib/core | Aggregates hotp/totp/authenticator functions + class |
|
|
460
|
-
|
|
461
|
-
#### Core (Async)
|
|
462
|
-
|
|
463
|
-
| file | description |
|
|
464
|
-
| -------------------------- | --------------------------------------- |
|
|
465
|
-
| otplib/hotp-async | async version of `otplib/hotp` |
|
|
466
|
-
| otplib/hotp-async | async version of `otplib/hotp` |
|
|
467
|
-
| otplib/authenticator-async | async version of `otplib/authenticator` |
|
|
468
|
-
| otplib/core-async | async version of `otplib/core` |
|
|
469
|
-
|
|
470
|
-
### Plugins
|
|
471
|
-
|
|
472
|
-
#### Crypto Plugins
|
|
473
|
-
|
|
474
|
-
| plugin | type | depends on |
|
|
475
|
-
| ---------------------------------- | ----- | ----------------------------------- |
|
|
476
|
-
| otplib/plugin-crypto | sync | crypto (included in Node.js) |
|
|
477
|
-
| otplib/plugin-crypto-js | sync | `npm install crypto-js` |
|
|
478
|
-
| otplib/plugin-crypto-async-ronomon | async | `npm install @ronomon/crypto-async` |
|
|
479
|
-
|
|
480
|
-
These crypto plugins provides:
|
|
481
|
-
|
|
482
|
-
```js
|
|
483
|
-
{
|
|
484
|
-
createDigest, // used for token derivation
|
|
485
|
-
createRandomBytes, //used to generate random keys for Google Authenticator
|
|
288
|
+
createRandomBytes: undefined, // to be provided via a @otplib/plugin-*
|
|
289
|
+
keyEncoder: undefined, // to be provided via a @otplib/plugin-*
|
|
290
|
+
keyDecoder: undefined, // to be provided via a @otplib/plugin-*
|
|
486
291
|
}
|
|
487
292
|
```
|
|
488
293
|
|
|
489
|
-
#### Base32 Plugins
|
|
490
|
-
|
|
491
|
-
| plugin | type | depends on |
|
|
492
|
-
| ---------------------------- | ---- | ----------------------------------------- |
|
|
493
|
-
| otplib/plugin-thirty-two | sync | `npm install thirty-two` |
|
|
494
|
-
| otplib/plugin-base32-enc-dec | sync | `npm install base32-encode base32-decode` |
|
|
495
|
-
|
|
496
|
-
These Base32 plugins provides:
|
|
497
|
-
|
|
498
|
-
```js
|
|
499
|
-
{
|
|
500
|
-
keyDecoder, //for decoding Google Authenticator secrets
|
|
501
|
-
keyEncoder, // for encoding Google Authenticator secrets.
|
|
502
|
-
}
|
|
503
|
-
```
|
|
504
|
-
|
|
505
|
-
### Presets
|
|
506
|
-
|
|
507
|
-
Presets are preconfigured HOTP, TOTP, Authenticator instances to
|
|
508
|
-
allow you to get started with the library quickly.
|
|
509
|
-
|
|
510
|
-
Each presets would need the corresponding dependent npm modules to be installed.
|
|
511
|
-
|
|
512
|
-
| file | depends on | description |
|
|
513
|
-
| --------------------------- | ------------------------------------------------------ | ---------------------------------------------------- |
|
|
514
|
-
| otplib/preset-default | `npm install thirty-two` | |
|
|
515
|
-
| otplib/preset-default-async | `npm install thirty-two @ronomon/crypto-async` | async version of `otplib/preset-default` |
|
|
516
|
-
| otplib/preset-browser | [See Browser Compatibility][docs-browser-compatiblity] | Webpack bundle and is self contained. |
|
|
517
|
-
| otplib/preset-v11 | `npm install thirty-two` | Wrapper to adapt the APIs to v11.x compatible format |
|
|
518
|
-
|
|
519
294
|
## Appendix
|
|
520
295
|
|
|
521
296
|
### Type Definitions
|
|
@@ -526,90 +301,23 @@ As of `v12.0.0`, the library has been re-written in Typescript from the ground u
|
|
|
526
301
|
|
|
527
302
|
### Async Support
|
|
528
303
|
|
|
529
|
-
`async` support was introduced in `v12.0.0
|
|
304
|
+
`async` support was introduced in `v12.0.0` as an additional core library.
|
|
530
305
|
|
|
531
306
|
This was added as some libraries like [expo.io][link-expo-crypto] or even
|
|
532
307
|
the browser API ([window.Crypto.subtle][link-mdn-subtlecrypto]) started providing
|
|
533
308
|
only async methods.
|
|
534
309
|
|
|
535
|
-
|
|
536
|
-
|
|
537
|
-
#### Using Async Replacements
|
|
538
|
-
|
|
539
|
-
This is the simplest way to get started. Other than `allOptions()` and `resetOptions`,
|
|
540
|
-
all other methods are converted to async and thus needs to be `Promise.resolve` or `await`.
|
|
541
|
-
eg: `await .generate(...)`, `await .check(...)`
|
|
542
|
-
|
|
543
|
-
```js
|
|
544
|
-
import { AuthenticatorAsync } from 'otplib/core-async';
|
|
545
|
-
|
|
546
|
-
const authenticator = new AuthenticatorAsync({
|
|
547
|
-
// ...options
|
|
548
|
-
// make sure you use async versions of
|
|
549
|
-
// required functions like createDigest.
|
|
550
|
-
});
|
|
551
|
-
|
|
552
|
-
// Note: await needed as all methods are async
|
|
553
|
-
const token = await authenticator.generate(secret);
|
|
554
|
-
```
|
|
555
|
-
|
|
556
|
-
#### Async over Sync Methods
|
|
557
|
-
|
|
558
|
-
In this method, you would essentially take over the digest generation, leaving
|
|
559
|
-
the library to handle the digest to token conversion.
|
|
560
|
-
|
|
561
|
-
```js
|
|
562
|
-
import { Authenticator } from 'otplib/core';
|
|
563
|
-
import { authenticatorDigestAsync } from 'otplib/authenticator-async';
|
|
564
|
-
|
|
565
|
-
// This is a synchronous Authenticator class.
|
|
566
|
-
const authenticator = new Authenticator({
|
|
567
|
-
// ...options
|
|
568
|
-
});
|
|
569
|
-
|
|
570
|
-
// Override the digest generation.
|
|
571
|
-
const digest = await authenticatorDigestAsync(secret, {
|
|
572
|
-
...authenticator.allOptions(),
|
|
573
|
-
createDigest: async (algorithm, hmacKey, counter) => 'string'; // put your async implementation
|
|
574
|
-
});
|
|
575
|
-
|
|
576
|
-
authenticator.options = { digest };
|
|
577
|
-
const token = authenticator.generate(secret);
|
|
578
|
-
|
|
579
|
-
// recommended: reset to remove the digest.
|
|
580
|
-
authenticator.resetOptions();
|
|
581
|
-
|
|
582
|
-
// reference test in: ./packages/tests-builds/example.test.js
|
|
583
|
-
```
|
|
584
|
-
|
|
585
|
-
Check the [API Documentation][project-api] for the full list of async functions.
|
|
586
|
-
All async functions are suffixed with `Async` except for class methods.
|
|
310
|
+
You to find more details in the [core-async][docs-core-async] folder.
|
|
587
311
|
|
|
588
312
|
### Browser Compatiblity
|
|
589
313
|
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
The following defaults have been used:
|
|
593
|
-
|
|
594
|
-
- **crypto**: `crypto-js`
|
|
595
|
-
- **encoder**: `base32-encode`
|
|
596
|
-
- **decoder**: `base32-decode`
|
|
597
|
-
|
|
598
|
-
To see what is included, you can take a look at `packages/otplib-browser/index.ts`.
|
|
599
|
-
|
|
600
|
-
#### Browser bundle size
|
|
601
|
-
|
|
602
|
-
The approximate **bundle sizes** are as follows:
|
|
603
|
-
|
|
604
|
-
| Bundle Type | Size |
|
|
605
|
-
| --------------------------------- | ---------- |
|
|
606
|
-
| original | 324KB |
|
|
607
|
-
| original, minified + gzipped | 102KB |
|
|
608
|
-
| optimised | 30.9KB |
|
|
609
|
-
| **optimised, minified + gzipped** | **9.53KB** |
|
|
314
|
+
`@otplib/preset-browser` is a `umd` bundle with some node modules replaced to reduce the browser size.
|
|
610
315
|
|
|
316
|
+
The approximate size for the **optimised, minified + gzipped** bundle is **9.53KB**.
|
|
611
317
|
Paired with the gzipped browser `buffer.js` module, it would be about `7.65KB + 9.53KB = 17.18KB`.
|
|
612
318
|
|
|
319
|
+
For more details, please refer to the [@otplib/preset-browser documentation][docs-preset-browser].
|
|
320
|
+
|
|
613
321
|
### Length of Secrets
|
|
614
322
|
|
|
615
323
|
In [RFC 6238][rfc-6238], the secret / seed length for different algorithms are predefined:
|
|
@@ -668,15 +376,15 @@ An example is shown below:
|
|
|
668
376
|
```js
|
|
669
377
|
// npm install qrcode
|
|
670
378
|
import qrcode from 'qrcode';
|
|
671
|
-
import { authenticator } from 'otplib/preset-default';
|
|
379
|
+
import { authenticator } from '@otplib/preset-default';
|
|
672
380
|
|
|
673
381
|
const user = 'A user name, possibly an email';
|
|
674
382
|
const service = 'A service name';
|
|
675
383
|
|
|
676
|
-
// v11.x
|
|
384
|
+
// v11.x and above
|
|
677
385
|
const otpauth = authenticator.keyuri(user, service, secret);
|
|
678
386
|
|
|
679
|
-
// v10.x
|
|
387
|
+
// v10.x and below
|
|
680
388
|
const otpauth = authenticator.keyuri(
|
|
681
389
|
encodeURIComponent(user),
|
|
682
390
|
encodeURIComponent(service),
|
|
@@ -692,10 +400,10 @@ qrcode.toDataURL(otpauth, (err, imageUrl) => {
|
|
|
692
400
|
});
|
|
693
401
|
```
|
|
694
402
|
|
|
695
|
-
> **Note**: For versions `v10.x
|
|
403
|
+
> **Note**: For versions `v10.x` and below, `keyuri` does not URI encode
|
|
696
404
|
> `user` and `service`. You'll need to do so before passing in the parameteres.
|
|
697
405
|
|
|
698
|
-
|
|
406
|
+
### Getting Time Remaining / Time Used
|
|
699
407
|
|
|
700
408
|
Helper methods for getting the remaining time and used time within a validity period
|
|
701
409
|
of a `totp` or `authenticator` token were introduced in `v10.0.0`.
|
|
@@ -715,8 +423,8 @@ authenticator.timeRemaining(); // or totp.timeRemaining();
|
|
|
715
423
|
While `otplib` does not provide an `expo` specified package, with the re-architecture
|
|
716
424
|
of `otplib`, you can now provide an expo native `createDigest` to the library.
|
|
717
425
|
|
|
718
|
-
Alternatively, you can make use of crypto provided by
|
|
719
|
-
the bundled browser umd module
|
|
426
|
+
Alternatively, you can make use of crypto provided by `@otplib/plugin-crypto-js` or
|
|
427
|
+
the bundled browser umd module `@otplib/preset-browser`.
|
|
720
428
|
|
|
721
429
|
Pull Requests are much welcomed for a native expo implementation as well.
|
|
722
430
|
|
|
@@ -725,20 +433,30 @@ Pull Requests are much welcomed for a native expo implementation as well.
|
|
|
725
433
|
If you'll like to explore the library with `local-repl` you can do so as well.
|
|
726
434
|
|
|
727
435
|
```bash
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
436
|
+
# after cloning the repo:
|
|
437
|
+
npm run setup
|
|
438
|
+
npm run build
|
|
439
|
+
npx local-repl
|
|
732
440
|
# You should see something like:
|
|
733
441
|
# Node v8.9.4, local-repl 4.0.0
|
|
734
442
|
# otplib 10.0.0
|
|
735
443
|
# Context: otplib
|
|
736
444
|
# [otplib] >
|
|
737
445
|
|
|
738
|
-
|
|
739
|
-
|
|
446
|
+
[otplib] > secret = 'KVKFKRCPNZQUYMLXOVYDSQKJKZDTSRLD'
|
|
447
|
+
[otplib] > otplib.authenticator.generate(secret)
|
|
740
448
|
```
|
|
741
449
|
|
|
450
|
+
### OTP Backup Codes
|
|
451
|
+
|
|
452
|
+
It is common for services to also provide a set of backup codes to authenticate
|
|
453
|
+
and bypass the OTP step in the event that you are not able to access your 2FA
|
|
454
|
+
device or have misplaced the device.
|
|
455
|
+
|
|
456
|
+
As this process is separate from the specifications for OTP, this library does not
|
|
457
|
+
provide any backup code related verification logic, and thus would have to be
|
|
458
|
+
implemented separately.
|
|
459
|
+
|
|
742
460
|
## Contributors
|
|
743
461
|
|
|
744
462
|
Thanks goes to these wonderful people ([emoji key](https://allcontributors.org/docs/en/emoji-key)):
|
|
@@ -753,12 +471,12 @@ Thanks goes to these wonderful people ([emoji key](https://allcontributors.org/d
|
|
|
753
471
|
<td align="center"><a href="https://developer.mozilla.org/profiles/madarche/"><img src="https://avatars0.githubusercontent.com/u/152407?v=4" width="80px;" alt="Marc-Aurèle DARCHE"/><br /><sub><b>Marc-Aurèle DARCHE</b></sub></a><br /><a href="https://github.com/yeojz/otplib/commits?author=madarche" title="Documentation">📖</a></td>
|
|
754
472
|
<td align="center"><a href="http://shakram02.github.io/"><img src="https://avatars3.githubusercontent.com/u/10996982?v=4" width="80px;" alt="Ahmed Hamdy (@shakram02)"/><br /><sub><b>Ahmed Hamdy (@shakram02)</b></sub></a><br /><a href="https://github.com/yeojz/otplib/commits?author=shakram02" title="Documentation">📖</a></td>
|
|
755
473
|
<td align="center"><a href="https://tony.brix.ninja"><img src="https://avatars3.githubusercontent.com/u/97994?v=4" width="80px;" alt="Tony Brix"/><br /><sub><b>Tony Brix</b></sub></a><br /><a href="https://github.com/yeojz/otplib/commits?author=UziTech" title="Code">💻</a> <a href="https://github.com/yeojz/otplib/commits?author=UziTech" title="Documentation">📖</a></td>
|
|
474
|
+
<td align="center"><a href="https://github.com/encX"><img src="https://avatars3.githubusercontent.com/u/5965883?v=4" width="80px;" alt="Plai"/><br /><sub><b>Plai</b></sub></a><br /><a href="https://github.com/yeojz/otplib/commits?author=encX" title="Documentation">📖</a></td>
|
|
756
475
|
</tr>
|
|
757
476
|
</table>
|
|
758
477
|
|
|
759
478
|
<!-- markdownlint-enable -->
|
|
760
479
|
<!-- prettier-ignore-end -->
|
|
761
|
-
|
|
762
480
|
<!-- ALL-CONTRIBUTORS-LIST:END -->
|
|
763
481
|
|
|
764
482
|
This project follows the [all-contributors](https://github.com/all-contributors/all-contributors)
|
|
@@ -766,21 +484,21 @@ specification. Contributions of any kind welcome!
|
|
|
766
484
|
|
|
767
485
|
## License
|
|
768
486
|
|
|
769
|
-
`otplib` is [MIT licensed]
|
|
487
|
+
`otplib` is [MIT licensed][project-license]
|
|
488
|
+
|
|
489
|
+
<img width="150" src="https://otplib.yeojz.dev/otplib.png" />
|
|
770
490
|
|
|
771
|
-
|
|
491
|
+
<!-- Badges -->
|
|
772
492
|
|
|
773
493
|
[badge-circle]: https://img.shields.io/circleci/project/github/yeojz/otplib/master.svg?style=flat-square
|
|
774
494
|
[badge-coveralls]: https://img.shields.io/coveralls/yeojz/otplib/master.svg?style=flat-square
|
|
775
495
|
[badge-npm-downloads]: https://img.shields.io/npm/dt/otplib.svg?style=flat-square
|
|
776
|
-
[badge-npm]: https://img.shields.io/npm/v/otplib.svg?style=flat-square
|
|
777
496
|
[badge-npm-next]: https://img.shields.io/npm/v/otplib/next.svg?style=flat-square
|
|
497
|
+
[badge-npm]: https://img.shields.io/npm/v/otplib.svg?style=flat-square
|
|
778
498
|
[badge-type-ts]: https://img.shields.io/badge/typedef-.d.ts-blue.svg?style=flat-square&longCache=true
|
|
779
|
-
|
|
780
|
-
|
|
781
|
-
|
|
782
|
-
[docs-plugins-crypto]: #crypto-plugins
|
|
783
|
-
[docs-quick-start]: #quick-start
|
|
499
|
+
|
|
500
|
+
<!-- External Links -->
|
|
501
|
+
|
|
784
502
|
[link-expo-crypto]: https://docs.expo.io/versions/v33.0.0/sdk/crypto/
|
|
785
503
|
[link-expo-io]: https://expo.io
|
|
786
504
|
[link-mdn-async]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/async_function
|
|
@@ -788,20 +506,29 @@ specification. Contributions of any kind welcome!
|
|
|
788
506
|
[link-mdn-functions]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions
|
|
789
507
|
[link-mdn-subtlecrypto]: https://developer.mozilla.org/en-US/docs/Web/API/SubtleCrypto
|
|
790
508
|
[link-npm-buffer]: https://www.npmjs.com/package/buffer
|
|
791
|
-
[project-api]: https://otplib.yeojz.com/api
|
|
792
|
-
[project-circle]: https://circleci.com/gh/yeojz/otplib
|
|
793
|
-
[project-coveralls]: https://coveralls.io/github/yeojz/otplib
|
|
794
|
-
[project-docs]: https://otplib.yeojz.com/api
|
|
795
|
-
[project-github-actions]: https://github.com/yeojz/otplib/actions
|
|
796
|
-
[project-npm]: https://www.npmjs.com/package/otplib
|
|
797
|
-
[project-v11-api]: https://5d4d0cc4c85e00000788a456--otplib.netlify.com/docs
|
|
798
|
-
[project-v11-readme]: https://github.com/yeojz/otplib/blob/d0aedccbca8ae7ec1983f40da4d7a14c9e815e9c/README.md
|
|
799
|
-
[project-web]: https://otplib.yeojz.com
|
|
800
509
|
[rfc-3548]: http://tools.ietf.org/html/rfc3548
|
|
801
|
-
[rfc-
|
|
802
|
-
[rfc-4226-dataset]: https://github.com/yeojz/otplib/blob/master/packages/tests-data/rfc4226.ts
|
|
510
|
+
[rfc-4226-dataset]: https://github.com/yeojz/otplib/blob/master/tests/data/rfc-4226.ts
|
|
803
511
|
[rfc-4226-wiki]: http://en.wikipedia.org/wiki/HMAC-based_One-time_Password_Algorithm
|
|
804
512
|
[rfc-4226]: http://tools.ietf.org/html/rfc4226
|
|
805
|
-
[rfc-
|
|
513
|
+
[rfc-4648]: https://tools.ietf.org/html/rfc4648
|
|
514
|
+
[rfc-6238-dataset]: https://github.com/yeojz/otplib/blob/master/tests/data/rfc-6238.ts
|
|
806
515
|
[rfc-6238-wiki]: http://en.wikipedia.org/wiki/Time-based_One-time_Password_Algorithm
|
|
807
516
|
[rfc-6238]: http://tools.ietf.org/html/rfc6238
|
|
517
|
+
|
|
518
|
+
<!-- Project Links -->
|
|
519
|
+
|
|
520
|
+
[docs-available-packages]: https://github.com/yeojz/otplib/blob/master/packages/README.md
|
|
521
|
+
[docs-core-async]: https://github.com/yeojz/otplib/blob/master/packages/otplib-core-async/README.md
|
|
522
|
+
[docs-in-depth]: https://github.com/yeojz/otplib/blob/master/packages/otplib-core/README.md#getting-started
|
|
523
|
+
[docs-preset-browser-src]: https://github.com/yeojz/otplib/blob/master/packages/otplib-preset-browser/src/index.ts
|
|
524
|
+
[docs-preset-browser]: https://github.com/yeojz/otplib/blob/master/packages/otplib-preset-browser/README.md
|
|
525
|
+
[project-circle]: https://circleci.com/gh/yeojz/otplib
|
|
526
|
+
[project-coveralls]: https://coveralls.io/github/yeojz/otplib
|
|
527
|
+
[project-license]: https://github.com/yeojz/otplib/blob/master/LICENSE
|
|
528
|
+
[project-npm]: https://www.npmjs.com/package/otplib
|
|
529
|
+
[project-repo]: https://github.com/yeojz/otplib
|
|
530
|
+
[project-v-api]: https://otplib.yeojz.dev/api
|
|
531
|
+
[project-v-readme]: https://github.com/yeojz/otplib/blob/master/README.md
|
|
532
|
+
[project-v-site]: https://otplib.yeojz.dev
|
|
533
|
+
[project-v11-api]: https://5d4d0cc4c85e00000788a456--otplib.netlify.com/docs
|
|
534
|
+
[project-v11-readme]: https://github.com/yeojz/otplib/blob/d0aedccbca8ae7ec1983f40da4d7a14c9e815e9c/README.md
|