From fa4da161c9b120dcff6d216b3c3b38e0f19b9bed Mon Sep 17 00:00:00 2001 From: Will Franklin Date: Thu, 30 Nov 2023 18:02:57 +0000 Subject: [PATCH 1/5] Generate CJS version of otpauth.d.ts file --- package.json | 7 +++++-- rollup.config.mjs | 5 +++++ 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index 215bfb88..241446ff 100644 --- a/package.json +++ b/package.json @@ -36,13 +36,16 @@ "browser": "./dist/otpauth.esm.js", "exports": { ".": { - "types": "./dist/otpauth.d.ts", "bun": "./dist/otpauth.esm.js", "deno": "./dist/otpauth.esm.js", "node": { "import": "./dist/otpauth.node.mjs", - "require": "./dist/otpauth.node.cjs" + "require": { + "types": "./dist/otpauth.d.cts", + "default": "./dist/otpauth.node.cjs" + } }, + "types": "./dist/otpauth.d.ts", "default": "./dist/otpauth.esm.js" }, "./dist/*": { diff --git a/rollup.config.mjs b/rollup.config.mjs index 6d3ddb4e..3e9334e3 100644 --- a/rollup.config.mjs +++ b/rollup.config.mjs @@ -123,5 +123,10 @@ export default async () => { output: [{ file: "./dist/otpauth.d.ts", format: "es" }], plugins: [dts()], }, + { + input: "./types/index.d.ts", + output: [{ file: "./dist/otpauth.d.cts", format: "cjs" }], + plugins: [dts()], + }, ]; }; From f5d190e4e4eddc9ace000f75047dc0f9b5e3dad8 Mon Sep 17 00:00:00 2001 From: Will Franklin Date: Fri, 1 Dec 2023 15:19:49 +0000 Subject: [PATCH 2/5] Add missing otpauth.d.cts file --- dist/otpauth.d.cts | 383 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 383 insertions(+) create mode 100644 dist/otpauth.d.cts diff --git a/dist/otpauth.d.cts b/dist/otpauth.d.cts new file mode 100644 index 00000000..7b654f6c --- /dev/null +++ b/dist/otpauth.d.cts @@ -0,0 +1,383 @@ +/** + * OTP secret key. + */ +declare class Secret { + /** + * Converts a Latin-1 string to a Secret object. + * @param {string} str Latin-1 string. + * @returns {Secret} Secret object. + */ + static fromLatin1(str: string): Secret; + /** + * Converts an UTF-8 string to a Secret object. + * @param {string} str UTF-8 string. + * @returns {Secret} Secret object. + */ + static fromUTF8(str: string): Secret; + /** + * Converts a base32 string to a Secret object. + * @param {string} str Base32 string. + * @returns {Secret} Secret object. + */ + static fromBase32(str: string): Secret; + /** + * Converts a hexadecimal string to a Secret object. + * @param {string} str Hexadecimal string. + * @returns {Secret} Secret object. + */ + static fromHex(str: string): Secret; + /** + * Creates a secret key object. + * @param {Object} [config] Configuration options. + * @param {ArrayBuffer} [config.buffer=randomBytes] Secret key. + * @param {number} [config.size=20] Number of random bytes to generate, ignored if 'buffer' is provided. + */ + constructor({ buffer, size }?: { + buffer?: ArrayBuffer | undefined; + size?: number | undefined; + } | undefined); + /** + * Secret key. + * @type {ArrayBuffer} + */ + buffer: ArrayBuffer; + /** + * Latin-1 string representation of secret key. + * @type {string} + */ + get latin1(): string; + /** + * UTF-8 string representation of secret key. + * @type {string} + */ + get utf8(): string; + /** + * Base32 string representation of secret key. + * @type {string} + */ + get base32(): string; + /** + * Hexadecimal string representation of secret key. + * @type {string} + */ + get hex(): string; +} + +/** + * HOTP: An HMAC-based One-time Password Algorithm. + * @see [RFC 4226](https://tools.ietf.org/html/rfc4226) + */ +declare class HOTP { + /** + * Default configuration. + * @type {{ + * issuer: string, + * label: string, + * issuerInLabel: boolean, + * algorithm: string, + * digits: number, + * counter: number + * window: number + * }} + */ + static get defaults(): { + issuer: string; + label: string; + issuerInLabel: boolean; + algorithm: string; + digits: number; + counter: number; + window: number; + }; + /** + * Generates an HOTP token. + * @param {Object} config Configuration options. + * @param {Secret} config.secret Secret key. + * @param {string} [config.algorithm='SHA1'] HMAC hashing algorithm. + * @param {number} [config.digits=6] Token length. + * @param {number} [config.counter=0] Counter value. + * @returns {string} Token. + */ + static generate({ secret, algorithm, digits, counter, }: { + secret: Secret; + algorithm?: string | undefined; + digits?: number | undefined; + counter?: number | undefined; + }): string; + /** + * Validates an HOTP token. + * @param {Object} config Configuration options. + * @param {string} config.token Token value. + * @param {Secret} config.secret Secret key. + * @param {string} [config.algorithm='SHA1'] HMAC hashing algorithm. + * @param {number} config.digits Token length. + * @param {number} [config.counter=0] Counter value. + * @param {number} [config.window=1] Window of counter values to test. + * @returns {number|null} Token delta or null if it is not found in the search window, in which case it should be considered invalid. + */ + static validate({ token, secret, algorithm, digits, counter, window, }: { + token: string; + secret: Secret; + algorithm?: string | undefined; + digits: number; + counter?: number | undefined; + window?: number | undefined; + }): number | null; + /** + * Creates an HOTP object. + * @param {Object} [config] Configuration options. + * @param {string} [config.issuer=''] Account provider. + * @param {string} [config.label='OTPAuth'] Account label. + * @param {boolean} [config.issuerInLabel=true] Include issuer prefix in label. + * @param {Secret|string} [config.secret=Secret] Secret key. + * @param {string} [config.algorithm='SHA1'] HMAC hashing algorithm. + * @param {number} [config.digits=6] Token length. + * @param {number} [config.counter=0] Initial counter value. + */ + constructor({ issuer, label, issuerInLabel, secret, algorithm, digits, counter, }?: { + issuer?: string | undefined; + label?: string | undefined; + issuerInLabel?: boolean | undefined; + secret?: string | Secret | undefined; + algorithm?: string | undefined; + digits?: number | undefined; + counter?: number | undefined; + } | undefined); + /** + * Account provider. + * @type {string} + */ + issuer: string; + /** + * Account label. + * @type {string} + */ + label: string; + /** + * Include issuer prefix in label. + * @type {boolean} + */ + issuerInLabel: boolean; + /** + * Secret key. + * @type {Secret} + */ + secret: Secret; + /** + * HMAC hashing algorithm. + * @type {string} + */ + algorithm: string; + /** + * Token length. + * @type {number} + */ + digits: number; + /** + * Initial counter value. + * @type {number} + */ + counter: number; + /** + * Generates an HOTP token. + * @param {Object} [config] Configuration options. + * @param {number} [config.counter=this.counter++] Counter value. + * @returns {string} Token. + */ + generate({ counter }?: { + counter?: number | undefined; + } | undefined): string; + /** + * Validates an HOTP token. + * @param {Object} config Configuration options. + * @param {string} config.token Token value. + * @param {number} [config.counter=this.counter] Counter value. + * @param {number} [config.window=1] Window of counter values to test. + * @returns {number|null} Token delta or null if it is not found in the search window, in which case it should be considered invalid. + */ + validate({ token, counter, window }: { + token: string; + counter?: number | undefined; + window?: number | undefined; + }): number | null; + /** + * Returns a Google Authenticator key URI. + * @returns {string} URI. + */ + toString(): string; +} + +/** + * TOTP: Time-Based One-Time Password Algorithm. + * @see [RFC 6238](https://tools.ietf.org/html/rfc6238) + */ +declare class TOTP { + /** + * Default configuration. + * @type {{ + * issuer: string, + * label: string, + * issuerInLabel: boolean, + * algorithm: string, + * digits: number, + * period: number + * window: number + * }} + */ + static get defaults(): { + issuer: string; + label: string; + issuerInLabel: boolean; + algorithm: string; + digits: number; + period: number; + window: number; + }; + /** + * Generates a TOTP token. + * @param {Object} config Configuration options. + * @param {Secret} config.secret Secret key. + * @param {string} [config.algorithm='SHA1'] HMAC hashing algorithm. + * @param {number} [config.digits=6] Token length. + * @param {number} [config.period=30] Token time-step duration. + * @param {number} [config.timestamp=Date.now] Timestamp value in milliseconds. + * @returns {string} Token. + */ + static generate({ secret, algorithm, digits, period, timestamp, }: { + secret: Secret; + algorithm?: string | undefined; + digits?: number | undefined; + period?: number | undefined; + timestamp?: number | undefined; + }): string; + /** + * Validates a TOTP token. + * @param {Object} config Configuration options. + * @param {string} config.token Token value. + * @param {Secret} config.secret Secret key. + * @param {string} [config.algorithm='SHA1'] HMAC hashing algorithm. + * @param {number} config.digits Token length. + * @param {number} [config.period=30] Token time-step duration. + * @param {number} [config.timestamp=Date.now] Timestamp value in milliseconds. + * @param {number} [config.window=1] Window of counter values to test. + * @returns {number|null} Token delta or null if it is not found in the search window, in which case it should be considered invalid. + */ + static validate({ token, secret, algorithm, digits, period, timestamp, window, }: { + token: string; + secret: Secret; + algorithm?: string | undefined; + digits: number; + period?: number | undefined; + timestamp?: number | undefined; + window?: number | undefined; + }): number | null; + /** + * Creates a TOTP object. + * @param {Object} [config] Configuration options. + * @param {string} [config.issuer=''] Account provider. + * @param {string} [config.label='OTPAuth'] Account label. + * @param {boolean} [config.issuerInLabel=true] Include issuer prefix in label. + * @param {Secret|string} [config.secret=Secret] Secret key. + * @param {string} [config.algorithm='SHA1'] HMAC hashing algorithm. + * @param {number} [config.digits=6] Token length. + * @param {number} [config.period=30] Token time-step duration. + */ + constructor({ issuer, label, issuerInLabel, secret, algorithm, digits, period, }?: { + issuer?: string | undefined; + label?: string | undefined; + issuerInLabel?: boolean | undefined; + secret?: string | Secret | undefined; + algorithm?: string | undefined; + digits?: number | undefined; + period?: number | undefined; + } | undefined); + /** + * Account provider. + * @type {string} + */ + issuer: string; + /** + * Account label. + * @type {string} + */ + label: string; + /** + * Include issuer prefix in label. + * @type {boolean} + */ + issuerInLabel: boolean; + /** + * Secret key. + * @type {Secret} + */ + secret: Secret; + /** + * HMAC hashing algorithm. + * @type {string} + */ + algorithm: string; + /** + * Token length. + * @type {number} + */ + digits: number; + /** + * Token time-step duration. + * @type {number} + */ + period: number; + /** + * Generates a TOTP token. + * @param {Object} [config] Configuration options. + * @param {number} [config.timestamp=Date.now] Timestamp value in milliseconds. + * @returns {string} Token. + */ + generate({ timestamp }?: { + timestamp?: number | undefined; + } | undefined): string; + /** + * Validates a TOTP token. + * @param {Object} config Configuration options. + * @param {string} config.token Token value. + * @param {number} [config.timestamp=Date.now] Timestamp value in milliseconds. + * @param {number} [config.window=1] Window of counter values to test. + * @returns {number|null} Token delta or null if it is not found in the search window, in which case it should be considered invalid. + */ + validate({ token, timestamp, window }: { + token: string; + timestamp?: number | undefined; + window?: number | undefined; + }): number | null; + /** + * Returns a Google Authenticator key URI. + * @returns {string} URI. + */ + toString(): string; +} + +/** + * HOTP/TOTP object/string conversion. + * @see [Key URI Format](https://github.com/google/google-authenticator/wiki/Key-Uri-Format) + */ +declare class URI { + /** + * Parses a Google Authenticator key URI and returns an HOTP/TOTP object. + * @param {string} uri Google Authenticator Key URI. + * @returns {HOTP|TOTP} HOTP/TOTP object. + */ + static parse(uri: string): HOTP | TOTP; + /** + * Converts an HOTP/TOTP object to a Google Authenticator key URI. + * @param {HOTP|TOTP} otp HOTP/TOTP object. + * @returns {string} Google Authenticator Key URI. + */ + static stringify(otp: HOTP | TOTP): string; +} + +/** + * Library version. + * @type {string} + */ +declare const version: string; + +export { HOTP, Secret, TOTP, URI, version }; From e2c398296baa4f4170b870e2446fe5cd2aa644d8 Mon Sep 17 00:00:00 2001 From: Will Franklin Date: Fri, 1 Dec 2023 16:24:29 +0000 Subject: [PATCH 3/5] Simpler type definition generation --- rollup.config.mjs | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/rollup.config.mjs b/rollup.config.mjs index 3e9334e3..8c30291b 100644 --- a/rollup.config.mjs +++ b/rollup.config.mjs @@ -120,12 +120,10 @@ export default async () => { }, { input: "./types/index.d.ts", - output: [{ file: "./dist/otpauth.d.ts", format: "es" }], - plugins: [dts()], - }, - { - input: "./types/index.d.ts", - output: [{ file: "./dist/otpauth.d.cts", format: "cjs" }], + output: [ + { file: "./dist/otpauth.d.ts", format: "es" }, + { file: "./dist/otpauth.d.cts", format: "cjs" } + ], plugins: [dts()], }, ]; From 512fda8b6d8feaf9e992a3358f1104318a3c2fba Mon Sep 17 00:00:00 2001 From: Will Franklin Date: Fri, 1 Dec 2023 16:26:02 +0000 Subject: [PATCH 4/5] Clean up exports --- package.json | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/package.json b/package.json index 241446ff..2f436361 100644 --- a/package.json +++ b/package.json @@ -36,16 +36,14 @@ "browser": "./dist/otpauth.esm.js", "exports": { ".": { - "bun": "./dist/otpauth.esm.js", - "deno": "./dist/otpauth.esm.js", + "types": { + "import": "./dist/otpauth.d.ts", + "require": "./dist/otpauth.d.cts" + }, "node": { "import": "./dist/otpauth.node.mjs", - "require": { - "types": "./dist/otpauth.d.cts", - "default": "./dist/otpauth.node.cjs" - } + "require": "./dist/otpauth.node.cjs" }, - "types": "./dist/otpauth.d.ts", "default": "./dist/otpauth.esm.js" }, "./dist/*": { From ff792a7a54cc83e76c183cd7d83303288aa6311a Mon Sep 17 00:00:00 2001 From: Will Franklin Date: Wed, 6 Dec 2023 12:07:28 +0000 Subject: [PATCH 5/5] Restore bun/deno, add trailing comma, update ./dist/* types --- package.json | 7 ++++++- rollup.config.mjs | 2 +- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index 2f436361..b1519b92 100644 --- a/package.json +++ b/package.json @@ -40,6 +40,8 @@ "import": "./dist/otpauth.d.ts", "require": "./dist/otpauth.d.cts" }, + "bun": "./dist/otpauth.esm.js", + "deno": "./dist/otpauth.esm.js", "node": { "import": "./dist/otpauth.node.mjs", "require": "./dist/otpauth.node.cjs" @@ -47,7 +49,10 @@ "default": "./dist/otpauth.esm.js" }, "./dist/*": { - "types": "./dist/otpauth.d.ts", + "types": { + "import": "./dist/otpauth.d.ts", + "require": "./dist/otpauth.d.cts" + }, "default": "./dist/*" } }, diff --git a/rollup.config.mjs b/rollup.config.mjs index 8c30291b..026536be 100644 --- a/rollup.config.mjs +++ b/rollup.config.mjs @@ -122,7 +122,7 @@ export default async () => { input: "./types/index.d.ts", output: [ { file: "./dist/otpauth.d.ts", format: "es" }, - { file: "./dist/otpauth.d.cts", format: "cjs" } + { file: "./dist/otpauth.d.cts", format: "cjs" }, ], plugins: [dts()], },