Files
dashcaddy/README.md
Hermes b4e09af712 [grade=A urn:ump:swcz3quualvlmdanpqm5v46cr6zkazes7erbftk6rj3jxv6ip4fa] docs(DC-170): changelog rebuild, version sync, API-SURFACE regen (audit batch 7)
Customer-facing professionalism tier (AUDIT-2026-10-27.md findings 34-39):

- CHANGELOG.md rebuilt to Keep-a-Changelog: ONE Unreleased section, the
  2026-08-12 hardening sprint folded into 1.17.0 (no v1.16.0 tag exists,
  verified via git tag -l), ALL 7 judge-grade/URN lines moved out of
  customer copy into RELEASE-EVIDENCE-internal.md, missing DC-166/169
  entries added, full DC-170 sweep entry written, DC-171 DNS-parity
  ticket recorded, date order strictly descending across all 22
  sections (1.1.5 restored with its true content after the re-sort ate
  the heading), compare-link chain filled (Unreleased from v1.17.0,
  1.17.0 from v1.14.6-patched, 18 missing version links added)
- VERSION 1.15.0 -> 1.17.0 + openapi.yaml 1.15.0 -> 1.17.0 (three-way
  drift closed: VERSION=package.json=openapi; start.sh build stamps
  single-sourced)
- README: quickstart endpoints rewritten against the live router (the
  fictional /api/caddy/{config,reload} section replaced with the real
  /api/v1/caddy/* routes from routes/sites.js), 50+ -> 78 templates
  (proven in VERIFY-OUTPUT.txt via require of src/docker/app-templates),
  version badge 1.17.0, yourusername links -> sami7777, roadmap
  reconciled with shipped features (multi-user DC-048, DNS UI DC-166,
  backup automation marked shipped), verification note scoped to the
  MCP drift gate's actual coverage
- API-SURFACE.md regenerated: 443 handler rows / 368 unique paths / 441
  unique operations / 88 public rows, Known Limitations section (static
  extraction, line-oriented, may omit multiline/computed/chained
  registrations), exact duplicate registrations with file:line
- VERIFY-OUTPUT.txt: verbatim command/output transcript proving all
  version + count claims (sha256 of the generated doc recorded and
  matching)
- state-manager test mock extended for the atomic tmp+rename contract

Judge rounds: r1 D -> r2 D -> r3 D -> r4 D -> r5 C -> r6 C -> r7 C ->
r8 C -> r9 C -> r10 A (each round fixed blockers in-lane; no bypasses).
r10 independently reproduced all counts and the generated doc hash
against the live repository.
2026-10-29 02:29:07 -07:00

445 lines
12 KiB
Markdown

# DashCaddy
**Self-hosted dashboard for managing Docker apps with automatic SSL, DNS, and reverse proxy configuration.**
![Version](https://img.shields.io/badge/version-1.17.0-blue)
![License](https://img.shields.io/badge/license-Proprietary-red)
## What is DashCaddy?
DashCaddy is an all-in-one solution for self-hosting Docker applications. It combines:
- 🎨 **Beautiful Dashboard** - Monitor all your services in one place
- 🐳 **Docker Management** - Deploy 78 pre-configured apps with one click
- 🔒 **Automatic SSL** - Internal CA with automatic certificate generation
- 🌐 **DNS Integration** - Automatic DNS record creation (Technitium DNS)
- 🔄 **Reverse Proxy** - Caddy configuration managed automatically
- 🔐 **Tailscale Support** - Secure remote access built-in
## Features
### Authentication & Security
- Built-in TOTP two-factor authentication
- Fine-grained access control per service
- Secure session management
- Group-based permissions
### Dashboard
- Real-time service health monitoring
- Response time tracking
- Status indicators with visual feedback
- Weather widget
- Multiple themes (dark/light/blue)
- Import/export configuration
### App Deployment
- 78 pre-configured app templates
- One-click deployment
- Automatic DNS + SSL + reverse proxy setup
- Container health checking
- Deployment status tracking
- SSL certificate generation monitoring
### Service Management
- Add/edit/delete services
- Restart containers
- View logs
- Update configurations
- Silent deletions (no annoying popups)
### Developer Tools
- Error log viewer
- API endpoints for automation
- Import/export for testing
- Comprehensive error logging
## Quick Start
### Prerequisites
- Docker & Docker Compose
- Caddy web server
- Technitium DNS (optional, for automatic DNS)
- Node.js 18+ (for API server)
### Installation
1. **Clone the repository**
```bash
git clone https://github.com/sami7777/dashcaddy.git
cd dashcaddy
```
2. **Install dependencies**
```bash
cd dashcaddy-api
npm install
```
3. **Configure environment**
```bash
cp .env.example .env
# Edit .env with your settings
```
4. **Start the API server**
```bash
npm start
```
5. **Configure Caddy**
Add to your Caddyfile:
```
status.yourdomain.com {
root * /path/to/dashcaddy/status
file_server
reverse_proxy /api/* localhost:3001
}
```
6. **Access the dashboard**
Open `https://status.yourdomain.com` in your browser
## Health Probes
DashCaddy exposes Kubernetes/Docker-standard health endpoints for container orchestration. **No auth required** — these are designed for orchestration tooling to poll.
| Path | Purpose | Returns |
|------|---------|---------|
| `/healthz` or `/health/live` | **Liveness** — is the Node.js process alive? | 200 with `{status: "alive", uptime: <seconds>}` |
| `/readyz` or `/health/ready` | **Readiness** — are critical deps reachable? (config file, services file, Docker daemon, Caddy admin API) | 200 if all OK, 503 if any dep fails (with details in the `checks` object) |
| `/health` | Backwards-compat alias for `/healthz` | Same as `/healthz` |
**When to use which:**
- Use `/healthz` / `/health/live` in a `livenessProbe` — should the container be **restarted**?
- Use `/readyz` / `/health/ready` in a `readinessProbe` — should traffic be **routed** to this instance?
### Docker Compose healthcheck
Copy-paste this into your DashCaddy `docker-compose.yml`:
```yaml
services:
dashcaddy-api:
image: ghcr.io/samiahmed7777/dashcaddy-api:latest
# ... your existing config ...
healthcheck:
test: ["CMD", "node", "-e", "require('http').get('http://localhost:3001/readyz', r => process.exit(r.statusCode === 200 ? 0 : 1)).on('error', () => process.exit(1))"]
interval: 30s
timeout: 5s
retries: 3
start_period: 30s
```
### Kubernetes probes
```yaml
livenessProbe:
httpGet:
path: /healthz
port: 3001
initialDelaySeconds: 30
periodSeconds: 30
readinessProbe:
httpGet:
path: /readyz
port: 3001
initialDelaySeconds: 10
periodSeconds: 10
```
Both endpoints return JSON. Liveness is cheap (no I/O, no deps). Readiness touches the Docker daemon and Caddy admin API with a 3-second timeout each, so it's safe to poll every 10s without load concerns.
## Configuration
### Environment Variables
Create a `.env` file in the `dashcaddy-api` directory:
```env
# Caddy Configuration
CADDYFILE_PATH=/path/to/Caddyfile
CADDY_ADMIN_URL=http://localhost:2019
# DNS Configuration (optional)
DNS_SERVER=192.168.1.1
DNS_TOKEN=your-dns-token
# File Paths
SERVICES_FILE=/path/to/services.json
ERROR_LOG_FILE=/path/to/dashcaddy-errors.log
```
### DNS Integration
DashCaddy works with Technitium DNS for automatic DNS record creation:
1. Install Technitium DNS
2. Create an API token with DNS management permissions
3. Configure DNS credentials in dashboard (🔑 Tokens button)
### Tailscale Integration
For secure remote access:
1. Install Tailscale on your server
2. Services can be restricted to Tailscale-only access
3. Configure in deployment settings
## Usage
### Deploying an App
1. Click **"App Selector"** button
2. Choose an app from the template library
3. Configure:
- Subdomain (e.g., `jellyfin` → `jellyfin.yourdomain.com`)
- Port (auto-suggested)
- IP address (defaults to localhost)
- Tailscale-only access (optional)
4. Click **"Deploy"**
5. Wait for SSL certificate generation (30-60 seconds)
6. Access your app!
### Managing Services
- **View Status**: Cards show real-time health and response times
- **Open Service**: Click "Open" button
- **Restart**: Click restart button (for Docker containers)
- **Delete**: Click delete button (removes everything: container, DNS, Caddy config)
- **Edit**: Click settings button to modify configuration
### Viewing Error Logs
1. Click **"📋 Logs"** button in toolbar
2. View all errors with timestamps and context
3. Refresh to see latest errors
4. Clear logs when resolved
### Log PII Redaction
Every log sink (console JSON, `error.log`, audit details) masks email addresses with a canonical form (`sa****@example.com`) — raw addresses never reach disk or stdout. When `error.log` crosses 5 MB it rotates to `error.log.1`, and the archive is scrubbed with the same canonical mask on rotation.
For **pre-existing** log files written before this defense existed:
```bash
node scripts/redact-log-pii.js --dry-run <file-or-dir> # see what would change
node scripts/redact-log-pii.js <file-or-dir> # atomic in-place rewrite
```
The script is idempotent, never touches byte-identical files (mtime preserved), reuses the same masking code the live logger uses (no regex drift), and post-verifies that no raw address remains (exit code 2 if any does). See `dashcaddy-api/scripts/redact-log-pii.js` header for flags including `--keep-raw` (explicitly preserves the raw copy — avoid unless required).
### Backup & Restore
**Export Configuration:**
1. Click **"📤 Export"** button
2. JSON file downloads with all your services
3. Save safely
**Import Configuration:**
1. Click **"📥 Import"** button
2. Select your backup JSON file
3. Confirm import
4. Dashboard reloads with restored configuration
**Note**: API tokens are not exported for security. Reconfigure after import.
## App Templates
DashCaddy includes 78 pre-configured templates:
### Media & Entertainment
- Plex, Jellyfin, Emby
- Navidrome, Airsonic
- Tautulli, Overseerr
### Downloads
- Sonarr, Radarr, Lidarr, Readarr
- Prowlarr, Bazarr
- qBittorrent, Transmission
- SABnzbd, NZBGet
### Productivity
- Nextcloud
- Paperless-ngx
- BookStack, Outline
- Standard Notes
### Management
- Portainer
- Homepage, Homarr
- Uptime Kuma
- Grafana
### Security & Authentication
- Vaultwarden (Password Manager)
### Development
- Gitea
- VS Code Server
- Jenkins, Drone CI
### And many more!
## API Endpoints
### Services
- `GET /api/v1/services` - List all services
- `POST /api/v1/services` - Add service
- `PUT /api/v1/services` - Bulk import services
- `DELETE /api/v1/services/:id` - Remove service
### App Deployment
- `GET /api/v1/apps/templates` - List app templates
- `POST /api/v1/apps/deploy` - Deploy new app
- `DELETE /api/v1/apps/:appId` - Remove deployed app
### Error Logs
- `GET /api/v1/error-logs` - Get error logs
- `DELETE /api/v1/error-logs` - Clear error logs
### DNS Management
- `POST /api/v1/dns/record` - Create DNS record
- `DELETE /api/v1/dns/record` - Delete DNS record
- `GET /api/v1/dns/records` - List DNS records (active provider)
### Reverse Proxy & Caddy Management
- `GET /api/v1/caddy/config` - Get Caddyfile content
- `POST /api/v1/caddy/reload` - Reload Caddy configuration
- `GET /api/v1/caddy/cas` - List upstream Caddy servers
- `POST /api/v1/caddycode/generate` - Generate a Caddyfile site block
- `POST /api/v1/caddycode/validate` - Validate a site-block config
- `GET /api/v1/caddycode/templates` - Preset configs for common patterns
> Endpoint accuracy: the MCP route-existence drift gate
> (`__tests__/mcp/mcp-core-dc166-integration.test.js`) verifies every MCP
> tool's handler-issued API call against the declared routes; the entries
> above were additionally spot-checked against the router, and the full
> generated inventory lives in [API-SURFACE.md](API-SURFACE.md).
## Troubleshooting
### SSL Certificate Errors
**Problem**: "Secure Connection Failed" when accessing new service
**Solution**:
- Wait 30-60 seconds for certificate generation
- Check dashboard notification for SSL status
- Manually reload Caddy: `caddy reload --config /path/to/Caddyfile`
- Check error logs in dashboard
### DNS Not Resolving
**Problem**: Service URL doesn't resolve
**Solution**:
- Verify DNS server is running
- Check DNS credentials in 🔑 Tokens menu
- Manually add DNS record in Technitium DNS
- Flush DNS cache: `ipconfig /flushdns` (Windows) or `sudo systemd-resolve --flush-caches` (Linux)
### Container Won't Start
**Problem**: Deployment succeeds but service is offline
**Solution**:
- Check Docker logs: `docker logs [container-id]`
- Verify port isn't already in use
- Check container resource limits
- View error logs in dashboard
### Import/Export Issues
**Problem**: Import fails or data is incomplete
**Solution**:
- Validate JSON format
- Check file has `version` and `services` fields
- Reconfigure API tokens after import
- Check error logs for details
## Development
### Project Structure
```
dashcaddy/
├── status/ # Dashboard frontend
│ ├── index.html # Main dashboard
│ └── assets/ # Logos, icons, fonts
├── dashcaddy-api/ # API backend
│ ├── server.js # Express server
│ ├── src/docker/app-templates.js # App template definitions
│ └── package.json # Dependencies
├── dashcaddy-installer/ # Electron installer (WIP)
└── docs/ # Documentation
```
### Adding Custom App Templates
Edit `dashcaddy-api/src/docker/app-templates.js`:
```javascript
"myapp": {
name: "My App",
description: "Description of my app",
icon: "🚀",
logo: "https://cdn.example.com/logo.png",
category: "Productivity",
docker: {
image: "myapp/myapp:latest",
ports: ["{{PORT}}:8080"],
volumes: ["/opt/myapp:/data"],
environment: {
"APP_ENV": "production"
}
},
subdomain: "myapp",
defaultPort: 8080,
healthCheck: "/health"
}
```
### Contributing
Contributions are welcome! Please:
1. Fork the repository
2. Create a feature branch
3. Make your changes
4. Test thoroughly
5. Submit a pull request
## Roadmap
- [ ] Service groups/categories
- [ ] Container log viewer
- [x] DNS management UI (DC-166)
- [x] Backup automation (schedules + point-in-time restore)
- [x] Multi-user support (DC-048 — opt-in via `siteConfig.authProviders.email.enabled`; bootstrap admin, allowlist, invites)
- [ ] Mobile app
- [ ] Analytics dashboard
- [ ] Template marketplace
## License
Proprietary software. All rights reserved. See [LICENSE](LICENSE) for the End-User License Agreement (EULA).
## Credits
- **Dashboard Icons**: [walkxcode/dashboard-icons](https://github.com/walkxcode/dashboard-icons) (MIT License)
- **Caddy**: [caddyserver.com](https://caddyserver.com/)
- **Technitium DNS**: [technitium.com/dns](https://technitium.com/dns/)
## Support
- **Issues**: [GitHub Issues](https://github.com/sami7777/dashcaddy/issues)
- **Discussions**: [GitHub Discussions](https://github.com/sami7777/dashcaddy/discussions)
- **Documentation**: [Wiki](https://github.com/sami7777/dashcaddy/wiki)
## Acknowledgments
Built with ❤️ for the self-hosting community.
---
**DashCaddy** - Making self-hosting beautiful and effortless.