π Automating My Portfolio Deployment with GitHub Actions
How I set up a fully automated CI/CD pipeline for my Next.js portfolio without crashing my VPS
Words
725
Read Time
4 min read
Category
DevOps
Recent articles you open here will appear in this quick history.
Automating My Portfolio Deployment with GitHub Actions
Building a Next.js application on a memory-constrained VPS was becoming a nightmare. Every time I wanted to add a blog post or make a small change, the build process would eat up all available RAM and sometimes crash the server. Here's how I solved it with GitHub Actions.
The Problem
My Oracle Cloud (OCI) VPS has limited resources:
- ARM64 Ampere processor
- Shared resources with portfolio and other services
- Multiple services running (Nginx Proxy Manager, Sentry Webhook, etc.)
Next.js builds are memory-hungry, requiring 2-4GB during compilation. Running npm run build would:
- Max out memory
- Trigger OOM (Out of Memory) killer
- Sometimes crash other services
- Take 6+ minutes if it succeeded
The Solution
Instead of building on my VPS, I offloaded the heavy lifting to GitHub's infrastructure:
Architecture Overview
Local Changes β GitHub β GitHub Actions Build β Docker Hub β VPS Deploy
- Make changes on the VPS or locally
- Push to GitHub - triggers the workflow
- GitHub Actions builds the Docker image (on their servers!)
- Push to Docker Hub - stores the built image
- Auto-deploy to VPS - pulls and restarts the container
Implementation Steps
1οΈβ£ Created Build Script with Swap Management
For local builds when needed:
#!/bin/bash
# Temporarily adds 4GB swap, builds, then cleans up
sudo /opt/portfolio/build-with-swap.sh
This prevents VPS crashes during manual builds.
2οΈβ£ Set Up GitHub Actions Workflow
Created .github/workflows/build-and-deploy.yml:
- Builds on GitHub's servers (not my VPS)
- Uses Docker BuildKit with caching
- Pushes image to Docker Hub
- SSHs to VPS and deploys
3οΈβ£ Implemented Secure Deployment
Instead of using root for deployments, created a dedicated deployer user:
sudo /opt/portfolio/create-deploy-user.sh
Security benefits:
- Limited to Docker commands only
- Can't modify system files
- Follows principle of least privilege
- Separate SSH key for automation
4οΈβ£ Configured Docker Hub
Made the Docker image private while keeping the GitHub repo public:
- Recruiters can see my code on GitHub
- Random users can't pull my Docker image
- Best of both worlds!
The New Workflow
Adding a blog post is now simple:
cd /opt/portfolio
nano content/blog/my-new-post.mdx
git add .
git commit -m "Add blog post about automation"
git push
Then:
- Wait 5-10 minutes
- β Grab coffee
- Site auto-updates!
No more:
- Manual builds
- Memory issues
- Server crashes
- Babysitting deployments
Results
Before:
- Build time: 6+ minutes (if successful)
- Success rate: ~70%
- Manual intervention: Required
- Stress level: High π°
After:
- Build time: 5-10 minutes
- Success rate: 100%
- Manual intervention: None
- Stress level: Zero π
Lessons Learned
- Offload heavy tasks: Don't build on resource-constrained servers
- Automate everything: One push, automatic deployment
- Security matters: Use dedicated users for automation
- Free tier is powerful: GitHub Actions + Docker Hub = $0/month
- Visibility vs Privacy: Keep code public, build artifacts private
Technical Stack
- CI/CD: GitHub Actions
- Container Registry: Docker Hub (private image)
- Deployment: SSH-based auto-deploy
- Build Environment: Node.js 18, Docker BuildKit
- Memory Management: Temporary swap for local builds
Future Improvements
Potential enhancements I'm considering:
- [ ] Add automated tests before deployment
- [ ] Implement blue-green deployments
- [ ] Add deployment notifications via Telegram
- [ ] Set up preview deployments for PRs
- [ ] Add performance monitoring
Final Thoughts
This setup has been a game-changer for my development workflow. I can now focus on creating content and improving features without worrying about infrastructure limitations.
The best part? Everything runs on free tiers:
- GitHub Actions: Unlimited for public repos
- Docker Hub: 1 free private repository
- No ongoing costs!
If you're running a portfolio or blog on a budget VPS, I highly recommend this approach. Your server will thank you! π
Questions? Feel free to check out my portfolio repository to see the complete setup!
Auto-deployed via GitHub Actions
Follow This Topic
Keep exploring through related builds and skill areas connected to this post.
Related Projects