You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Node.js/Express并发大请求报错:BadRequestError: request aborted 求助

Fixing BadRequestError: request aborted in Node.js/Express for Large Base64 Uploads

Looking at your error logs and app.ts code, this error pops up when handling concurrent large Base64 image uploads because the request gets interrupted before the server can fully receive or process it. Let's break down the likely causes and how to fix them:

Likely Causes

  1. Request Body Parsing Timeout: The express.json() middleware relies on the raw-body library, which has a default timeout of 10 seconds. Your 7-8MB images turn into ~9-10MB Base64 payloads—if network speeds are slow or the server is under load, transferring this data can take longer than 10 seconds, triggering the abort.
  2. Client-Side Timeout: Your load testing tool might have a too-short timeout setting. If the server takes longer than this threshold to process or receive the request, the client will drop the connection early.
  3. Server Resource Bottlenecks: Concurrent large requests can spike CPU/memory usage, blocking the Node.js event loop. This delays the server's ability to receive the full request body, leading to an abort.
  4. Reverse Proxy Limits: If you're using a reverse proxy like Nginx in front of your API, settings like client_max_body_size (restricting payload size) or proxy_read_timeout (proxy timeout) might be cutting off requests.

Solutions

1. Adjust Request Parsing Timeout & Limits

Update your express.json() configuration to extend the timeout and confirm the size limit is sufficient (your 16MB limit is okay, but explicit timeout helps):

this.app.use(express.json({
  limit: "16mb",
  timeout: 30000 // 30 seconds—tweak based on your network and processing speed
}));

Keep your express.urlencoded() config as-is since your requests are application/json, but it's good to have it covered for other scenarios.

2. Set HTTP Server Timeout

Node.js' HTTP server doesn't have a default timeout, but explicitly setting one prevents hanging connections. Add this when starting your server:

import * as http from 'http';

// After creating your App instance
const appInstance = new App();
const server = http.createServer(appInstance.app);
server.timeout = 60000; // 60 seconds—give enough time for large uploads
server.listen(process.env.PORT || 3000);

3. Optimize Large Request Handling

Base64 adds 33% overhead and uses more memory. To improve performance:

  • Switch to binary uploads: Use multipart/form-data instead of Base64, and use a streaming middleware like multer to process files without loading them entirely into memory.
  • Stream Base64 processing: If you must use Base64, decode and process the data in chunks immediately instead of holding the full string in memory.

4. Tune Load Testing Tool Settings

Make sure your load tester's timeout is longer than your server's timeout. For example, in Artillery, add this to your config:

config:
  timeout: 60 # 60 seconds

This prevents the client from dropping connections before the server can finish processing.

5. Monitor Server Resources

While load testing, keep an eye on CPU, memory, and network usage:

  • Use top or htop for CPU/memory monitoring
  • Use iftop for network bandwidth tracking
    If resources are maxed out, upgrade your server or optimize your API's processing logic (e.g., offload image processing to a background service).

6. Check Reverse Proxy Config (If Applicable)

If using Nginx, update these settings in your server block:

client_max_body_size 16m; # Match your Express limit
proxy_read_timeout 60s;    # Extend proxy timeout
proxy_send_timeout 60s;

7. Improve Error Handling

Add an Express error-handling middleware to catch these abort errors and return meaningful responses:

private errors(): void {
    process.on("unhandledRejection", (ex) => {
        throw ex;
    });
    // Add error handling middleware
    this.app.use((err: any, req: express.Request, res: express.Response, next: express.NextFunction) => {
        if (err.name === 'BadRequestError' && err.message === 'request aborted') {
            this.log.warn(`Request aborted (ID: ${req.log_id})`, err);
            return res.status(400).json({
                error: 'Request was interrupted mid-transmission. Check network stability or increase timeout settings.'
            });
        }
        // Handle other errors
        this.log.error('Unhandled server error:', err);
        res.status(500).json({ error: 'Internal server error' });
    });
}

Final Notes

Start with adjusting the request parsing timeout and server timeout—these are the most common fixes for this scenario. Switching to binary uploads will also significantly reduce resource strain and improve concurrency.

内容的提问来源于stack exchange,提问作者Kay

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.14 07:26:20