diff --git a/.prettierignore b/.prettierignore new file mode 100644 index 00000000..8eef1430 --- /dev/null +++ b/.prettierignore @@ -0,0 +1 @@ +*.disabled \ No newline at end of file diff --git a/src/background.ts b/src/background.ts index bb59a2f9..888f0ae3 100644 --- a/src/background.ts +++ b/src/background.ts @@ -8,7 +8,7 @@ import { getCurrentTab, okToInjectContentScript, } from "./utils"; -import { CodeState } from "./models/otp"; +import { CodeState, OTPType } from "./models/otp"; import { getOTPAuthPerLineFromOPTAuthMigration } from "./models/migration"; import { isChrome, isFirefox } from "./browser"; @@ -193,15 +193,15 @@ async function getTotp(text: string, silent = false) { if ( !/^[2-7a-z]+=*$/i.test(secret) && /^[0-9a-f]+$/i.test(secret) && - type === "totp" + type === OTPType[OTPType.totp] ) { - type = "hex"; + type = OTPType[OTPType.hex]; } else if ( !/^[2-7a-z]+=*$/i.test(secret) && /^[0-9a-f]+$/i.test(secret) && - type === "hotp" + type === OTPType[OTPType.hotp] ) { - type = "hhex"; + type = OTPType[OTPType.hhex]; } const entryData: { [hash: string]: RawOTPStorage } = {}; entryData[hash] = { diff --git a/src/components/Popup/BackupPage.vue b/src/components/Popup/BackupPage.vue index 8e718b46..913526ad 100644 --- a/src/components/Popup/BackupPage.vue +++ b/src/components/Popup/BackupPage.vue @@ -71,6 +71,7 @@ <script lang="ts"> import Vue from "vue"; import { isSafari } from "../../browser"; +import { OTPType } from "../../models/otp"; export default Vue.extend({ data: function () { @@ -176,8 +177,8 @@ export default Vue.extend({ function hasUnsupportedAccounts(exportData: { [h: string]: RawOTPStorage }) { for (const entry of Object.keys(exportData)) { if ( - exportData[entry].type === "battle" || - exportData[entry].type === "steam" + exportData[entry].type === OTPType[OTPType.battle] || + exportData[entry].type === OTPType[OTPType.steam] ) { return true; } @@ -212,10 +213,16 @@ function getOneLineOtpBackupFile(entryData: { [hash: string]: RawOTPStorage }) { ? otpStorage.issuer + ":" + (otpStorage.account || "") : otpStorage.account || ""; let type = ""; - if (otpStorage.type === "totp" || otpStorage.type === "hex") { - type = "totp"; - } else if (otpStorage.type === "hotp" || otpStorage.type === "hhex") { - type = "hotp"; + if ( + otpStorage.type === OTPType[OTPType.totp] || + otpStorage.type === OTPType[OTPType.hex] + ) { + type = OTPType[OTPType.totp]; + } else if ( + otpStorage.type === OTPType[OTPType.hotp] || + otpStorage.type === OTPType[OTPType.hhex] + ) { + type = OTPType[OTPType.hotp]; } else { continue; } @@ -228,8 +235,8 @@ function getOneLineOtpBackupFile(entryData: { [hash: string]: RawOTPStorage }) { "?secret=" + otpStorage.secret + (otpStorage.issuer ? "&issuer=" + otpStorage.issuer : "") + - (type === "hotp" ? "&counter=" + otpStorage.counter : "") + - (type === "totp" && otpStorage.period + (type === OTPType[OTPType.hotp] ? "&counter=" + otpStorage.counter : "") + + (type === OTPType[OTPType.totp] && otpStorage.period ? "&period=" + otpStorage.period : "") + (otpStorage.digits ? "&digits=" + otpStorage.digits : "") + diff --git a/src/content.ts b/src/content.ts index 5ac1805c..c9021423 100644 --- a/src/content.ts +++ b/src/content.ts @@ -4,6 +4,7 @@ import jsQR from "jsqr"; // @ts-expect-error - injected by vue-svg-loader import scanGIF from "../images/scan.gif"; +import { OTPType } from "./models/otp"; if (!document.getElementById("__ga_grayLayout__")) { chrome.runtime.onMessage.addListener((message, sender, sendResponse) => { @@ -304,7 +305,7 @@ function pasteCode(code: string) { "authenticator", "factor", "code", - "totp", + OTPType[OTPType.totp], "twoFactorCode", ]; for (const inputBox of inputBoxes) { diff --git a/src/import.ts b/src/import.ts index 21bebdab..256142ed 100644 --- a/src/import.ts +++ b/src/import.ts @@ -7,6 +7,7 @@ import { Encryption } from "./models/encryption"; import { EntryStorage } from "./models/storage"; import { getOTPAuthPerLineFromOPTAuthMigration } from "./models/migration"; import * as CryptoJS from "crypto-js"; +import { OTPType } from "./models/otp"; async function init() { // i18n @@ -282,15 +283,15 @@ export async function getEntryDataFromOTPAuthPerLine(importCode: string) { if ( !/^[2-7a-z]+=*$/i.test(secret) && /^[0-9a-f]+$/i.test(secret) && - type === "totp" + type === OTPType[OTPType.totp] ) { - type = "hex"; + type = OTPType[OTPType.hex]; } else if ( !/^[2-7a-z]+=*$/i.test(secret) && /^[0-9a-f]+$/i.test(secret) && - type === "hotp" + type === OTPType[OTPType.hotp] ) { - type = "hhex"; + type = OTPType[OTPType.hhex]; } exportData[hash] = { diff --git a/src/models/migration.ts b/src/models/migration.ts index 9d00c63e..c364099a 100644 --- a/src/models/migration.ts +++ b/src/models/migration.ts @@ -1,4 +1,5 @@ import * as CryptoJS from "crypto-js"; +import { OTPType } from "./otp"; function byteArray2Base32(bytes: number[]) { const chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ234567"; @@ -111,11 +112,13 @@ export function getOTPAuthPerLineFromOPTAuthMigration(migrationUri: string) { byteData[isserStart + isserLength + 1] ]; const digits = [6, 6, 8][byteData[isserStart + isserLength + 3]]; - const type = ["totp", "hotp", "totp"][ - byteData[isserStart + isserLength + 5] - ]; + const type = [ + OTPType[OTPType.totp], + OTPType[OTPType.hotp], + OTPType[OTPType.totp], + ][byteData[isserStart + isserLength + 5]]; let line = `otpauth://${type}/${account}?secret=${secret}&issuer=${issuer}&algorithm=${algorithm}&digits=${digits}`; - if (type === "hotp") { + if (type === OTPType[OTPType.hotp]) { let counter = 1; if (isserStart + isserLength + 7 <= lineLength) { counter = byteData[isserStart + isserLength + 7]; diff --git a/src/models/otp.ts b/src/models/otp.ts index cdfa38db..7e0b0fc0 100644 --- a/src/models/otp.ts +++ b/src/models/otp.ts @@ -3,7 +3,8 @@ import { UserSettings } from "./settings"; import { EntryStorage } from "./storage"; export enum OTPType { - totp = 1, + PLACEHOLDER_DO_NOT_USE, // https://github.com/Authenticator-Extension/Authenticator/pull/1283#issuecomment-2382842440 + totp, hotp, battle, steam, @@ -223,8 +224,8 @@ export class OTPEntry implements OTPEntryInterface { this.period = decryptedData.period || 30; this.pinned = decryptedData.pinned || false; this.secret = decryptedData.secret; - // @ts-expect-error need a better way to do this - this.type = OTPType[decryptedData.type] || OTPType.totp; + this.type = + OTPType[decryptedData.type as keyof typeof OTPType] || OTPType.totp; if (this.type !== OTPType.hotp && this.type !== OTPType.hhex) { this.generate(); diff --git a/src/models/storage.ts b/src/models/storage.ts index 4b3699fb..e2e57457 100644 --- a/src/models/storage.ts +++ b/src/models/storage.ts @@ -478,7 +478,7 @@ export class EntryStorage { algorithm: OTPAlgorithm; pinned: boolean; } = { - type: (parseInt(data[hash].type) as OTPType) || OTPType[OTPType.totp], + type: OTPType[data[hash].type as keyof typeof OTPType] || OTPType.totp, index: data[hash].index || 0, issuer: data[hash].issuer || "", account: data[hash].account || "", @@ -622,13 +622,13 @@ export class EntryStorage { let type: OTPType; switch (entryData.type) { - case "totp": - case "hotp": - case "battle": - case "steam": - case "hex": - case "hhex": - type = OTPType[entryData.type]; + case OTPType[OTPType.totp]: + case OTPType[OTPType.hotp]: + case OTPType[OTPType.battle]: + case OTPType[OTPType.steam]: + case OTPType[OTPType.hex]: + case OTPType[OTPType.hhex]: + type = OTPType.hhex; break; default: // we need correct the type here