Files
App-Estoque-LiberiKids/INTEGRACAO-PIX-GUIDE.md
2025-10-14 14:04:17 -03:00

9.0 KiB
Raw Blame History

🏦 Integração PIX com QR Code - Liberi Kids

🎯 Opções de Integração PIX

1. Mercado Pago (Recomendado)

  • Gratuito para começar
  • QR Code automático
  • Webhook para confirmação
  • Documentação excelente

2. PagSeguro/PagBank

  • PIX instantâneo
  • Taxas competitivas

3. Asaas

  • Focado em pequenas empresas
  • PIX + Boleto + Cartão

🚀 Implementação Mercado Pago

Passo 1: Criar Conta

  1. Acesse: https://www.mercadopago.com.br/developers
  2. Crie conta de desenvolvedor
  3. Obtenha suas credenciais:
    • Public Key (pk_test_...)
    • Access Token (TEST-...)

Passo 2: Instalar SDK

npm install mercadopago

Passo 3: Configurar no .env

# Mercado Pago PIX
MERCADOPAGO_ACCESS_TOKEN=TEST-sua_access_token_aqui
MERCADOPAGO_PUBLIC_KEY=pk_test_sua_public_key_aqui

Passo 4: API Backend

// server-supabase.js - Adicionar rota PIX

const mercadopago = require('mercadopago');

// Configurar Mercado Pago
mercadopago.configurations.setAccessToken(process.env.MERCADOPAGO_ACCESS_TOKEN);

// Rota para gerar PIX
app.post('/api/pix/gerar', async (req, res) => {
  try {
    const { valor, descricao, cliente_email, venda_id } = req.body;
    
    const payment_data = {
      transaction_amount: parseFloat(valor),
      description: descricao || `Venda #${venda_id} - Liberi Kids`,
      payment_method_id: 'pix',
      payer: {
        email: cliente_email || 'cliente@liberikids.com'
      },
      external_reference: venda_id.toString(),
      notification_url: `${process.env.BASE_URL}/api/pix/webhook`
    };
    
    const payment = await mercadopago.payment.create(payment_data);
    
    res.json({
      success: true,
      payment_id: payment.body.id,
      qr_code: payment.body.point_of_interaction.transaction_data.qr_code,
      qr_code_base64: payment.body.point_of_interaction.transaction_data.qr_code_base64,
      pix_copy_paste: payment.body.point_of_interaction.transaction_data.qr_code,
      expiration_date: payment.body.date_of_expiration
    });
    
  } catch (error) {
    console.error('Erro ao gerar PIX:', error);
    res.status(500).json({ success: false, error: error.message });
  }
});

// Webhook para receber confirmação de pagamento
app.post('/api/pix/webhook', async (req, res) => {
  try {
    const { type, data } = req.body;
    
    if (type === 'payment') {
      const payment = await mercadopago.payment.get(data.id);
      
      if (payment.body.status === 'approved') {
        const venda_id = payment.body.external_reference;
        
        // Atualizar status da venda no banco
        const { error } = await supabase
          .from('vendas')
          .update({ 
            status_pagamento: 'pago',
            data_pagamento: new Date(),
            pix_payment_id: payment.body.id
          })
          .eq('id', venda_id);
        
        if (!error) {
          console.log(`Pagamento confirmado para venda #${venda_id}`);
        }
      }
    }
    
    res.status(200).send('OK');
  } catch (error) {
    console.error('Erro no webhook PIX:', error);
    res.status(500).send('Error');
  }
});

Passo 5: Frontend - Modal PIX

// Adicionar ao Vendas.js

const [showPixModal, setShowPixModal] = useState(false);
const [pixData, setPixData] = useState(null);
const [loadingPix, setLoadingPix] = useState(false);

const gerarPix = async (venda) => {
  setLoadingPix(true);
  try {
    const response = await fetch('/api/pix/gerar', {
      method: 'POST',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify({
        valor: venda.valor_total,
        descricao: `Venda #${venda.id_venda} - Liberi Kids`,
        cliente_email: venda.cliente?.email,
        venda_id: venda.id
      })
    });
    
    const data = await response.json();
    
    if (data.success) {
      setPixData(data);
      setShowPixModal(true);
    } else {
      toast.error('Erro ao gerar PIX');
    }
  } catch (error) {
    toast.error('Erro ao gerar PIX');
  }
  setLoadingPix(false);
};

// Modal PIX
{showPixModal && (
  <div className="modal-overlay">
    <div className="modal pix-modal">
      <div className="modal-header">
        <h3>🏦 Pagamento PIX</h3>
        <button onClick={() => setShowPixModal(false)}>×</button>
      </div>
      
      <div className="modal-body">
        <div className="pix-content">
          <div className="qr-code-section">
            <h4>QR Code PIX</h4>
            <img 
              src={`data:image/png;base64,${pixData.qr_code_base64}`}
              alt="QR Code PIX"
              className="qr-code-image"
            />
          </div>
          
          <div className="pix-copy-section">
            <h4>Código PIX (Copiar e Colar)</h4>
            <div className="pix-code-container">
              <input
                type="text"
                value={pixData.pix_copy_paste}
                readOnly
                className="pix-code-input"
              />
              <button
                onClick={() => {
                  navigator.clipboard.writeText(pixData.pix_copy_paste);
                  toast.success('Código PIX copiado!');
                }}
                className="btn-copy-pix"
              >
                📋 Copiar
              </button>
            </div>
          </div>
          
          <div className="pix-info">
            <p><strong>Valor:</strong> R$ {parseFloat(pixData.transaction_amount).toFixed(2)}</p>
            <p><strong>Válido até:</strong> {new Date(pixData.expiration_date).toLocaleString()}</p>
            <p className="pix-instructions">
              📱 <strong>Como pagar:</strong><br/>
              1. Abra o app do seu banco<br/>
              2. Escaneie o QR Code ou cole o código PIX<br/>
              3. Confirme o pagamento
            </p>
          </div>
        </div>
      </div>
    </div>
  </div>
)}

Passo 6: CSS para Modal PIX

/* styles/pix-integration.css */

.pix-modal {
  max-width: 500px;
  width: 90vw;
}

.pix-content {
  text-align: center;
}

.qr-code-section {
  margin-bottom: 20px;
}

.qr-code-image {
  max-width: 200px;
  height: auto;
  border: 2px solid #ddd;
  border-radius: 8px;
  padding: 10px;
  background: white;
}

.pix-copy-section {
  margin-bottom: 20px;
}

.pix-code-container {
  display: flex;
  gap: 10px;
  margin-top: 10px;
}

.pix-code-input {
  flex: 1;
  padding: 10px;
  border: 1px solid #ddd;
  border-radius: 4px;
  font-family: monospace;
  font-size: 12px;
}

.btn-copy-pix {
  background: #00d4aa;
  color: white;
  border: none;
  padding: 10px 15px;
  border-radius: 4px;
  cursor: pointer;
  white-space: nowrap;
}

.btn-copy-pix:hover {
  background: #00b894;
}

.pix-info {
  background: #f8f9fa;
  padding: 15px;
  border-radius: 8px;
  text-align: left;
}

.pix-instructions {
  margin-top: 10px;
  font-size: 14px;
  color: #666;
}

.btn-pix {
  background: #00d4aa;
  color: white;
  border: none;
  padding: 8px 12px;
  border-radius: 4px;
  cursor: pointer;
  font-size: 12px;
}

.btn-pix:hover {
  background: #00b894;
}

🎯 Integração no Sistema de Vendas

1. Adicionar Botão PIX na Lista de Vendas

// Na tabela de vendas, adicionar botão PIX
<button
  onClick={() => gerarPix(venda)}
  className="btn-icon btn-pix"
  title="Gerar PIX"
  disabled={loadingPix}
>
  🏦 PIX
</button>

2. Adicionar Campo no Banco de Dados

-- Adicionar colunas para controle de PIX
ALTER TABLE vendas ADD COLUMN IF NOT EXISTS status_pagamento VARCHAR(20) DEFAULT 'pendente';
ALTER TABLE vendas ADD COLUMN IF NOT EXISTS data_pagamento TIMESTAMP;
ALTER TABLE vendas ADD COLUMN IF NOT EXISTS pix_payment_id VARCHAR(100);

3. Dashboard com Status de Pagamentos

  • Vendas pendentes de pagamento
  • Vendas pagas via PIX
  • Relatório de recebimentos

💰 Custos e Taxas

Mercado Pago:

  • PIX: 0,99% por transação
  • Sem mensalidade
  • Recebimento em 1 dia útil

PagSeguro:

  • PIX: 0,99% por transação
  • Recebimento em 1 dia útil

Asaas:

  • PIX: R$ 0,20 por transação
  • Melhor para alto volume

🔒 Segurança

  1. Nunca exponha as credenciais no frontend
  2. Use HTTPS sempre em produção
  3. Valide webhooks com assinatura
  4. Monitore transações suspeitas

📱 Funcionalidades Extras

1. WhatsApp com PIX

  • Enviar QR Code via WhatsApp
  • Link de pagamento direto

2. Relatórios PIX

  • Vendas pagas via PIX
  • Tempo médio de pagamento
  • Conversão PIX vs outros métodos

3. Notificações

  • Email quando PIX for pago
  • Notificação no sistema
  • Atualização automática do status

🎉 Benefícios da Integração

  • Pagamento instantâneo
  • Sem taxas para o cliente
  • QR Code automático
  • Confirmação automática
  • Integração com WhatsApp
  • Relatórios detalhados

🚀 Com essa integração, seu sistema Liberi Kids terá pagamentos PIX completos com QR Code automático!