/**
 * Assign unique secure passwords to customer test users.
 * Run: DATABASE_URL=... PII_KEY=... tsx src/server/db/seeds/update-customer-passwords.ts
 *
 * Updates password_hash in DB and patches Docs/logins.dev entries.
 */

import { scriptOutput } from '../../lib/script-output.js';
import { getDb } from '../client.js';
import { hashPassword } from '../../auth/credentials.js';
import { readFileSync, writeFileSync } from 'node:fs';
import { resolve } from 'node:path';
import { updatePasswordHash } from '../queries/users.js';
import { readSeedCliEnv } from '../seed-cli-env.js';

const { DATABASE_URL, PASSWORD_PEPPER_V1 } = readSeedCliEnv();

const db = getDb({ DATABASE_URL });

function generatePassword(): string {
  const upper = 'ABCDEFGHJKLMNPQRSTUVWXYZ';
  const lower = 'abcdefghjkmnpqrstuvwxyz';
  const digits = '23456789';
  const symbols = '!@#$%^&*';
  const all = upper + lower + digits + symbols;

  const rand = (chars: string) => {
    const view = new Uint8Array(1);
    crypto.getRandomValues(view);
    return chars[view[0]! % chars.length]!;
  };

  // Guarantee at least one of each class, rest random, then shuffle
  const required = [
    rand(upper),
    rand(upper),
    rand(lower),
    rand(lower),
    rand(digits),
    rand(symbols),
  ];
  const rest = Array.from({ length: 10 }, () => rand(all));
  const combined = [...required, ...rest];

  // Fisher-Yates shuffle
  for (let i = combined.length - 1; i > 0; i--) {
    const view = new Uint8Array(1);
    crypto.getRandomValues(view);
    const j = view[0]! % (i + 1);
    [combined[i], combined[j]] = [combined[j]!, combined[i]!];
  }

  return combined.join('');
}

const CUSTOMERS = [
  { num: '01', id: '8a86334c-5bb9-4417-9405-dd1c90fecb5b', email: 'customer01@multi.deal' },
  { num: '02', id: '0810d17a-c3f4-4aab-b7fc-83abfc5c1f88', email: 'customer02@multi.deal' },
  { num: '03', id: '1c868701-d829-4aaf-a0e1-59d7c4f57461', email: 'customer03@multi.deal' },
  { num: '04', id: '21b1ab27-5fa6-4b4a-937e-c074733b86eb', email: 'customer04@multi.deal' },
  { num: '05', id: '0bd7fcea-9d0e-429b-b376-555e26cb8147', email: 'customer05@multi.deal' },
];

async function main() {
  const updates: { email: string; password: string }[] = [];

  for (const c of CUSTOMERS) {
    const password = generatePassword();
    const passwordHash = await hashPassword(password, PASSWORD_PEPPER_V1);

    await updatePasswordHash(db, c.id, passwordHash);

    updates.push({ email: c.email, password });
    scriptOutput(`  [${c.num}] customer ${c.num} → password updated`);
  }

  // Patch Docs/logins.dev — replace each "Password │ Multideal1!" line
  // for these specific customer blocks
  const loginsPath = resolve(process.cwd(), '../../Docs/logins.dev');
  let content = readFileSync(loginsPath, 'utf8');

  for (const { email, password } of updates) {
    // Match the block: Email line followed by Password line
    const emailEscaped = email.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
    const blockRe = new RegExp(
      `(Email\\s+│\\s+${emailEscaped}\\s*\\n)(Password\\s+│\\s+)[^\\n]+`,
      'g',
    );
    content = content.replace(blockRe, `$1$2${password}`);
  }

  writeFileSync(loginsPath, content, 'utf8');
  scriptOutput('\nPatched Docs/logins.dev with new passwords.');
}

main().catch((err) => {
  console.error(err);
  process.exit(1);
});
