Introduction
Imagine this: You're deep into developing your Strapi and Next.js v13 application, happily testing your API, when suddenly, the browser smacks you with a 503 Service Unavailable error. Panic starts creeping in. But then you check your API response manually, and—surprise!—your API is still returning data.
What’s going on?
This post takes you through my troubleshooting journey, from confusion to resolution, as I tackled this weird issue while deploying Strapi on an IIS server with a reverse proxy and PM2. Along the way, I’ll share lessons learned and why Nginx might have been a better choice from the start.
The Problem: The 503 Enigma
What I Saw
I deployed my Strapi API on a server running IIS with a reverse proxy. Everything seemed fine at first, but then:
- The browser displayed a "503 Service Unavailable" error.
-
However, direct API calls via Postman or
fetch()
still returned data.
The browser console screamed:
GET http://xx.xx.xx.xx:8000/api/sales 503 (Service Unavailable)
But when I manually checked via Postman:
{
"data": [...],
"meta": {...}
}
The API was clearly still responding. So why was IIS throwing a 503?
The Troubleshooting Journey
1️⃣ Initial Steps: Where to Begin?
I started by checking the usual suspects:
-
Strapi logs (
pm2 logs strapi
) – Nothing unusual. - Reverse proxy logs (IIS logs & Event Viewer) – No clear signs of failure.
-
Restarting the Strapi service (
pm2 restart strapi
) – No effect.
Everything seemed fine… but clearly, something was wrong.
2️⃣ Resource Monitoring: A CPU Clue
Next, I checked server resource usage using PM2 and system tools:
pm2 list
Boom. CPU usage was abnormally high.
Strapi was running, but it was struggling under load, possibly affecting IIS’s ability to serve requests.
3️⃣ IIS and Reverse Proxy Deep Dive
IIS can be tricky, especially with reverse proxy configurations. Here’s what I checked:
✅ Application Pool Settings – Ensured the pool was running.
✅ URL Rewrite Rules – Verified they were forwarding requests correctly.
✅ IIS Logs (C:\inetpub\logs\LogFiles
) – Found a 5002 error!
The key clue was in Windows Event Viewer:
Microsoft-Windows-WAS Error 5002: Application pool for Strapi has been disabled due to repeated failures.
4️⃣ The Culprit: Application Pool Issues
What happened?
🔍 IIS application pool had stopped due to high CPU usage and repeated failures.
🔍 Windows automatically disabled the pool to prevent further issues.
✅ Restarting the application pool manually resolved the 503 error!
iisreset /restart
But… this was only a temporary fix.
5️⃣ IIS vs. Nginx: Considering a Better Solution
While IIS works, Nginx is much better suited for Node.js applications like Strapi. Here’s why:
Feature | IIS | Nginx |
---|---|---|
Performance | Slower for Node.js apps | Faster, optimized for Node.js |
Reverse Proxy | More complex setup | Easier & more efficient |
Stability | Can crash under high load | Handles high traffic better |
Configuration | GUI-based, less flexible | Config files, more control |
👉 In the long run, switching to Nginx could prevent these issues.
The Solution and Lessons Learned
✅ Immediate Fix
- Restarted the IIS application pool manually.
- Lowered Strapi’s resource usage by optimizing queries.
- Used PM2 process limits to prevent overload:
pm2 start strapi --max-memory-restart 200M
Key Takeaways
✔ Check logs early – IIS logs and Event Viewer revealed the real issue.
✔ Monitor resource usage – PM2 helped catch high CPU usage.
✔ Understand your hosting environment – IIS behaves differently from Nginx.
✔ Consider switching to Nginx – A better long-term solution for Node.js apps.
Conclusion
Troubleshooting this issue was frustrating but ultimately rewarding. Understanding how IIS, Strapi, and the reverse proxy interact was crucial in solving it.
If you’re a junior dev running into weird 503 errors, always check your server logs, application pools, and CPU usage.
Have you had a similar experience? Share your story in the comments!
Top comments (0)