import { Router, Request, Response } from 'express'
import { GoogleMerchantService, ProductData } from '../services/googleMerchantService'

const router = Router()

// Lazy initialization - só cria o serviço quando necessário
let merchantService: GoogleMerchantService | null = null

function getMerchantService(): GoogleMerchantService {
  if (!merchantService) {
    try {
      merchantService = new GoogleMerchantService()
    } catch (error) {
      throw new Error(
        `Google Merchant Service não configurado: ${error instanceof Error ? error.message : 'Unknown error'}. ` +
        `Configure GOOGLE_MERCHANT_CLIENT_ID e GOOGLE_MERCHANT_CLIENT_SECRET no arquivo .env`
      )
    }
  }
  return merchantService
}

/**
 * GET /api/merchant/auth
 * Inicia o fluxo de autenticação OAuth
 */
router.get('/auth', (req: Request, res: Response) => {
  try {
    const service = getMerchantService()
    const authUrl = service.getAuthUrl()
    const redirectUri = process.env.GOOGLE_MERCHANT_REDIRECT_URI || 'http://localhost:3000/api/merchant/callback'
    
    res.json({ 
      authUrl,
      redirectUri,
      instructions: [
        'Se receber erro "redirect_uri_mismatch":',
        '1. Vá em https://console.cloud.google.com/apis/credentials',
        '2. Clique no seu OAuth 2.0 Client ID',
        `3. Adicione esta URI exata em "Authorized redirect URIs": ${redirectUri}`,
        '4. Salve e tente novamente',
      ],
    })
  } catch (error) {
    res.status(500).json({
      error: 'Failed to generate auth URL',
      message: error instanceof Error ? error.message : 'Unknown error',
    })
  }
})

/**
 * GET /api/merchant/callback
 * Callback OAuth - recebe o código e retorna o refresh token
 */
router.get('/callback', async (req: Request, res: Response) => {
  try {
    const { code, error } = req.query

    if (error) {
      return res.send(`
        <!DOCTYPE html>
        <html>
        <head>
          <title>Erro de Autenticação</title>
          <style>
            body { font-family: Arial, sans-serif; max-width: 600px; margin: 50px auto; padding: 20px; }
            .error { background: #fee; border: 2px solid #fcc; padding: 20px; border-radius: 8px; }
            .code { background: #f5f5f5; padding: 10px; border-radius: 4px; font-family: monospace; }
          </style>
        </head>
        <body>
          <div class="error">
            <h2>❌ Erro de Autenticação</h2>
            <p><strong>Erro:</strong> ${error}</p>
            <p>Tente novamente ou verifique as configurações no Google Cloud Console.</p>
          </div>
        </body>
        </html>
      `)
    }

    if (!code) {
      return res.send(`
        <!DOCTYPE html>
        <html>
        <head>
          <title>Erro - Código não fornecido</title>
          <style>
            body { font-family: Arial, sans-serif; max-width: 600px; margin: 50px auto; padding: 20px; }
            .error { background: #fee; border: 2px solid #fcc; padding: 20px; border-radius: 8px; }
          </style>
        </head>
        <body>
          <div class="error">
            <h2>❌ Código de autorização não fornecido</h2>
            <p>O Google não retornou o código de autorização. Tente autenticar novamente.</p>
          </div>
        </body>
        </html>
      `)
    }

    const service = getMerchantService()
    const tokens = await service.getTokens(code as string)

    if (!tokens.refresh_token) {
      return res.send(`
        <!DOCTYPE html>
        <html>
        <head>
          <title>Refresh Token não recebido</title>
          <style>
            body { font-family: Arial, sans-serif; max-width: 700px; margin: 50px auto; padding: 20px; }
            .warning { background: #fff3cd; border: 2px solid #ffc107; padding: 20px; border-radius: 8px; }
            .code { background: #f5f5f5; padding: 10px; border-radius: 4px; font-family: monospace; margin: 10px 0; }
            .steps { background: #e7f3ff; padding: 15px; border-radius: 8px; margin-top: 20px; }
            ol { margin-left: 20px; }
          </style>
        </head>
        <body>
          <div class="warning">
            <h2>⚠️ Refresh Token não recebido</h2>
            <p>O Google não forneceu um refresh token. Isso geralmente acontece quando você já autorizou este app antes.</p>
            <div class="steps">
              <h3>Solução:</h3>
              <ol>
                <li>Vá em <a href="https://myaccount.google.com/permissions" target="_blank">https://myaccount.google.com/permissions</a></li>
                <li>Encontre "100mlstore Analytics" ou seu app</li>
                <li>Clique em "Remover acesso"</li>
                <li>Volte e autentique novamente</li>
              </ol>
            </div>
          </div>
        </body>
        </html>
      `)
    }

    // Página HTML amigável com o refresh token
    res.send(`
      <!DOCTYPE html>
      <html>
      <head>
        <title>Autenticação Concluída - Google Merchant</title>
        <style>
          body { 
            font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Arial, sans-serif; 
            max-width: 700px; 
            margin: 50px auto; 
            padding: 20px; 
            background: #f5f5f5;
          }
          .container {
            background: white;
            padding: 30px;
            border-radius: 12px;
            box-shadow: 0 2px 10px rgba(0,0,0,0.1);
          }
          .success { 
            background: #d4edda; 
            border: 2px solid #28a745; 
            padding: 20px; 
            border-radius: 8px; 
            margin-bottom: 20px;
          }
          .token-box { 
            background: #f8f9fa; 
            border: 2px solid #007bff;
            padding: 15px; 
            border-radius: 8px; 
            margin: 20px 0;
            word-break: break-all;
            font-family: 'Courier New', monospace;
            font-size: 12px;
            position: relative;
          }
          .copy-btn {
            background: #007bff;
            color: white;
            border: none;
            padding: 8px 16px;
            border-radius: 4px;
            cursor: pointer;
            margin-top: 10px;
            font-size: 14px;
          }
          .copy-btn:hover {
            background: #0056b3;
          }
          .instructions {
            background: #e7f3ff;
            padding: 20px;
            border-radius: 8px;
            margin-top: 20px;
          }
          .instructions ol {
            margin-left: 20px;
            line-height: 1.8;
          }
          .instructions code {
            background: #f1f1f1;
            padding: 2px 6px;
            border-radius: 3px;
            font-family: 'Courier New', monospace;
          }
          h1 { color: #28a745; margin-top: 0; }
          h2 { color: #333; margin-top: 0; }
          .checkmark { color: #28a745; font-size: 24px; }
        </style>
      </head>
      <body>
        <div class="container">
          <div class="success">
            <h1><span class="checkmark">✅</span> Autenticação Concluída com Sucesso!</h1>
            <p>Você recebeu o refresh token. Siga as instruções abaixo para completar a configuração.</p>
          </div>

          <h2>📋 Refresh Token:</h2>
          <div class="token-box" id="tokenBox">
            ${tokens.refresh_token}
          </div>
          <button class="copy-btn" onclick="copyToken()">📋 Copiar Refresh Token</button>

          <div class="instructions">
            <h2>📝 Próximos Passos:</h2>
            <ol>
              <li>Copie o <strong>refresh_token</strong> acima (ou clique no botão copiar)</li>
              <li>Abra o arquivo <code>backend/.env</code></li>
              <li>Adicione a linha: <code>GOOGLE_MERCHANT_REFRESH_TOKEN=${tokens.refresh_token}</code></li>
              <li>Salve o arquivo</li>
              <li><strong>Reinicie o servidor backend</strong> (Ctrl+C e depois <code>npm run dev</code>)</li>
              <li>Volte para a página Merchant e teste a sincronização</li>
            </ol>
          </div>

          <div style="margin-top: 30px; padding-top: 20px; border-top: 1px solid #ddd; color: #666; font-size: 12px;">
            <p><strong>Nota:</strong> Este token é sensível. Não compartilhe publicamente.</p>
            <p>Você pode fechar esta janela após copiar o token.</p>
          </div>
        </div>

        <script>
          function copyToken() {
            const token = '${tokens.refresh_token}';
            navigator.clipboard.writeText(token).then(() => {
              const btn = event.target;
              const originalText = btn.textContent;
              btn.textContent = '✅ Copiado!';
              btn.style.background = '#28a745';
              setTimeout(() => {
                btn.textContent = originalText;
                btn.style.background = '#007bff';
              }, 2000);
            }).catch(err => {
              alert('Erro ao copiar. Selecione o texto manualmente.');
            });
          }
        </script>
      </body>
      </html>
    `)
  } catch (error) {
    console.error('OAuth callback error:', error)
    res.status(500).send(`
      <!DOCTYPE html>
      <html>
      <head>
        <title>Erro</title>
        <style>
          body { font-family: Arial, sans-serif; max-width: 600px; margin: 50px auto; padding: 20px; }
          .error { background: #fee; border: 2px solid #fcc; padding: 20px; border-radius: 8px; }
        </style>
      </head>
      <body>
        <div class="error">
          <h2>❌ Erro ao processar autenticação</h2>
          <p><strong>Erro:</strong> ${error instanceof Error ? error.message : 'Unknown error'}</p>
          <p>Verifique o console do servidor para mais detalhes.</p>
        </div>
      </body>
      </html>
    `)
  }
})

/**
 * POST /api/merchant/sync-products
 * Sincroniza produtos do sistema para o Google Merchant Center
 */
router.post('/sync-products', async (req: Request, res: Response) => {
  try {
    const { orders } = req.body

    if (!orders || !Array.isArray(orders) || orders.length === 0) {
      return res.status(400).json({
        error: 'Orders array is required',
      })
    }

    // Agrupar produtos únicos por nome
    const uniqueProducts = new Map<string, {
      productName: string
      category: string
      price: number
      link: string
      imageLink: string
      availability: 'in stock' | 'out of stock'
    }>()

    orders.forEach((order: any) => {
      const key = order.productName
      if (!uniqueProducts.has(key)) {
        uniqueProducts.set(key, {
          productName: order.productName,
          category: order.productCategory || 'Outros',
          price: order.lineTotal || 0,
          link: `https://100mlstore.com/produto/${encodeURIComponent(order.productName)}`,
          imageLink: `https://100mlstore.com/images/${encodeURIComponent(order.productName)}.jpg`,
          availability: order.orderStatus === 'completed' ? 'in stock' : 'out of stock',
        })
      }
    })

    // Converter para formato Google Merchant
    const products: ProductData[] = Array.from(uniqueProducts.values()).map((product) => ({
      offerId: `PROD-${product.productName.replace(/\s+/g, '-').replace(/[^a-zA-Z0-9-]/g, '').toUpperCase().substring(0, 50)}`,
      title: product.productName,
      description: `${product.productName} - ${product.category}`,
      link: product.link,
      imageLink: product.imageLink,
      price: {
        value: product.price.toFixed(2),
        currency: 'EUR',
      },
      availability: product.availability,
      brand: '100mlstore',
      condition: 'new',
      category: product.category,
    }))

    // Enviar produtos para Google Merchant
    const service = getMerchantService()
    const results = []
    for (const product of products) {
      try {
        const result = await service.insertProduct(product)
        results.push({
          success: true,
          product: product.title,
          offerId: product.offerId,
          data: result,
        })
      } catch (error: any) {
        console.error(`Error syncing product ${product.title}:`, error)
        
        // Extrair informações do erro
        const errorData = error.originalError?.response?.data || error.response?.data || {}
        const errorMessage = errorData.error?.message || error.message || 'Unknown error'
        const errorCode = errorData.error?.code || error.code
        const errorDetails = errorData ? JSON.stringify(errorData, null, 2) : ''
        
        // Se o produto já existe, tenta atualizar
        if (errorMessage.includes('already exists') || 
            errorMessage.includes('duplicate') || 
            errorMessage.includes('already_exist') ||
            errorCode === 409) {
          try {
            const updateResult = await service.updateProduct(product.offerId, product)
            results.push({
              success: true,
              product: product.title,
              offerId: product.offerId,
              action: 'updated',
              data: updateResult,
            })
          } catch (updateError: any) {
            const updateErrorMessage = updateError.response?.data?.error?.message || updateError.message || 'Failed to update'
            results.push({
              success: false,
              product: product.title,
              offerId: product.offerId,
              error: updateErrorMessage,
              details: updateError.response?.data ? JSON.stringify(updateError.response.data, null, 2) : '',
            })
          }
        } else {
          results.push({
            success: false,
            product: product.title,
            offerId: product.offerId,
            error: errorMessage,
            details: errorDetails,
          })
        }
      }
    }

    const successCount = results.filter((r) => r.success).length
    const failCount = results.filter((r) => !r.success).length

    res.json({
      message: 'Sincronização concluída',
      summary: {
        total: products.length,
        success: successCount,
        failed: failCount,
      },
      results,
    })
  } catch (error) {
    console.error('Sync products error:', error)
    res.status(500).json({
      error: 'Erro ao sincronizar produtos',
      message: error instanceof Error ? error.message : 'Unknown error',
    })
  }
})

/**
 * GET /api/merchant/products
 * Lista produtos do Google Merchant Center
 */
router.get('/products', async (req: Request, res: Response) => {
  try {
    const service = getMerchantService()
    const maxResults = parseInt(req.query.maxResults as string) || 50
    const products = await service.listProducts(maxResults)
    res.json(products)
  } catch (error) {
    console.error('List products error:', error)
    res.status(500).json({
      error: 'Erro ao listar produtos',
      message: error instanceof Error ? error.message : 'Unknown error',
    })
  }
})

/**
 * GET /api/merchant/generate-feed
 * Gera feed XML no formato Google Merchant para upload manual
 */
router.post('/generate-feed', async (req: Request, res: Response) => {
  try {
    const { orders } = req.body

    if (!orders || !Array.isArray(orders)) {
      return res.status(400).json({
        error: 'Orders array is required',
      })
    }

    // Agrupar produtos únicos
    const uniqueProducts = new Map<string, any>()
    orders.forEach((order: any) => {
      const key = order.productName
      if (!uniqueProducts.has(key)) {
        uniqueProducts.set(key, {
          offerId: `PROD-${order.productName.replace(/\s+/g, '-').replace(/[^a-zA-Z0-9-]/g, '').toUpperCase().substring(0, 50)}`,
          title: order.productName,
          description: `${order.productName} - ${order.productCategory || 'Outros'}`,
          link: `https://100mlstore.com/produto/${encodeURIComponent(order.productName)}`,
          imageLink: `https://100mlstore.com/images/${encodeURIComponent(order.productName)}.jpg`,
          price: (order.lineTotal || 0).toFixed(2),
          availability: order.orderStatus === 'completed' ? 'in stock' : 'out of stock',
          brand: '100mlstore',
          condition: 'new',
          category: order.productCategory || 'Outros',
        })
      }
    })

    // Gerar XML
    const xml = `<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:g="http://base.google.com/ns/1.0">
  <channel>
    <title>100mlstore Products</title>
    <link>https://100mlstore.com</link>
    <description>Product feed for Google Merchant Center</description>
    ${Array.from(uniqueProducts.values())
      .map(
        (product) => `
    <item>
      <g:id>${escapeXml(product.offerId)}</g:id>
      <g:title>${escapeXml(product.title)}</g:title>
      <g:description>${escapeXml(product.description)}</g:description>
      <g:link>${escapeXml(product.link)}</g:link>
      <g:image_link>${escapeXml(product.imageLink)}</g:image_link>
      <g:price>${product.price} EUR</g:price>
      <g:availability>${product.availability}</g:availability>
      <g:brand>${escapeXml(product.brand)}</g:brand>
      <g:condition>${product.condition}</g:condition>
      <g:google_product_category>${escapeXml(product.category)}</g:google_product_category>
    </item>`
      )
      .join('')}
  </channel>
</rss>`

    res.setHeader('Content-Type', 'application/xml')
    res.setHeader('Content-Disposition', 'attachment; filename="google-merchant-feed.xml"')
    res.send(xml)
  } catch (error) {
    console.error('Generate feed error:', error)
    res.status(500).json({
      error: 'Erro ao gerar feed',
      message: error instanceof Error ? error.message : 'Unknown error',
    })
  }
})

function escapeXml(unsafe: string): string {
  return unsafe
    .replace(/&/g, '&amp;')
    .replace(/</g, '&lt;')
    .replace(/>/g, '&gt;')
    .replace(/"/g, '&quot;')
    .replace(/'/g, '&apos;')
}

export default router
