Primeiro commit
This commit is contained in:
387
INTEGRACAO-PIX-GUIDE.md
Normal file
387
INTEGRACAO-PIX-GUIDE.md
Normal file
@@ -0,0 +1,387 @@
|
||||
# 🏦 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**
|
||||
```bash
|
||||
npm install mercadopago
|
||||
```
|
||||
|
||||
### **Passo 3: Configurar no .env**
|
||||
```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**
|
||||
```javascript
|
||||
// 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**
|
||||
```javascript
|
||||
// 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**
|
||||
```css
|
||||
/* 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**
|
||||
```javascript
|
||||
// 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**
|
||||
```sql
|
||||
-- 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!**
|
||||
Reference in New Issue
Block a user