// scripts/scim-csrf-positive-verify.ts
//
// §3(a) gold-standard positive proof for the /scim/v2/* CSRF exemption.
//
// The curl battery already proved: no-bearer POST -> 401 (reaches handler, was 403),
// admin /api -> 403 (CSRF kept), non-scim /api -> 403 (CSRF alive). This harness adds
// the explicit (a)+(b) PAIR with a VALID bearer:
//   POSITIVE: valid bearer + NO csrf -> 201 CREATED (write proceeds on its own logic, no 403)
//   NEGATIVE: no bearer  + NO csrf -> 401 (bearer still gates)
//
// The bearer token is generated in-memory and NEVER printed (Rule 1). All seeded
// rows (config, provision, synced local user) are torn down in finally.
//
// Run: npx tsx scripts/scim-csrf-positive-verify.ts

import { db, withBypassRls } from "../server/db";
import { encryptionService } from "../server/lib/encryption-service";
import { scimConfigs, scimProvisions } from "../shared/schema-integrations";
import { users } from "../shared/schema";
import { eq } from "drizzle-orm";
import { randomBytes } from "crypto";

const B = "http://localhost:5000";
const TAG = randomBytes(4).toString("hex");
const TEST_TENANT = `scim-csrf-verify-${TAG}`;       // throwaway: no FK, no collision (0 existing configs)
const TEST_USERNAME = `csrf-pos-probe-${TAG}@verify.local`;

async function main() {
  // Dev-only guard — this harness SEEDS and DELETES rows against the app DB. Never run in prod.
  if (process.env.NODE_ENV === "production") {
    console.error("REFUSING: scim-csrf-positive-verify is a dev-only harness (seeds/deletes rows).");
    process.exit(3);
  }

  const rawToken = `verify_${randomBytes(40).toString("hex")}`; // in-memory only — never logged
  const encryptedBearerToken = encryptionService.encrypt(rawToken);

  await withBypassRls((bdb) =>
    bdb.insert(scimConfigs).values({
      tenantId: TEST_TENANT,
      providerName: "csrf-verify",
      encryptedBearerToken,
      isActive: true,
    }));

  let posStatus = 0, posClass = "", negStatus = 0;
  try {
    // POSITIVE — valid bearer, NO csrf token
    const r = await fetch(`${B}/scim/v2/Users`, {
      method: "POST",
      headers: { "Content-Type": "application/json", Authorization: `Bearer ${rawToken}` },
      body: JSON.stringify({ userName: TEST_USERNAME, displayName: "Verify Probe", active: true }),
    });
    posStatus = r.status;
    const txt = await r.text();
    // Classify by STATUS, not a body substring (the 201 body echoes our own fields and
    // would false-match a "CSRF" needle). A real CSRF block is HTTP 403.
    posClass = posStatus === 403 ? "CSRF_BLOCK(403)" : posStatus === 201 ? "CREATED" : `OTHER(${posStatus}):${txt.slice(0, 80)}`;

    // NEGATIVE — no bearer, NO csrf token (re-confirm the gate in the same harness)
    const r2 = await fetch(`${B}/scim/v2/Users`, {
      method: "POST",
      headers: { "Content-Type": "application/json" },
      body: JSON.stringify({ userName: `neg-${TEST_USERNAME}` }),
    });
    negStatus = r2.status;
  } finally {
    await withBypassRls((bdb) => bdb.delete(scimProvisions).where(eq(scimProvisions.tenantId, TEST_TENANT)));
    await db.delete(users).where(eq(users.username, TEST_USERNAME));
    await withBypassRls((bdb) => bdb.delete(scimConfigs).where(eq(scimConfigs.tenantId, TEST_TENANT)));
  }

  console.log(JSON.stringify({
    positive_validBearer_noCsrf: { status: posStatus, class: posClass, expect: "201 CREATED, no 403" },
    negative_noBearer_noCsrf: { status: negStatus, expect: "401" },
  }, null, 2));

  const pass = posStatus === 201 && posClass === "CREATED" && negStatus === 401;
  console.log(pass ? "POSITIVE-PROOF: PASS" : "POSITIVE-PROOF: FAIL");
  process.exit(pass ? 0 : 1);
}

main().catch((e) => { console.error("script error:", e?.message ?? e); process.exit(2); });
