@codecot/pw-checker
Version:
A comprehensive CLI tool to audit passwords locally using HIBP and import from Chrome/Bitwarden
132 lines âĸ 6.83 kB
JavaScript
// password-checker/src/index.ts
import dotenv from "dotenv";
import { importCsvToDb } from "./importCsv.js";
import { checkAllPasswords } from "./checkPasswords.js";
import { checkAllAccountsForBreaches, runScheduledBreachCheck, showBreachStatistics, } from "./checkBreaches.js";
import { importFromChrome } from "./importFromChrome.js";
import { importFromChromeCsv } from "./importFromChromeCsv.js";
import chalk from "chalk";
import fs from "fs";
// Load environment variables from .env file
dotenv.config();
function getChromeExportPath(args) {
const pathIndex = args.findIndex((arg) => arg === "--chrome-csv-path");
if (pathIndex !== -1 && pathIndex + 1 < args.length) {
return args[pathIndex + 1];
}
return "data/chrome-passwords.csv";
}
export async function main() {
// Parse command-line arguments
const args = process.argv.slice(2);
// Show help if requested
if (args.includes("--help") || args.includes("-h")) {
console.log(chalk.blue.bold("đ pw-checker - Password Security Auditing Tool\n"));
console.log("Usage: pw-checker [OPTIONS]\n");
console.log("Import Options:");
console.log(" --chrome Import passwords from Chrome database");
console.log(" --chrome-csv Import passwords from Chrome CSV export");
console.log(" --chrome-csv=PATH Specify custom path to Chrome CSV file");
console.log("\nSecurity Options:");
console.log(" --check-breaches Check email accounts for data breaches (requires HIBP API key)");
console.log(" --breach-stats Show breach check progress and statistics");
console.log(" --breach-scheduled Run a single batch of breach checks (for cron jobs)");
console.log(" --resume Resume breach checking from where it left off");
console.log(" --limit=N Limit number of accounts to check (e.g., --limit=10)");
console.log("\nDevelopment Options:");
console.log(" --dev Development mode (limit API calls to 5 records)");
console.log(" --skip-network Skip all network API calls");
console.log("\nOther Options:");
console.log(" --help, -h Show this help message");
console.log("\nExamples:");
console.log(" pw-checker Import CSV and check passwords");
console.log(" pw-checker --chrome-csv Import from Chrome CSV export");
console.log(" pw-checker --check-breaches Check for data breaches");
process.exit(0);
}
const importChrome = args.includes("--chrome");
const importChromeCsv = args.includes("--chrome-csv");
const checkBreaches = args.includes("--check-breaches");
const breachStats = args.includes("--breach-stats");
const breachScheduled = args.includes("--breach-scheduled");
const resumeBreachCheck = args.includes("--resume");
const chromeCsvPath = getChromeExportPath(args);
// Parse limit parameter
const limitArg = args.find((arg) => arg.startsWith("--limit="));
const limitValue = limitArg ? parseInt(limitArg.split("=")[1]) : undefined;
try {
console.log("đ Starting pw-checker...");
// Handle breach statistics request first (no other processing needed)
if (breachStats) {
await showBreachStatistics();
return;
}
// Handle scheduled breach check (for cron jobs)
if (breachScheduled) {
const batchSize = limitValue || 8;
const completed = await runScheduledBreachCheck(batchSize);
if (completed) {
console.log(chalk.green("đ All accounts have been checked for breaches!"));
}
return;
}
// Import passwords from CSV
console.log("đĨ Checking for CSV file: data/passwords.csv");
if (fs.existsSync("data/passwords.csv")) {
await importCsvToDb("data/passwords.csv");
}
else {
console.log(chalk.yellow("â ī¸ No CSV file found at data/passwords.csv. Skipping CSV import."));
console.log(chalk.blue("âšī¸ To import from CSV, create data/passwords.csv or copy from data/passwords.csv.template"));
}
// Import from Chrome if requested
if (importChrome) {
console.log("đ Importing passwords from Chrome...");
const imported = await importFromChrome();
console.log(chalk.green(`â
Imported ${imported} credentials from Chrome.`));
}
// Import from Chrome CSV export if requested
if (importChromeCsv) {
if (!fs.existsSync(chromeCsvPath)) {
console.error(chalk.red(`â Chrome CSV export file not found at: ${chromeCsvPath}`));
console.log(chalk.yellow(`âšī¸ Export your Chrome passwords to CSV and save the file to "${chromeCsvPath}" or specify path with --chrome-csv-path`));
}
else {
console.log(`đ Importing passwords from Chrome CSV export: ${chromeCsvPath}`);
const imported = await importFromChromeCsv(chromeCsvPath);
console.log(chalk.green(`â
Imported/updated ${imported} credentials from Chrome CSV export.`));
}
}
// Check for development mode flags
const isDevelopment = args.includes("--dev") || args.includes("--development");
const skipNetworkCalls = args.includes("--skip-network") || process.env.SKIP_NETWORK === "true";
const limitRecords = isDevelopment ? 5 : undefined;
if (isDevelopment) {
console.log(chalk.yellow(`âšī¸ Development mode: Limiting network API calls to ${limitRecords} records.`));
}
if (skipNetworkCalls) {
console.log(chalk.yellow("âšī¸ Skipping network API calls (use --dev or --skip-network to disable)."));
}
else {
// Check all passwords against HIBP
console.log("đ Checking passwords against HIBP database...");
await checkAllPasswords(limitRecords);
// Check accounts for data breaches if requested
if (checkBreaches) {
console.log("đ Checking accounts for data breaches...");
await checkAllAccountsForBreaches(limitValue || limitRecords, resumeBreachCheck);
}
}
console.log("â
pw-checker finished.");
}
catch (error) {
console.error(chalk.red("â An error occurred:"), error);
console.log(chalk.yellow("âšī¸ Please check your configuration and try again."));
process.exit(1);
}
}
// If this file is run directly, execute main
if (import.meta.url === `file://${process.argv[1]}`) {
main();
}
//# sourceMappingURL=index.js.map