Core infrastructure: - Uber fx dependency injection - Chi router with middleware stack - SQLite database with embedded migrations - Embedded templates and static assets - Structured logging with slog Features implemented: - Authentication (login, logout, session management, argon2id hashing) - App management (create, edit, delete, list) - Deployment pipeline (clone, build, deploy, health check) - Webhook processing for Gitea - Notifications (ntfy, Slack) - Environment variables, labels, volumes per app - SSH key generation for deploy keys Server startup: - Server.Run() starts HTTP server on configured port - Server.Shutdown() for graceful shutdown - SetupRoutes() wires all handlers with chi router
9.4 KiB
9.4 KiB
UPAAS Implementation Plan
Feature Roadmap
Core Infrastructure
- Uber fx dependency injection
- Chi router integration
- Structured logging (slog) with TTY detection
- Configuration via Viper (env vars, config files)
- SQLite database with embedded migrations
- Embedded templates (html/template)
- Embedded static assets (Tailwind CSS, JS)
- Server startup (
Server.Run()) - Graceful shutdown (
Server.Shutdown()) - Route wiring (
SetupRoutes())
Authentication & Authorization
- Single admin user model
- Argon2id password hashing
- Initial setup flow (create admin on first run)
- Cookie-based session management (gorilla/sessions)
- Session middleware for protected routes
- Login/logout handlers
- API token authentication (for JSON API)
App Management
- Create apps with name, repo URL, branch, Dockerfile path
- Edit app configuration
- Delete apps (cascades to related entities)
- List all apps on dashboard
- View app details
- Per-app SSH keypair generation (Ed25519)
- Per-app webhook secret (UUID)
Container Configuration
- Environment variables (add, delete per app)
- Docker labels (add, delete per app)
- Volume mounts (add, delete per app, with read-only option)
- Docker network configuration per app
- Edit existing environment variables
- Edit existing labels
- Edit existing volume mounts
- CPU/memory resource limits
Deployment Pipeline
- Manual deploy trigger from UI
- Repository cloning via Docker git container
- SSH key authentication for private repos
- Docker image building with configurable Dockerfile
- Container creation with env vars, labels, volumes
- Old container removal before new deployment
- Deployment status tracking (building, deploying, success, failed)
- Deployment logs storage
- View deployment history per app
- Container logs viewing
- Deployment rollback to previous image
- Deployment cancellation
Manual Container Controls
- Restart container
- Stop container
- Start stopped container
Webhook Integration
- Gitea webhook endpoint (
/webhook/:secret) - Push event parsing
- Branch extraction from refs
- Branch matching (only deploy configured branch)
- Webhook event audit log
- Automatic deployment on matching webhook
- Webhook event history UI
- GitHub webhook support
- GitLab webhook support
Health Monitoring
- Health check endpoint (
/health) - Application uptime tracking
- Docker container health status checking
- Post-deployment health verification (60s delay)
- Custom health check commands per app
Notifications
- ntfy integration (HTTP POST)
- Slack-compatible webhook integration
- Build start/success/failure notifications
- Deploy success/failure notifications
- Priority mapping for notification urgency
Observability
- Request logging middleware
- Request ID generation
- Sentry error reporting (optional)
- Prometheus metrics endpoint (optional, with basic auth)
- Structured logging for all operations
- Deployment count/duration metrics
- Container health status metrics
- Webhook event metrics
- Audit log table for user actions
API
- JSON API (
/api/v1/*) - List apps endpoint
- Get app details endpoint
- Create app endpoint
- Delete app endpoint
- Trigger deploy endpoint
- List deployments endpoint
- API documentation
UI Features
- Server-rendered HTML templates
- Dashboard with app list
- App creation form
- App detail view with all configurations
- App edit form
- Deployment history page
- Login page
- Setup page
- Container logs page
- Webhook event history page
- Settings page (webhook secret, SSH public key)
- Real-time deployment log streaming (WebSocket/SSE)
Future Considerations
- Multi-user support with roles
- Private Docker registry authentication
- Scheduled deployments
- Backup/restore of app configurations
Phase 1: Critical (Application Cannot Start)
1.1 Server Startup Infrastructure
- Implement
Server.Run()ininternal/server/server.go- Start HTTP server with configured address/port
- Handle TLS if configured
- Block until shutdown signal received
- Implement
Server.Shutdown()ininternal/server/server.go- Graceful shutdown with context timeout
- Close database connections
- Stop running containers gracefully (optional)
- Implement
SetupRoutes()ininternal/server/routes.go- Wire up chi router with all handlers
- Apply middleware (logging, auth, CORS, metrics)
- Define public vs protected route groups
- Serve static assets and templates
1.2 Route Configuration
Public Routes:
GET /health
GET /setup, POST /setup
GET /login, POST /login
POST /webhook/:secret
Protected Routes (require auth):
GET /logout
GET /dashboard
GET /apps/new, POST /apps
GET /apps/:id, POST /apps/:id, DELETE /apps/:id
GET /apps/:id/edit, POST /apps/:id/edit
GET /apps/:id/deployments
GET /apps/:id/logs
POST /apps/:id/env-vars, DELETE /apps/:id/env-vars/:id
POST /apps/:id/labels, DELETE /apps/:id/labels/:id
POST /apps/:id/volumes, DELETE /apps/:id/volumes/:id
POST /apps/:id/deploy
Phase 2: High Priority (Core Functionality Gaps)
2.1 Container Logs
- Implement
HandleAppLogs()ininternal/handlers/app.go- Fetch logs via Docker API (
ContainerLogs) - Support tail parameter (last N lines)
- Stream logs with SSE or chunked response
- Fetch logs via Docker API (
- Add Docker client method
GetContainerLogs(containerID, tail int) (io.Reader, error)
2.2 Manual Container Controls
- Add
POST /apps/:id/restartendpoint- Stop and start container
- Record restart in deployment log
- Add
POST /apps/:id/stopendpoint- Stop container without deleting
- Update app status
- Add
POST /apps/:id/startendpoint- Start stopped container
- Run health check
Phase 3: Medium Priority (UX Improvements)
3.1 Edit Operations for Related Entities
- Add
PUT /apps/:id/env-vars/:idendpoint- Update existing environment variable value
- Trigger container restart with new env
- Add
PUT /apps/:id/labels/:idendpoint- Update existing Docker label
- Add
PUT /apps/:id/volumes/:idendpoint- Update volume mount paths
- Validate paths before saving
3.2 Deployment Rollback
- Add
previous_image_idcolumn to apps table- Store last successful image ID before new deploy
- Add
POST /apps/:id/rollbackendpoint- Stop current container
- Start container with previous image
- Create deployment record for rollback
- Update deploy service to save previous image before building new one
3.3 Deployment Cancellation
- Add cancellation context to deploy service
- Add
POST /apps/:id/deployments/:id/cancelendpoint - Handle cleanup of partial builds/containers
Phase 4: Lower Priority (Nice to Have)
4.1 JSON API
- Add
/api/v1route group with JSON responses - Implement API endpoints mirroring web routes:
GET /api/v1/apps- list appsPOST /api/v1/apps- create appGET /api/v1/apps/:id- get app detailsDELETE /api/v1/apps/:id- delete appPOST /api/v1/apps/:id/deploy- trigger deployGET /api/v1/apps/:id/deployments- list deployments
- Add API token authentication (separate from session auth)
- Document API in README
4.2 Resource Limits
- Add
cpu_limitandmemory_limitcolumns to apps table - Add fields to app edit form
- Pass limits to Docker container create
4.3 UI Improvements
- Add webhook event history page
- Show received webhooks per app
- Display match/no-match status
- Add settings page
- View/regenerate webhook secret
- View SSH public key
- Add real-time deployment log streaming
- WebSocket or SSE for live build output
4.4 Observability
- Add structured logging for all operations
- Add Prometheus metrics for:
- Deployment count/duration
- Container health status
- Webhook events received
- Add audit log table for user actions
Phase 5: Future Considerations
- Multi-user support with roles
- Private Docker registry authentication
- Custom health check commands per app
- Scheduled deployments
- Backup/restore of app configurations
- GitHub/GitLab webhook support (in addition to Gitea)
Implementation Notes
Server.Run() Example
func (s *Server) Run() error {
s.SetupRoutes()
srv := &http.Server{
Addr: s.config.ListenAddr,
Handler: s.router,
}
go func() {
<-s.shutdownCh
ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second)
defer cancel()
srv.Shutdown(ctx)
}()
return srv.ListenAndServe()
}
SetupRoutes() Structure
func (s *Server) SetupRoutes() {
r := chi.NewRouter()
// Global middleware
r.Use(s.middleware.RequestID)
r.Use(s.middleware.Logger)
r.Use(s.middleware.Recoverer)
// Public routes
r.Get("/health", s.handlers.HandleHealthCheck())
r.Get("/login", s.handlers.HandleLoginPage())
// ...
// Protected routes
r.Group(func(r chi.Router) {
r.Use(s.middleware.SessionAuth)
r.Get("/dashboard", s.handlers.HandleDashboard())
// ...
})
s.router = r
}