mediumCWE-770A04:2021

GraphQL Batching Attack

GraphQL endpoints accepting arrays of operations without size limits, enabling attackers to bypass rate limiting by bundling thousands of requests into a single HTTP call.

How It Works

GraphQL supports batching — sending an array of operations in one HTTP request. Batching is meant for performance, but without size limits, attackers batch thousands of login attempts or resource requests into one HTTP call. Your rate limiter sees one request and lets it through, but the server executes thousands of operations.

Vulnerable Code
// BAD: batching with no size limit
// Attacker sends: [{query: 'mutation login(email:"a"...)'}, {query: ...}, ...x1000]
app.post('/graphql', graphqlHTTP({ schema }));
// Rate limiter sees 1 request, but server runs 1000 mutations
Secure Code
// GOOD: limit batch size
app.post('/graphql', (req, res, next) => {
  const body = req.body;
  if (Array.isArray(body) && body.length > 10) {
    return res.status(400).json({ error: 'Batch size limit exceeded' });
  }
  return graphqlHTTP({ schema })(req, res, next);
});

Real-World Example

GraphQL batching was used to bypass SMS OTP rate limiting on several major platforms — attackers could try hundreds of OTP codes in a single batched request. HackerOne has documented multiple bounty payouts for this issue.

How to Prevent It

  • Limit batch size to a small number (5-10 operations per request)
  • Consider disabling batching entirely if your clients don't use it
  • Apply rate limiting per operation within a batch, not per HTTP request
  • Use a GraphQL server that supports operation-level rate limiting (Apollo Router, GraphQL Armor)

Affected Technologies

nodejsNext.js

Data Hogo detects this vulnerability automatically.

Scan Your Repo Free

Related Vulnerabilities