# Documentação técnica — API REST Kombex v1

Documento técnico da API com foco em conexão, autenticação, contratos de requisição e retorno.

---

## 1. Convenções gerais

- **Prefixo de rota:** `/api/v1`
- **Formato:** JSON (`Content-Type: application/json`)
- **Resposta padrão:**

```json
{
  "success": true,
  "data": {},
  "error": null
}
```

- **Códigos comuns:** `200`, `201`, `204`, `400`, `401`, `403`, `404`, `405`, `409`, `422`, `429`, `500`, `503`

---

## 2. Conexão e ambientes (banco de dados)

A seleção do banco é feita por `Config::getPDOForRequest()`, baseada no endpoint acessado.

### 2.1 Hospedagem

- Host contendo `api-desenv` -> ambiente **desenv**
- Host contendo `api-production` -> ambiente **production**

### 2.2 Localhost

- Caminho contendo `kombex-api-desenv` -> **desenv**
- Caminho contendo `kombex-api` -> **production**

### 2.3 Variáveis de controle

- `KOMBEX_DB_SLOT`: força slot (`local_desenv`, `local_production`, `hosted_desenv`, `hosted_production`)
- `KOMBEX_FORCE_HOSTED=1`: força matriz de hospedagem

> Credenciais por ambiente/slot ficam em `config/Config.php`.

---

## 3. Autenticação

### 3.1 Credenciais do cliente

- `api_key` (texto)
- `api_secret` (texto, exibido apenas em criação/reset)
- Banco guarda somente `api_secret_hash` (`password_hash`)

### 3.2 JWT

- Emissão: `POST /api/v1/auth/token`
- Renovação: `POST /api/v1/auth/refresh`
- Algoritmo: HS256 (`JwtService`)

Claims:

- `sub` (id interno clientes_api)
- `cid` (cliente_id lógico)
- `amb` (`desenv`/`production`)
- `typ` (`access`/`refresh`)
- `iss`, `iat`, `exp`

TTL padrão:

- `JWT_ACCESS_TTL` = 3600s
- `JWT_REFRESH_TTL` = 604800s

### 3.3 Headers aceitos para rotas JWT

1. `Authorization: Bearer <token>`
2. `X-Kombex-Authorization: Bearer <token>` (**recomendado** em cPanel/CGI/FastCGI)
3. `X-Access-Token: <token>` (sem `Bearer`)

### 3.4 Segredo interno

Para endpoints administrativos internos:

- `X-Kombex-Internal-Secret: <segredo>`

Validação por:

- `CLIENTES_API_REGISTER_SECRET`, ou
- `INTERNAL_STATUS_SECRET` (fallback)

### 3.5 Rate limit

- `/auth/token`: por IP + api_key (`RATE_LIMIT_AUTH_PER_MINUTE`)
- Rotas JWT: por `clientes_api.id` (`RATE_LIMIT_PER_MINUTE`)

---

## 4. Endpoints

| Método | Caminho | Auth | Descrição |
|--------|---------|------|-----------|
| POST | `/api/v1/auth/token` | — | Emite access + refresh JWT |
| POST | `/api/v1/auth/refresh` | — | Renova access JWT |
| POST | `/api/v1/admin/clientes-api` | `X-Kombex-Internal-Secret` | Cadastra cliente API |
| POST | `/api/v1/admin/clientes-api/reset-secret` | `X-Kombex-Internal-Secret` | Redefine `api_secret` |
| POST | `/api/v1/solicitacoes` | JWT | Cria solicitação |
| GET | `/api/v1/solicitacoes` | JWT | Lista solicitações |
| GET | `/api/v1/solicitacoes/{codigo}` | JWT | Consulta por código |
| PUT | `/api/v1/solicitacoes/{codigo}/status` | `X-Kombex-Internal-Secret` | Atualiza status (interno) |
| DELETE | `/api/v1/solicitacoes/{codigo}` | JWT | Cancela solicitação |
| POST | `/api/v1/webhooks` | JWT | Cadastra webhook |
| GET | `/api/v1/webhooks` | JWT | Lista webhooks |

---

## 5. Contratos por endpoint

### 5.1 POST `/auth/token`

Body:

```json
{ "api_key": "kbx_xxx", "api_secret": "segredo_em_texto" }
```

200 `data`:

- `access_token`, `refresh_token`, `token_type`, `expires_in`, `ambiente`

Erros: `400`, `401`, `403`, `429`

### 5.2 POST `/auth/refresh`

Body:

```json
{ "refresh_token": "<jwt_refresh>" }
```

200 `data`:

- `access_token`, `token_type`, `expires_in`, `ambiente`

Erros: `400`, `401`

### 5.3 POST `/admin/clientes-api`

Body:

```json
{ "cliente_id": "ERP_001", "ambiente": "desenv", "ativo": "Sim" }
```

201 `data`:

- `id`, `cliente_id`, `api_key`, `api_secret`, `ambiente`, `ativo`, `aviso`

Erros: `400`, `401`, `503`, `500`

### 5.4 POST `/admin/clientes-api/reset-secret`

Body (informar **exatamente um**):

```json
{ "id": 10 }
```

ou

```json
{ "cliente_id": "ERP_001" }
```

ou

```json
{ "api_key": "kbx_xxx" }
```

200 `data`:

- `id`, `cliente_id`, `api_key`, `api_secret` (novo), `ambiente`, `ativo`, `aviso`

Regras:

- registro deve estar `ativo = Sim`
- ambiente da linha deve bater com endpoint atual

Erros: `400`, `401`, `404`, `503`, `500`

### 5.5 POST `/solicitacoes`

Campos obrigatórios principais:

- dados de origem/destino (nome, documento, contato, telefone, cep, rua, numero, bairro, cidade, estado)
- `termo_aceite` aceito
- `itens` não vazio

Regra de item:

- obrigatório `quantidade` (ou `qtde`) >= 1
- obrigatório informar **ao menos um** entre:
  - `peso` (`> 0`)
  - `valor_nf` (`> 0`)
  - `dimensoes` (array não vazio)
- se `dimensoes` for enviado, cada dimensão exige:
  - `altura > 0`
  - `largura > 0`
  - `comprimento > 0`

201 `data`:

- `id`, `codigo`, `status`, `valor_frete`, `metro_cubico_total`, `empresas_rota`, `resumo_rota`

Erros: `400`, `401`, `422`, `429`, `500`

### 5.6 GET `/solicitacoes`

Query opcional:

- `status`, `data_inicio`, `data_fim`, `page`, `per_page`

Regras:

- lista somente status `0` ou `1`
- janela máxima de consulta: `SOLICITACOES_LIST_MAX_DIAS` (30 por padrão)

200 `data`:

- `solicitacoes[]`
- `periodo_consulta`
- `pagination`

### 5.7 GET `/solicitacoes/{codigo}`

200 `data`: objeto completo da solicitação (origem, destino, itens, status etc.)  
404 se não existir ou não pertencer ao cliente.

### 5.8 PUT `/solicitacoes/{codigo}/status` (interno)

Body:

```json
{ "status": 2 }
```

200 `data`: solicitação atualizada  
Erros: `401`, `404`, `409`, `500`, `503`

### 5.9 DELETE `/solicitacoes/{codigo}`

200 `data` resumido:

- `mensagem`, `codigo`, `id`, `status`, `data_atualizacao_status`

Erros: `401`, `404`, `409`

### 5.10 POST `/webhooks`

Body:

```json
{ "url": "https://...", "eventos": "status", "secret": "opcional" }
```

201 `data`: `id`, `url`, `eventos`

### 5.11 GET `/webhooks`

200 `data`:

```json
{ "webhooks": [ ... ] }
```

---

## 6. Status da solicitação

| Código | Significado |
|--------|-------------|
| 0 | Solicitado |
| 1 | Em processamento |
| 2 | Em coleta |
| 3 | Em trânsito |
| 4 | Entregue (terminal) |
| 9 | Cancelado (terminal) |

---

## 7. Webhooks (evento de status)

Evento disparado:

- `solicitacao.status`

Assinatura opcional:

- `X-Kombex-Signature: sha256=<hmac>`

Timeout:

- `WEBHOOK_TIMEOUT_SECONDS`

---

## 8. Referências

- `public/index.php` (roteamento)
- `controllers/` (regras de endpoint)
- `models/` (persistência)
- `middlewares/JwtAuthMiddleware.php` (auth headers)
- `services/JwtService.php` (JWT)
- `services/Response.php` (response envelope)
- `config/Config.php` (ambientes e limites)
- `postman/Kombex-API-v1.postman_collection.json`
- `docs/HOSPEDAGEM-AUTHORIZATION.md`

