Getting Started
Get up and running with Bloque Payments in minutes. This guide will walk you through setting up both the frontend React component and the backend SDK.
Installation
Frontend (React)
Install the React components package:
npm add @bloque/payments-react
yarn add @bloque/payments-react
pnpm add @bloque/payments-react
bun add @bloque/payments-react
deno add npm:@bloque/payments-react
Backend (Node.js/Bun)
Install the backend SDK:
yarn add @bloque/payments
pnpm add @bloque/payments
deno add npm:@bloque/payments
API Key
To use Bloque Payments, you'll need an API key. You can obtain one from the Bloque Dashboard.
:::tip API Keys
Bloque provides two types of API keys:
- Public API Key: Can be safely used in the client (frontend) to initialize the SDK.
- Secret API Key: Should only be used on the backend. Never expose it in client-side code.
:::
Quick Start: Complete Integration
Here's a complete example showing how to integrate Bloque Payments with React on the frontend and Node.js/Bun on the backend.
Frontend Setup (React)
import { init, BloqueCheckout } from '@bloque/payments-react';
import type {
CheckoutConfig,
AppearanceConfig,
PaymentResponse,
} from '@bloque/payments-react';
// Initialize SDK (do this once at app startup)
init({
publicApiKey: 'pk_live_...',
mode: 'sandbox',
});
function CheckoutPage() {
// Configuration
const config: CheckoutConfig = {
payment_methods: ['card', 'pse', 'cash'],
amount: 2999, // Amount in smallest currency unit (e.g., cents)
currency: 'USD',
};
// Appearance customization
const appearance: AppearanceConfig = {
primaryColor: '#10b981',
borderRadius: '12px',
fontFamily: 'Inter, system-ui, sans-serif',
};
// Handle payment submission
const handleSubmit = async (payload) => {
const response = await fetch('/api/payments', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(payload),
});
if (!response.ok) {
throw new Error('Payment failed');
}
return response.json();
};
return (
<BloqueCheckout
config={config}
appearance={appearance}
onSubmit={handleSubmit}
onSuccess={(response) => {
console.log('Payment successful!');
console.log('Payment ID:', response.id);
console.log('Status:', response.status);
window.location.href = '/success';
}}
onError={(error) => {
console.error('Payment failed:', error.message);
alert(`Payment failed: ${error.message}`);
}}
/>
);
}
export default CheckoutPage;
Backend Setup (Node.js/Bun)
import { Bloque } from '@bloque/payments';
import express from 'express';
const app = express();
app.use(express.json());
// Initialize Bloque SDK
const bloque = new Bloque({
apiKey: process.env.BLOQUE_API_KEY!,
mode: 'production', // or 'sandbox' for testing
});
// Payment endpoint
app.post('/api/payments', async (req, res) => {
try {
const payload = req.body;
// Process payment using Bloque SDK
const payment = await bloque.payments.create({
payment: payload,
});
res.json(payment);
} catch (error) {
console.error('Payment error:', error);
res.status(500).json({
success: false,
error: error.message,
});
}
});
app.listen(3000, () => {
console.log('Server running on http://localhost:3000');
});
Environment Variables
Create a .env file in your backend project:
# .env
BLOQUE_API_KEY=your_api_key_here
BLOQUE_MODE=sandbox # or 'production'
Load them in your application:
import 'dotenv/config';
const bloque = new Bloque({
apiKey: process.env.BLOQUE_API_KEY!,
mode: process.env.BLOQUE_MODE as 'sandbox' | 'production',
});
Configuration Options
SDK Configuration
Modes
sandbox: For testing and development. No real transactions.
production: For live operations with real payments.
Checkout Configuration
Configure the payment experience:
const config: CheckoutConfig = {
payment_methods: ['card', 'pse', 'cash'], // Available payment methods
amount: 2999, // Amount in smallest currency unit
currency: 'USD', // Currency code
};
Appearance Configuration
Customize the look and feel:
const appearance: AppearanceConfig = {
primaryColor: '#10b981', // Brand color
borderRadius: '12px', // Border radius for inputs
fontFamily: 'Inter, system-ui, sans-serif', // Font family
};
React Component Props
BloqueCheckout
Payment Flow
Here's how the payment flow works:
1. User fills payment form in React component
↓
2. Component calls onSubmit with payment data
↓
3. Your frontend sends data to your backend API
↓
4. Your backend processes payment using Bloque SDK
↓
5. Bloque API processes the payment
↓
6. Response flows back to frontend
↓
7. onSuccess or onError callback is triggered
Error Handling
Always implement proper error handling:
<BloqueCheckout
config={config}
onSubmit={async (payload) => {
try {
const response = await fetch('/api/payments', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(payload),
});
if (!response.ok) {
const error = await response.json();
throw new Error(error.message || 'Payment failed');
}
return response.json();
} catch (error) {
console.error('Payment error:', error);
throw error;
}
}}
onSuccess={(response) => {
// Handle success
console.log('Payment successful:', response.id);
window.location.href = `/success?payment=${response.id}`;
}}
onError={(error) => {
// Handle error
console.error('Payment failed:', error);
alert(`Payment failed: ${error.message}`);
}}
/>
Backend Error Handling
app.post('/api/payments', async (req, res) => {
try {
const payload = req.body;
const payment = await bloque.payments.create({
payment: payload,
});
res.json(payment);
} catch (error) {
console.error('Payment processing error:', error);
// Send appropriate error response
const statusCode = error.status || 500;
res.status(statusCode).json({
success: false,
error: error.message,
code: error.code,
});
}
});
TypeScript Support
The SDK is fully typed with TypeScript. Import types for better development experience:
import type {
BloqueCheckoutProps,
CheckoutConfig,
AppearanceConfig,
PaymentResponse,
PaymentSubmitPayload,
PaymentMethodType,
} from '@bloque/payments-react';
// Type-safe configuration
const config: CheckoutConfig = {
payment_methods: ['card', 'pse'],
amount: 2999,
currency: 'USD',
};
// Type-safe event handlers
const handleSuccess = (response: PaymentResponse) => {
console.log('Payment ID:', response.id);
console.log('Status:', response.status);
};
Discriminated Union Types
The PaymentSubmitPayload uses discriminated unions for type safety:
import type { PaymentSubmitPayload } from '@bloque/payments-react';
const handleSubmit = async (payload: PaymentSubmitPayload) => {
// TypeScript automatically narrows the type
switch (payload.type) {
case 'card':
// payload.data is CardPaymentFormData
console.log('Card ending in:', payload.data.cardNumber.slice(-4));
break;
case 'pse':
// payload.data is PSEPaymentFormData
console.log('Bank code:', payload.data.bankCode);
break;
case 'cash':
// payload.data is CashPaymentFormData
console.log('Customer:', payload.data.fullName);
break;
}
// Send to backend...
};
Testing in Sandbox Mode
Use sandbox mode for testing without real transactions:
// Backend
const bloque = new Bloque({
apiKey: process.env.BLOQUE_API_KEY!,
mode: 'sandbox', // Test mode
});
Test Card Numbers
Use these test card numbers in sandbox mode:
Next Steps
Now that you have basic integration working, explore more features:
Examples
Check out complete examples:
Need Help?