Deploying with Heroku
Classic PaaS with git push deploys, buildpacks, add-ons, and dyno scaling.
PlatformsBeginner
Why
Heroku pioneered git-push deploys with managed add-ons (Postgres, Redis, SendGrid). Its buildpack system auto-detects languages and handles build, release, and runtime.
Platform-as-a-Service adoption grew 24% in 2024 as teams shift from VM management to git-push deploys. the cloud infrastructure market reached $330B in 2024, growing 22% year-over-year (Synergy Research), and PaaS layers capture the majority of new workloads.
When
Use Heroku for rapid prototyping, Ruby/Python/Node apps, and teams wanting simplicity. Note: free tier removed in 2022.
How
1. Create — heroku create myapp
2. Deploy — git push heroku main
3. Buildpack — heroku buildpacks:set heroku/nodejs
4. Procfile — web: npm start, worker: npm run worker
5. Add-ons — heroku addons:create heroku-postgresql:hobby-basic
6. Scale — heroku ps:scale web=2 worker=1
7. Release — heroku run npm run migrate as release phase
Example
# Procfile
web: npm start
worker: npm run worker
release: npm run db:migrate
# app.json — one-click deploy
{
"name": "My App",
"scripts": { "postdeploy": "npm run db:migrate" },
"env": { "SECRET_KEY": { "generator": "secret" } },
"addons": ["heroku-postgresql"]
}
# Deploy
heroku create
git push heroku main
heroku addons:create heroku-postgresql:essential-0
heroku ps:scale worker=1
Common Problems
- ⚠Build fails — wrong buildpack or Node version, set engines in package.json
- ⚠Dyno restarts every 24h — Heroku cycles dynos, use release phase for migrations
- ⚠Configuration drift between environments — use infrastructure-as-code (Terraform/Pulumi) to keep dev/staging/prod identical
Best Practices
- ✓Use release phase in Procfile — runs migrations before dyno starts, atomic deploys
- ✓Set engines in package.json — ensures Heroku uses correct Node/Python version
- ✓Set up health checks and graceful shutdown — handle SIGTERM to drain in-flight requests before exit