Vercel: 504 timeout on serverless functions [2026 fix]
Serverless functions exceed 10-second execution limit or cold start delays. Optimize function logic, increase timeout via vercel.json, or split into smaller functions.
TL;DR
Cause: Your serverless function exceeded Vercel's 10-second timeout limit or is experiencing cold start delays from heavy dependencies.
Fix: Reduce function execution time, set maxDuration in vercel.json (up to 60 seconds on Pro), or split heavy work into async background jobs.
---
Real Console Error Messages
Here are exact error patterns you'll see:
``` 504: GATEWAY_TIMEOUT The request took too long to complete. This indicates that a function took longer than the maximum duration and was terminated. ```
``` Error: Task timed out after 10 seconds. Attempt to call a function that took too long. ERR_FUNCTION_TIMEOUT ```
``` Fetch error: The function did not complete before the timeout of 10 seconds status: 504 ```
``` Error: connect ETIMEDOUT 127.0.0.1:3000 (Usually means cold start + slow initialization) ```
``` WARNING: Function took 12453ms to complete. This exceeds the 10000ms timeout for your plan. ```
---
Broken Code → Fixed Code
Problem 1: Database Query Without Timeout
BROKEN: ```javascript // api/fetch-users.js export default async function handler(req, res) { const db = require('pg'); const client = new db.Client(process.env.DATABASE_URL); await client.connect(); // No timeout set const result = await client.query('SELECT * FROM users'); // Slow query hangs await client.end(); return res.json(result.rows); } ```
FIXED: ```javascript // api/fetch-users.js export default async function handler(req, res) { const db = require('pg'); const client = new db.Client({ connectionString: process.env.DATABASE_URL, connectionTimeoutMillis: 5000, // 5 second timeout query_timeout: 8000, // 8 second query timeout }); try { await client.connect(); const result = await client.query('SELECT * FROM users LIMIT 100'); // Add LIMIT await client.end(); return res.json(result.rows); } catch (error) { await client.end(); return res.status(500).json({ error: 'Database timeout' }); } } ```
Problem 2: Heavy Synchronous Processing
BROKEN: ```javascript // api/process-image.js export default async function handler(req, res) { const sharp = require('sharp'); const image = req.body.imageData; // Synchronous image processing blocks everything const processed = await sharp(image) .resize(1920, 1080) .rotate(45) .blur(15) .greyscale() .normalize() .toBuffer(); // Can take 15+ seconds res.json({ success: true }); } ```
FIXED: ```javascript // api/process-image.js import { Queue } from '@vercel/functions';
export default async function handler(req, res) { const jobId = crypto.randomUUID(); // Queue async job instead of blocking await fetch(process.env.BACKGROUND_JOB_URL, { method: 'POST', body: JSON.stringify({ jobId, imageData: req.body.imageData }) }); // Return immediately res.json({ jobId, status: 'processing' }); }
// crons/process-images.js - separate long-running function export default async function handler(req, res) { const sharp = require('sharp'); const { imageData } = req.body; const processed = await sharp(imageData) .resize(1920, 1080) .rotate(45) .blur(15) .greyscale() .normalize() .toBuffer(); res.json({ success: true }); } ```
Problem 3: Missing vercel.json Timeout Config
BROKEN: ```json // vercel.json (no timeout set) { "buildCommand": "npm run build" } ```
FIXED: ```json // vercel.json { "buildCommand": "npm run build", "functions": { "api/**/*.js": { "maxDuration": 30, "memory": 1024 }, "api/heavy-processing.js": { "maxDuration": 60, "memory": 3008 } } } ```
Important caveat: I'm uncertain whether all plan tiers support maxDuration beyond 10 seconds in 2026—verify your Vercel plan. Pro and Enterprise typically allow 30-60 seconds. Hobby tier is locked to 10 seconds.
---
Still Broken? Check These Too
1. [Cold Start Delays](/?guide=vercel-cold-starts) - First request after deployment takes 3-5 seconds. Minimize dependencies, use @vercel/node utilities, avoid heavy imports at module level.
2. [Database Connection Pooling](/?guide=postgres-connection-limits) - Creating new DB connection per request exhausts connection limits. Use pg-boss or connection pooling middleware (PgBouncer on backend).
3. External API Timeouts - If your function calls third-party APIs, they might be slow. Implement timeout wrappers: Promise.race([apiCall(), timeout(5000)]).
---
Next Steps
1. Check current function duration in Vercel dashboard → Function logs
2. Add explicit timeout values to vercel.json
3. Profile code with console.time() to find slow sections
4. Move work to [background jobs or cron functions](https://vercel.com/docs/crons)
Official Reference: [Vercel Serverless Functions Documentation](https://vercel.com/docs/functions)
---
Found a different variation? Drop it in the comments—especially if you hit timeout issues with specific databases, frameworks, or 2026+ Vercel pricing tiers.