#!/usr/bin/env node

/**
 * Script de test COMPLET Odentas Sign + Vérification + Ledger
 * 
 * Workflow complet:
 * 1. Upload PDF → S3
 * 2. Crée demande de signature
 * 3. Affiche les liens pour signer manuellement (Employeur puis Salarié)
 * 4. Attend que les 2 signatures soient faites
 * 5. Lance le scellement PAdES
 * 6. Crée la preuve de vérification avec ledger S3 Compliance Lock
 * 7. Affiche le lien de vérification publique
 */

const fs = require('fs');
const path = require('path');
const { S3Client, PutObjectCommand } = require('@aws-sdk/client-s3');

// Configuration
const PDF_PATH = path.join(__dirname, 'test-contrat.pdf');
const BUCKET = process.env.ODENTAS_SIGN_BUCKET || 'odentas-sign';
const REGION = process.env.AWS_REGION || 'eu-west-3';
const API_URL = process.env.NEXT_PUBLIC_APP_URL || 'http://localhost:3000';

// Emails pour le test
const EMPLOYEUR_EMAIL = 'paie@odentas.fr';
const SALARIE_EMAIL = 'renaud.breviere@gmail.com';

// Couleurs console
const colors = {
  reset: '\x1b[0m',
  bright: '\x1b[1m',
  green: '\x1b[32m',
  blue: '\x1b[34m',
  yellow: '\x1b[33m',
  cyan: '\x1b[36m',
  red: '\x1b[31m',
};

function log(emoji, text, color = colors.reset) {
  console.log(`${color}${emoji} ${text}${colors.reset}`);
}

function sleep(ms) {
  return new Promise(resolve => setTimeout(resolve, ms));
}

async function checkSignaturesStatus(requestId) {
  const response = await fetch(`${API_URL}/api/odentas-sign/requests/${requestId}/status`);
  if (!response.ok) return null;
  const data = await response.json();
  return data;
}

async function waitForSignatures(requestId, signers) {
  log('⏳', 'En attente des signatures...', colors.yellow);
  console.log('');
  
  let attempts = 0;
  const maxAttempts = 120; // 10 minutes max
  
  while (attempts < maxAttempts) {
    const status = await checkSignaturesStatus(requestId);
    
    if (status && status.signers) {
      const allSigned = status.signers.every(s => s.has_signed);
      const signedCount = status.signers.filter(s => s.has_signed).length;
      
      process.stdout.write(`\r⏳ Signatures: ${signedCount}/${status.signers.length} `);
      
      if (allSigned) {
        console.log('');
        log('✅', 'Toutes les signatures sont complètes !', colors.green);
        return true;
      }
    }
    
    await sleep(5000); // Vérifier toutes les 5 secondes
    attempts++;
  }
  
  log('❌', 'Timeout: signatures non complètes après 10 minutes', colors.red);
  return false;
}

async function sealDocument(requestId) {
  log('🔒', 'Lancement du scellement PAdES...', colors.cyan);
  
  const response = await fetch(`${API_URL}/api/odentas-sign/seal-document`, {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify({ requestId }),
  });
  
  if (!response.ok) {
    const error = await response.json();
    throw new Error(error.error || 'Erreur scellement');
  }
  
  const result = await response.json();
  log('✅', `Document scellé avec ${result.signatures_count} signatures PAdES`, colors.green);
  return result;
}

async function createVerificationProof(sealedPdfUrl, signatureData) {
  log('📜', 'Création de la preuve de vérification avec ledger immuable...', colors.cyan);
  
  // Simuler les données de signature (à adapter selon votre API)
  const verificationData = {
    document_name: signatureData.title || 'Document Test',
    pdf_url: sealedPdfUrl,
    signer_name: 'Odentas Media SAS',
    signer_email: 'paie@odentas.fr',
    signature_hash: signatureData.pdf_sha256 || 'test-hash',
    signature_hex: 'test-hex-signature',
    certificate_info: {
      issuer: 'Odentas CA',
      subject: 'CN=Odentas Media SAS',
      valid_from: new Date().toISOString(),
      valid_until: new Date(Date.now() + 365 * 24 * 60 * 60 * 1000).toISOString(),
      serial_number: '1234567890',
    },
    timestamp: {
      tsa_url: 'https://freetsa.org/tsr',
      timestamp: new Date().toISOString(),
      hash: signatureData.tsa_token_sha256 || 'test-tsa-hash',
    },
  };
  
  const response = await fetch(`${API_URL}/api/signatures/create-verification`, {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify(verificationData),
  });
  
  if (!response.ok) {
    const error = await response.json();
    throw new Error(error.error || 'Erreur création preuve');
  }
  
  const result = await response.json();
  log('✅', 'Preuve de vérification créée avec succès', colors.green);
  return result;
}

async function main() {
  console.log('');
  log('🚀', '═══════════════════════════════════════════════════════', colors.bright);
  log('🚀', '  ODENTAS SIGN - TEST COMPLET (Signature + Ledger)    ', colors.bright);
  log('🚀', '═══════════════════════════════════════════════════════', colors.bright);
  console.log('');
  
  // 1. Vérifier que le PDF existe
  if (!fs.existsSync(PDF_PATH)) {
    log('❌', `PDF introuvable: ${PDF_PATH}`, colors.red);
    process.exit(1);
  }
  
  const pdfBuffer = fs.readFileSync(PDF_PATH);
  log('✅', `PDF chargé: ${(pdfBuffer.length / 1024).toFixed(1)} KB`, colors.green);
  console.log('');
  
  // 2. Upload vers S3
  log('📤', 'Upload du PDF vers S3...', colors.blue);
  const testRef = `TEST-${Date.now()}`;
  const s3Key = `source/test/${testRef}.pdf`;
  
  const s3Client = new S3Client({ region: REGION });
  
  try {
    await s3Client.send(new PutObjectCommand({
      Bucket: BUCKET,
      Key: s3Key,
      Body: pdfBuffer,
      ContentType: 'application/pdf',
      Metadata: {
        test: 'true',
        uploaded_by: 'test-complete-script',
        original_name: 'test-contrat.pdf',
      },
    }));
    
    log('✅', `PDF uploadé: s3://${BUCKET}/${s3Key}`, colors.green);
  } catch (error) {
    log('❌', `Erreur upload S3: ${error.message}`, colors.red);
    process.exit(1);
  }
  console.log('');
  
  // 3. Créer la demande de signature
  log('📝', 'Création de la demande de signature...', colors.blue);
  
  const requestBody = {
    contractId: `test-complete-${Date.now()}`,
    contractRef: testRef,
    pdfS3Key: s3Key,
    title: 'Contrat CDDU - Test Complet',
    signers: [
      {
        role: 'Employeur',
        name: 'Odentas Paie',
        email: EMPLOYEUR_EMAIL,
      },
      {
        role: 'Salarié',
        name: 'Renaud Breviere',
        email: SALARIE_EMAIL,
      },
    ],
    positions: [
      {
        role: 'Employeur',
        page: 3,
        x: 20,
        y: 260,
        w: 150,
        h: 60,
        kind: 'signature',
      },
      {
        role: 'Salarié',
        page: 3,
        x: 180,
        y: 260,
        w: 150,
        h: 60,
        kind: 'signature',
      },
    ],
  };
  
  let result;
  try {
    const response = await fetch(`${API_URL}/api/odentas-sign/requests/create`, {
      method: 'POST',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify(requestBody),
    });
    
    if (!response.ok) {
      const error = await response.json();
      throw new Error(error.error || `HTTP ${response.status}`);
    }
    
    result = await response.json();
    log('✅', 'Demande créée avec succès !', colors.green);
  } catch (error) {
    log('❌', `Erreur création demande: ${error.message}`, colors.red);
    process.exit(1);
  }
  
  console.log('');
  log('📋', '═══════════════════════════════════════════════════════', colors.bright);
  log('📋', '  LIENS DE SIGNATURE (ouvrir dans le navigateur)      ', colors.bright);
  log('📋', '═══════════════════════════════════════════════════════', colors.bright);
  console.log('');
  
  result.signers.forEach((signer, index) => {
    console.log(`${colors.cyan}${index + 1}. ${signer.role} - ${signer.name}${colors.reset}`);
    console.log(`   ${colors.yellow}${signer.signatureUrl}${colors.reset}`);
    console.log('');
  });
  
  log('💡', 'Ouvrez ces liens et signez dans l\'ordre:', colors.yellow);
  log('💡', '  1. D\'abord l\'Employeur', colors.yellow);
  log('💡', '  2. Puis le Salarié', colors.yellow);
  log('💡', 'Les codes OTP sont dans les logs du serveur (mode TEST)', colors.yellow);
  console.log('');
  
  // Sauvegarder les infos
  const testInfoPath = path.join(__dirname, 'test-complete-info.json');
  fs.writeFileSync(testInfoPath, JSON.stringify(result, null, 2));
  log('💾', `Infos sauvegardées: ${testInfoPath}`, colors.green);
  console.log('');
  
  // 4. Attendre que les 2 signatures soient complètes
  const allSigned = await waitForSignatures(result.request.id, result.signers);
  
  if (!allSigned) {
    log('❌', 'Test interrompu: signatures non complètes', colors.red);
    process.exit(1);
  }
  
  console.log('');
  
  // 5. Lancer le scellement PAdES
  let sealResult;
  try {
    sealResult = await sealDocument(result.request.id);
  } catch (error) {
    log('❌', `Erreur scellement: ${error.message}`, colors.red);
    process.exit(1);
  }
  
  console.log('');
  
  // 6. Créer la preuve de vérification avec ledger
  let verificationResult;
  try {
    verificationResult = await createVerificationProof(
      sealResult.signed_s3_key,
      sealResult
    );
  } catch (error) {
    log('❌', `Erreur création preuve: ${error.message}`, colors.red);
    log('⚠️', 'Le document est scellé mais la preuve n\'a pas pu être créée', colors.yellow);
    process.exit(1);
  }
  
  console.log('');
  log('🎉', '═══════════════════════════════════════════════════════', colors.green);
  log('🎉', '  TEST COMPLET RÉUSSI !                                ', colors.green);
  log('🎉', '═══════════════════════════════════════════════════════', colors.green);
  console.log('');
  
  if (verificationResult) {
    log('🔗', 'LIEN DE VÉRIFICATION PUBLIQUE:', colors.cyan);
    console.log(`   ${colors.bright}${verificationResult.verification_url}${colors.reset}`);
    console.log('');
    
    if (verificationResult.ledger) {
      log('🔒', 'LEDGER IMMUABLE (S3 Compliance Lock):', colors.cyan);
      console.log(`   Clé S3: ${verificationResult.ledger.s3_key}`);
      console.log(`   Verrouillé jusqu'au: ${verificationResult.ledger.locked_until}`);
      console.log(`   Mode: COMPLIANCE (aucune suppression possible)`);
      console.log('');
    }
    
    if (verificationResult.proof_pdf_url) {
      log('📄', 'PDF DE PREUVE:', colors.cyan);
      console.log(`   ${verificationResult.proof_pdf_url}`);
      console.log('');
    }
  }
  
  log('✅', 'Document signé: ' + sealResult.signed_s3_key, colors.green);
  console.log('');
}

main().catch(error => {
  console.error('');
  log('❌', `ERREUR FATALE: ${error.message}`, colors.red);
  console.error(error.stack);
  process.exit(1);
});
