Explica os 10 riscos de segurança mais críticos específicos das APIs e como reduzi-los.
Uma classificação de riscos de segurança específicos de API publicada pela OWASP (Open Worldwide Application Security Project). A edição de 2023 fornece a lista mais recente que reflete as ameaças que aumentaram com a adoção generalizada de APIs.
Uma vulnerabilidade que permite o acesso não autorizado aos dados de outros usuários por meio da manipulação de IDs de objetos. É conhecida como a vulnerabilidade que ocorre com mais frequência e é mais fácil de ser explorada.
Os invasores podem acessar informações pessoais de outros usuários, detalhes de pagamento, histórico de pedidos e muito mais simplesmente alterando o ID no URL ou nos parâmetros de solicitação.
// Recebe ID e retorna dados diretamente - sem verificação de autorização app.get('/api/users/:id/orders', async (req, res) => { const orders = await Order.find({ userId: req.params.id }); res.json(orders); });
// Verificar com base no ID do usuário autenticado para verificação de autorização app.get('/api/users/:id/orders', authenticate, async (req, res) => { if (req.user.id !== req.params.id && !req.user.isAdmin) { return res.status(403).json({ error: 'Forbidden' }); } const orders = await Order.find({ userId: req.params.id }); res.json(orders); });
Uma vulnerabilidade que permite que os invasores assumam o controle de contas de usuário legítimas devido a implementações falhas do mecanismo de autenticação.
Políticas de senha fracas, gerenciamento inadequado de tokens, falta de proteção contra força bruta, gerenciamento inadequado de sessões e muito mais.
const jwt = require('jsonwebtoken'); function authenticate(req, res, next) { const token = req.headers.authorization?.split(' ')[1]; if (!token) return res.status(401).json({ error: 'Token required' }); try { // Especificar explicitamente o algoritmo (evita o ataque alg: none) const decoded = jwt.verify(token, process.env.JWT_SECRET, { algorithms: ['HS256'], issuer: 'your-app', }); req.user = decoded; next(); } catch (err) { res.status(401).json({ error: 'Invalid token' }); } }
Uma vulnerabilidade em que o controle de acesso às propriedades (campos) dos objetos incluídos nas respostas da API é insuficiente. Este item combina Exposição excessiva de dados e Atribuição em massa.
// Retornar apenas os campos públicos do objeto do usuário function sanitizeUser(user, requesterId) { const publicFields = { id: user.id, name: user.name, avatar: user.avatar }; // Somente o proprietário pode ver os campos adicionais if (requesterId === user.id) { publicFields.email = user.email; publicFields.phone = user.phone; } return publicFields; // ❌ return user; vazaria password_hash etc. }
Uma vulnerabilidade em que não há limites para o tamanho, a frequência ou o consumo de recursos das solicitações de API, o que leva a ataques de DoS ou picos de custo.
const rateLimit = require('express-rate-limit'); // Limitação de taxa global app.use(rateLimit({ windowMs: 15 * 60 * 1000, // 15 minutos max: 100, // Máximo de 100 solicitações standardHeaders: true, })); // Limite de tamanho da carga útil app.use(express.json({ limit: '10kb' })); // Limite superior de paginação app.get('/api/items', (req, res) => { const limit = Math.min(parseInt(req.query.limit) || 20, 100); // ... });
Uma vulnerabilidade em que o controle de acesso adequado não é implementado para funções administrativas e endpoints, permitindo que usuários comuns realizem operações administrativas.
function authorize(...roles) { return (req, res, next) => { if (!roles.includes(req.user.role)) { return res.status(403).json({ error: 'Insufficient permissions' }); } next(); }; } // Acesso somente para administradores app.delete('/api/admin/users/:id', authenticate, authorize('admin'), deleteUser); // Administrador e moderador app.put('/api/posts/:id/moderate', authenticate, authorize('admin', 'moderator'), moderatePost);
Uma vulnerabilidade em que os fluxos críticos da lógica comercial não estão protegidos contra ataques automatizados. Exemplos: escalonamento de ingressos, coleta de cupons em massa, postagem de spam, etc.
Uma vulnerabilidade em que o servidor busca uma URL fornecida pelo usuário sem validação, permitindo o acesso não autorizado a redes internas.
const { URL } = require('url'); function isAllowedUrl(input) { try { const url = new URL(input); // Restringir protocolos if (!['https:', 'http:'].includes(url.protocol)) return false; // Bloquear intervalos de IP privados const blocked = ['127.0.0.1', 'localhost', '0.0.0.0', '169.254.169.254']; if (blocked.includes(url.hostname)) return false; // Verifique os intervalos de rede interna (10.x, 172.16-31.x, 192.168.x) if (/^(10\.|172\.(1[6-9]|2\d|3[01])\.|192\.168\.)/.test(url.hostname)) return false; return true; } catch { return false; } }
Configurações de segurança inadequadas em servidores ou estruturas de API. Inclui a permissão de métodos HTTP desnecessários, políticas CORS excessivamente permissivas, exposição de informações de depuração e muito mais.
const helmet = require('helmet'); const cors = require('cors'); app.use(helmet()); app.use(cors({ origin: ['https://app.example.com'], // Não use curingas methods: ['GET', 'POST', 'PUT', 'DELETE'], credentials: true, })); // Manipulador de erros: não retorne traços de pilha na produção app.use((err, req, res, next) => { res.status(500).json({ error: process.env.NODE_ENV === 'production' ? 'Internal Server Error' : err.message, }); });
Um estado em que versões antigas de endpoints de API são deixadas expostas sem a aplicação de patches de segurança. Também conhecido como shadow APIs ou APIs zumbis.
Uma vulnerabilidade em que as respostas de APIs de terceiros são confiáveis sem validação. Se uma API externa for comprometida, o impacto se propagará para o seu próprio sistema.
const Ajv = require('ajv'); const ajv = new Ajv(); // Validação de respostas de API externas com um esquema const externalSchema = { type: 'object', required: ['id', 'status'], properties: { id: { type: 'string', maxLength: 50 }, status: { type: 'string', enum: ['active', 'inactive'] }, }, additionalProperties: false, }; const validate = ajv.compile(externalSchema); async function fetchExternalData() { const res = await fetch('https://api.external.com/data'); const data = await res.json(); if (!validate(data)) { throw new Error('External API response validation failed'); } return data; }
| ID | Vulnerabilidade | Gravidade | Principais medidas de mitigação |
|---|---|---|---|
| API1 | Broken Object Level Authorization | Critical | Verificações de autorização em nível de objeto |
| API2 | Broken Authentication | Critical | Gerenciamento adequado de tokens e proteção contra força bruta |
| API3 | Broken Object Property Level Authorization | High | Filtragem de campo de resposta explícita |
| API4 | Unrestricted Resource Consumption | High | Limitação de taxa e restrições de tamanho de carga útil |
| API5 | Broken Function Level Authorization | High | Controle de acesso baseado em função |
| API6 | Unrestricted Access to Sensitive Business Flows | Medium | CAPTCHA e limitação de taxa em nível comercial |
| API7 | Server Side Request Forgery | High | Validação de URL e bloqueio de IPs privados |
| API8 | Security Misconfiguration | Medium | Cabeçalhos de segurança e configuração de CORS |
| API9 | Improper Inventory Management | Medium | Gerenciamento de inventário de API e políticas de depreciação |
| API10 | Unsafe Consumption of APIs | Medium | Validação de esquema de respostas de API externas |