HIGH cors wildcardexpressdynamodb

Cors Wildcard in Express with Dynamodb

Cors Wildcard in Express with Dynamodb — how this specific combination creates or exposes the vulnerability

Using a CORS wildcard (Access-Control-Allow-Origin: *) in an Express application that interacts with DynamoDB can unintentionally expose sensitive data and amplify authorization issues. When the wildcard is set at the Express/CORS layer, browsers allow any origin to read responses from your endpoints. If those endpoints return DynamoDB data without enforcing per-request authorization, any webpage on the internet can make authenticated requests on behalf of a user (BOLA/IDOR) and harvest data that should be restricted.

Consider an Express route that queries DynamoDB based on a path parameter such as userId:

app.get('/users/:userId', async (req, res) => {
  const { userId } = req.params;
  const params = {
    TableName: 'users',
    Key: { userId },
  };
  const data = await docClient.get(params).promise();
  res.json(data.Item);
});

If the route is protected only by a CORS wildcard and not by proper ownership checks, a malicious site can load this endpoint for any userId and read other users' records. This becomes a data exposure vector when combined with DynamoDB’s behavior: successful GetItem responses return the item if the key exists, even if the requester should not have access to that specific partition key. The wildcard does not cause the authorization flaw, but it removes the browser-enforced same-origin policy that would otherwise limit which origins can observe leaked data.

The risk is especially relevant when the API exposes sensitive attributes (email, PII, tokens) and when preflight requests are handled permissively. An attacker can chain CORS wildcard misconfiguration with DynamoDB queries that lack attribute-level or row-level authorization, leading to mass data extraction. This pattern is commonly flagged as a high-severity finding in scans because it maps directly to OWASP API Top 10:2023 — Broken Object Level Authorization (BOLA) and Data Exposure.

In a middleBrick scan, such a setup typically results in a high severity finding under BOLA/IDOR and Data Exposure categories, with remediation guidance focused on replacing the wildcard with specific origins and enforcing ownership checks on every DynamoDB request.

Dynamodb-Specific Remediation in Express — concrete code fixes

To remediate, enforce strict CORS origins and implement per-request authorization that validates the authenticated subject against the DynamoDB partition key. Below is a secure Express pattern that combines proper CORS configuration with DynamoDB access control.

1) Configure CORS to specify origins instead of using a wildcard. For production, avoid * and enumerate allowed origins:

const cors = require('cors');
const allowedOrigins = ['https://app.example.com', 'https://admin.example.com'];
app.use(cors({
  origin: (origin, callback) => {
    if (!origin || allowedOrigins.includes(origin)) {
      callback(null, true);
    } else {
      callback(new Error('Not allowed by CORS'));
    }
  },
  credentials: true,
}));

2) Enforce ownership checks in your route handler. Retrieve the authenticated user’s ID (e.g., from a session or JWT) and ensure it matches the DynamoDB partition key:

app.get('/users/:userId', async (req, res) => {
  const requestingUserId = req.user.sub; // from auth middleware
  const targetUserId = req.params.userId;

  if (requestingUserId !== targetUserId) {
    return res.status(403).json({ error: 'Forbidden: cannot access other user data' });
  }

  const params = {
    TableName: 'users',
    Key: { userId: targetUserId },
    // Project only necessary attributes to minimize exposure
    ProjectionExpression: 'userId,email,role',
  };

  try {
    const data = await docClient.get(params).promise();
    if (!data.Item) {
      return res.status(404).json({ error: 'Not found' });
    }
    res.json(data.Item);
  } catch (err) {
    res.status(500).json({ error: 'Internal server error' });
  }
});

3) Apply a DynamoDB condition expression when updates are allowed, ensuring the item’s partition key matches the subject. This prevents BOLA even if a higher-level check is bypassed:

app.put('/users/:userId', async (req, res) => {
  const requestingUserId = req.user.sub;
  const targetUserId = req.params.userId;

  const updateParams = {
    TableName: 'users',
    Key: { userId: targetUserId },
    UpdateExpression: 'set email = :email',
    ConditionExpression: 'userId = :uid',
    ExpressionAttributeValues: {
      ':email': req.body.email,
      ':uid': targetUserId,
    },
    ReturnValues: 'UPDATED_NEW',
  };

  try {
    await docClient.update(updateParams).promise();
    res.json({ message: 'updated' });
  } catch (err) {
    if (err.code === 'ConditionalCheckFailedException') {
      return res.status(403).json({ error: 'Cannot update this resource' });
    }
    res.status(500).json({ error: 'Internal server error' });
  }
});

These steps ensure that CORS does not widen the attack surface and that DynamoDB operations remain constrained to the authenticated user’s data. middleBrick will flag the wildcard CORS configuration and missing ownership checks separately, enabling you to address each control with clearly separated remediation actions.

Related CWEs: dataExposure

CWE IDNameSeverity
CWE-200Exposure of Sensitive Information HIGH
CWE-209Error Information Disclosure MEDIUM
CWE-213Exposure of Sensitive Information Due to Incompatible Policies HIGH
CWE-215Insertion of Sensitive Information Into Debugging Code MEDIUM
CWE-312Cleartext Storage of Sensitive Information HIGH
CWE-359Exposure of Private Personal Information (PII) HIGH
CWE-522Insufficiently Protected Credentials CRITICAL
CWE-532Insertion of Sensitive Information into Log File MEDIUM
CWE-538Insertion of Sensitive Information into Externally-Accessible File HIGH
CWE-540Inclusion of Sensitive Information in Source Code HIGH

Frequently Asked Questions

Does a CORS wildcard alone cause data exposure from DynamoDB?
No. The wildcard only relaxes browser enforcement; the underlying exposure occurs when endpoints return sensitive DynamoDB data without per-request authorization. Fix both CORS and authorization.
How does middleBrick assess this risk?
middleBrick checks for a permissive CORS configuration and tests BOLA by probing endpoints with different identifiers, reporting findings under BOLA/IDOR and Data Exposure with remediation steps.