☁️ CloudHost — Self-Service PaaS Platform
A self-service Platform-as-a-Service (PaaS) that lets developers deploy Node.js and Laravel applications onto Kubernetes with zero DevOps overhead. Super admins manage clusters, quotas, and users; developers simply push code and deploy.
Architecture Overview
| Layer |
Technology |
| Frontend |
Next.js 14, Tailwind CSS, React Query, Zustand |
| Backend API |
NestJS 10, TypeORM, Passport JWT, Bull (Redis) |
| Build Engine |
Kaniko (in-cluster, daemon-less Docker builds) |
| Orchestrator |
@kubernetes/client-node, Handlebars YAML templates |
| Database |
PostgreSQL 16 |
| Queue |
Redis 7 + BullMQ |
Features
For Developers
- 🚀 One-click deploys from a Git URL or uploaded code archive
- 🟢 Node.js (with
npm run build & npm start) support
- 🟣 Laravel (PHP 8.3 + Nginx + Supervisor) support
- 🗄️ Managed databases — PostgreSQL or MySQL provisioned automatically
- 📊 Live logs & deployment history
- 🔒 Environment variables managed as Kubernetes Secrets
- ⚙️ Resource controls — CPU, memory, replica count
For Super Admins
- 🖥️ Multi-cluster management — register/remove Kubernetes clusters
- 👥 User management — activate, deactivate, change roles
- 📈 Quotas — per-cluster limits (CPU, memory, max apps)
- 🔐 RBAC — role-based guards on every endpoint
Project Structure
Quick Start
Prerequisites
| Tool |
Version |
| Node.js |
≥ 20 |
| Docker & Compose |
≥ 24 |
| PostgreSQL |
16 (or use Docker) |
| Redis |
7 (or use Docker) |
1. Clone & Install
2. Environment Variables
3. Run with Docker Compose (recommended)
This spins up PostgreSQL, Redis, Backend (port 4000), and Frontend (port 3000).
Open http://localhost:3000 in your browser.
4. Run Locally (development)
API Endpoints
All endpoints are prefixed with /api/v1.
Auth
| Method |
Path |
Description |
| POST |
/auth/register |
Create account |
| POST |
/auth/login |
Get JWT tokens |
| POST |
/auth/refresh |
Refresh access token |
Applications
| Method |
Path |
Description |
| POST |
/applications |
Create app |
| GET |
/applications |
List user's apps |
| GET |
/applications/:id |
Get app details |
| PATCH |
/applications/:id |
Update app |
| DELETE |
/applications/:id |
Delete app |
Deployments
| Method |
Path |
Description |
| POST |
/applications/:appId/deployments |
Trigger deploy |
| GET |
/applications/:appId/deployments |
List deployments |
| GET |
/deployments/:id |
Deployment detail |
| GET |
/deployments/:id/logs |
Get pod logs |
| POST |
/deployments/:id/stop |
Stop deployment |
| POST |
/deployments/:id/restart |
Restart deployment |
Users (authenticated)
| Method |
Path |
Description |
| GET |
/users/me |
Current user |
| PATCH |
/users/me |
Update profile |
Admin — Users
| Method |
Path |
Description |
| GET |
/users |
List all users |
| PATCH |
/users/:id/activate |
Activate user |
| PATCH |
/users/:id/deactivate |
Deactivate user |
| PATCH |
/users/:id/role |
Change role |
Admin — Clusters
| Method |
Path |
Description |
| POST |
/clusters |
Add cluster |
| GET |
/clusters |
List clusters |
| GET |
/clusters/:id |
Cluster details |
| PATCH |
/clusters/:id |
Update cluster |
| DELETE |
/clusters/:id |
Remove cluster |
📖 Full Swagger docs available at http://localhost:4000/docs when the backend is running.
Deployment Flow
Kubernetes Templates
The platform dynamically generates K8s manifests using Handlebars templates located in backend/templates/:
| Template |
Purpose |
namespace.yaml |
Per-user namespace with resource quotas |
deployment.yaml |
App deployment with health probes & resources |
service.yaml |
ClusterIP service |
ingress.yaml |
Ingress with TLS (cert-manager annotations) |
database.yaml |
PostgreSQL or MySQL StatefulSet |
pvc.yaml |
Persistent volume claim for databases |
secret.yaml |
Environment variables as K8s Secrets |
Security
- JWT access + refresh tokens with configurable expiry
- Bcrypt password hashing (12 rounds)
- Helmet HTTP security headers
- RBAC role-based route guards (
@Roles(UserRole.ADMIN))
- Namespace isolation — each user deploys to their own K8s namespace
- Secrets — env vars stored as K8s Secrets, never in plain manifests
- Input validation —
class-validator on all DTOs
Configuration
All configuration is via environment variables. See backend/.env.example for the full list:
| Variable |
Description |
Default |
PORT |
Backend port |
4000 |
DB_HOST |
PostgreSQL host |
localhost |
DB_PORT |
PostgreSQL port |
5432 |
DB_USERNAME |
Database user |
cloudhost |
DB_PASSWORD |
Database password |
— |
DB_NAME |
Database name |
cloudhost |
JWT_SECRET |
JWT signing secret |
— |
JWT_EXPIRES_IN |
Access token TTL |
15m |
REDIS_HOST |
Redis host |
localhost |
REDIS_PORT |
Redis port |
6379 |
REGISTRY_URL |
Container registry URL |
— |
PLATFORM_DOMAIN |
Base domain for app subdomains |
apps.localhost |
License
MIT