import { DocumentBuilder } from "@nestjs/swagger";

const description = [
  "Pasarela de pagos multi-tenant, multi-provider.",
  "",
  "## Autenticación",
  "",
  "Hay **dos esquemas Bearer distintos**. El candado de cada endpoint indica cuál usar.",
  "",
  "### 🔑 `bearerAuth` — API key del merchant",
  "",
  "- **Formato:** `sk_test_…`, `sk_live_…`, `pk_test_…`, `pk_live_…`",
  "- **Header:** `Authorization: Bearer sk_test_xxxxxxxxxxxx`",
  "- **Cómo obtenerla:** un admin emite la primera key vía `POST /v1/admin/merchants/{merchantId}/api-keys`. El campo `secret` de la respuesta **solo se muestra una vez** — guardalo en password manager.",
  "- **Scopes:** `full` (todo) o `restricted` (no puede tocar provider-configs, webhook-endpoints ni refunds).",
  "- **Usar en:** todos los endpoints de comercio — `/payment-intents`, `/refunds`, `/customers`, `/provider-configs`, `/webhook-endpoints`, `/merchants/me`, etc.",
  "",
  "### 🛡️ `adminUserAuth` — JWT de usuario admin del gateway",
  "",
  "- **Formato:** JWT firmado con `ADMIN_JWT_SECRET`.",
  "- **Header:** `Authorization: Bearer <accessToken>`.",
  "- **Cómo obtenerlo:** `POST /v1/admin/auth/login` con email + password de un `admin_user`. Devuelve `accessToken` (15 min) y `refreshToken` (30 días).",
  "- **Renovación:** `POST /v1/admin/auth/refresh` con el `refreshToken`.",
  "- **Usar en:** todos los endpoints bajo `/v1/admin/*` — crear merchants, emitir API keys, inspeccionar eventos.",
  "",
  "### Errores comunes",
  "",
  "| Mensaje | Causa | Cómo arreglar |",
  "|---|---|---|",
  "| `Invalid API key format` | Mandaste `adm_…` o algo arbitrario donde se espera `sk_*` / `pk_*` | Usá la key del merchant, no el admin token |",
  "| `Missing Bearer token` | El header `Authorization` no llegó o no empieza con `Bearer ` | Verificá auth en el cliente HTTP |",
  "| `Invalid API key` | La key no existe o fue revocada | Emití una nueva con el admin |",
  "| `Merchant is not active` | El merchant está `suspended` o `disabled` | Reactivá el merchant vía admin |",
  "| `API key does not have permission for this action` (403) | Scope `restricted` intentando un endpoint sensible | Generá una key con `scope: \"full\"` |",
  "",
  "## Convenciones generales",
  "",
  "- **Versionado:** todas las rutas viven bajo `/v1`.",
  "- **IDs:** prefijo del recurso + ULID time-ordered (`mer_`, `pi_`, `pa_`, `re_`, `cs_`, `whe_`, `evt_`, `wei_`, `cus_`, `pcfg_`, `key_`).",
  "- **Idempotency:** endpoints de creación aceptan header `Idempotency-Key` (ventana 24h, mismo key + mismo merchant ⇒ devuelve el intent original).",
  "- **Paginación:** cursor-based. Respuesta `{ data: [...], nextCursor: string | null }`.",
  "- **Montos:** enteros en la unidad menor de la moneda (PYG es zero-decimal: `150000` = 150.000 Gs; USD: `12500` = USD 125,00).",
  "- **Errores:** formato uniforme `{ error: { code, message, details? } }` con `statusCode` HTTP estándar.",
  "",
  "## Webhooks",
  "",
  "- **Outbound:** firmamos cada evento con HMAC-SHA256 usando el `whsec_…` del endpoint del merchant. Headers: `X-Payments-Signature: t=<unix>,v1=<hex>`, `X-Payments-Event-Id`, `X-Payments-Event-Type`. Verificá la firma + ventana de 5 min para evitar replays.",
  "- **Inbound (de providers):** el adapter del provider verifica firma propia (ej. dLocal usa `X-Dlocalgo-Signature`). El body se preserva raw para que la firma sea reproducible.",
].join("\n");

export const SWAGGER_VERSION = "1.0.0";

export function buildSwaggerConfig(opts: { serverUrl?: string } = {}) {
  const builder = new DocumentBuilder()
    .setTitle("Novasis Pay")
    .setDescription(description)
    .setVersion(SWAGGER_VERSION);

  if (opts.serverUrl) {
    builder.addServer(opts.serverUrl, "Local");
  }

  return builder
    .addBearerAuth(
      {
        type: "http",
        scheme: "bearer",
        bearerFormat: "sk_test_… / sk_live_… / pk_test_… / pk_live_…",
        description:
          "API key del **merchant**. Se emite vía `POST /v1/admin/merchants/{merchantId}/api-keys` y se devuelve **una sola vez** en el campo `secret`. " +
          "Usar en todos los endpoints de comercio (payment-intents, refunds, customers, provider-configs, webhook-endpoints, merchants/me).",
      },
      "bearerAuth",
    )
    .addBearerAuth(
      {
        type: "http",
        scheme: "bearer",
        bearerFormat: "JWT",
        description:
          "JWT de usuario admin. Obtenelo vía `POST /v1/admin/auth/login` (email + password). " +
          "Renovalo con `POST /v1/admin/auth/refresh`. Válido para endpoints bajo `/v1/admin/*`.",
      },
      "adminUserAuth",
    )
    .build();
}

export const SWAGGER_CUSTOM_CSS = `
  .swagger-ui .markdown p,
  .swagger-ui .markdown li,
  .swagger-ui .renderedMarkdown p,
  .swagger-ui .renderedMarkdown li { line-height: 1.7; }
  .swagger-ui .markdown ul,
  .swagger-ui .renderedMarkdown ul { margin: 8px 0; }
  .swagger-ui .markdown li,
  .swagger-ui .renderedMarkdown li { margin: 6px 0; }
  .swagger-ui .markdown code,
  .swagger-ui .renderedMarkdown code { padding: 2px 6px; line-height: 1.4; display: inline-block; }
  .swagger-ui .markdown table,
  .swagger-ui .renderedMarkdown table { border-collapse: collapse; margin: 12px 0; }
  .swagger-ui .markdown th,
  .swagger-ui .markdown td,
  .swagger-ui .renderedMarkdown th,
  .swagger-ui .renderedMarkdown td { border: 1px solid #444; padding: 6px 10px; }
`;
