# Tratamento de erros
Erros de pagamento, estados de loading e popups bloqueados.
## Erros no createOrder
Se o seu backend falhar a criar a ordem, **lance** dentro do `createOrder()`. A SDK
encaminha para `onError` e o popup não avança.
```js
async createOrder() {
const r = await fetch('/api/facipay/create-order', { method: 'POST' });
if (!r.ok) {
const { error } = await r.json().catch(() => ({}));
throw new Error(error || 'Falha ao criar ordem');
}
const { referenceNumber } = await r.json();
if (!referenceNumber) throw new Error('referenceNumber vazio');
return referenceNumber;
}
```
Se o `createOrder()` devolver uma string vazia, o popup fecha-se sem erro visível.
Valide sempre que o `referenceNumber` é uma **string não-vazia**.
## onError
```js
async onError(error) {
console.error('FaciPay error:', error.code, error.message);
showToast('Ocorreu um erro durante o pagamento. Tente novamente.', 'error');
}
```
## Estados de loading
Desative o botão enquanto valida dados e reative quando estiver pronto.
```js
facipay.generateButton({
async onInit(actions) {
if (!cartIsValid()) actions.disable();
},
async onClick(data, actions) {
const customer = validateCustomerForm();
if (!customer) {
actions.reject(); // interrompe o fluxo deste clique (o popup não abre)
return;
}
facipay.button.addCustomerInfo(customer);
},
});
```
## Popups bloqueados
Os browsers podem bloquear o popup se ele não nascer de um gesto direto do utilizador.
- Abra o popup como reação **direta** ao clique (a SDK já o faz no handler do botão).
- Avise o utilizador para **permitir popups** do seu site.
- Evite `await` longos antes de abrir o popup no caminho do clique.
## Chave inválida
Se `apiKeyStatus` ficar `invalid`, o `render()` mostra uma mensagem de erro em vez do botão.
Confirme que a chave corresponde ao ambiente (sandbox vs produção) e que não está vazia.
```js
const facipay = FaciPay(PUBLISHABLE_KEY);
// Verifique no console se aparece "API Key status: invalid"
```