Offline-first HTTP backup scheduler with Web UI, retention and structured logging — written in Go.
httpBackupGo periodically downloads HTTP-accessible backup files (for example backup.zip),
stores them per site with timestamped filenames, enforces a retention policy, and exposes a
local-only web interface for configuration and control.
The application is designed to run unattended as a long-running process or service
(Windows service / systemd), while remaining fully usable from a browser on localhost.
- 🕒 Scheduled backups with configurable interval
- 🌐 Offline Web UI (no CDN, all assets embedded)
- 📁 Per-site backup directories
- 🗂 Retention policy (keep last N backups per site)
▶️ Run now trigger from the UI- 🔄 Live scheduler reload when config changes
- ⚡ Parallel downloads using goroutines with a concurrency limit
- 🧠 Atomic downloads using temporary files
- 📜 Structured JSON logging (
slog) - 🪟 Windows + Linux friendly paths
- 🔒 Web UI bound to
localhostonly by default
git clone https://github.com/krootjes/httpBackupGo
cd httpBackupGo
go build -o httpbackupgo
./httpbackupgohttp://127.0.0.1:8123
A configuration file is created automatically on first start.
Configuration is stored as JSON and can be edited via the Web UI or directly on disk.
Example config.json:
{
"IntervalMinutes": 5,
"BackupFolder": "C:\\Backups\\httpBackupGo",
"Retention": 30,
"WebListenAddr": "127.0.0.1:8123",
"Sites": [
{
"Enabled": true,
"Name": "site1",
"Url": "http://localhost:81/backup.zip"
}
]
}-
IntervalMinutes
Interval between scheduled runs (minutes). -
BackupFolder
Base directory where all backups are stored. -
Retention
Number of backups to keep per site. -
WebListenAddr
Address and port for the Web UI.
Changing this requires restarting the application. -
Sites
List of backup targets.
Backups are written to disk as:
<BackupFolder>/<SiteName>/backup_<SiteName>_DD-MM-YYYY_HH-mm-ss.zip
Example:
httpBackupGo/site1/backup_site1_10-01-2026_21-22-34.zip
Downloads are written to a temporary .tmp file first and then renamed,
preventing partial or corrupt backups.
- Runs on a ticker based on
IntervalMinutes - Reloads configuration on every tick
- Updates its interval dynamically when the config changes
- Prevents overlapping runs using an atomic guard
- Executes backups for all enabled sites
- Uses goroutines with a semaphore for concurrency control
- Each site runs independently
- Errors in one site do not stop others
- Applied after each successful backup
- Keeps only the newest
Retentionbackups per site - Removes the oldest backups first
- Best-effort: retention errors never fail a backup run
- Fully offline (embedded Bootstrap + assets)
- Edit configuration
- Enable/disable sites
- Trigger immediate runs
- Reload scheduler without restart
httpBackupGo uses structured JSON logging via log/slog.
-
Windows
C:\ProgramData\httpBackupGo\log.json -
Linux / macOS
./log.json
Logs are also written to stdout, making them compatible with journald when running as a systemd service.
Example log entry:
{
"time": "2026-01-13T22:41:12Z",
"level": "INFO",
"msg": "backup: saved",
"site": "site1",
"bytes": 7340032,
"duration_ms": 842
}Limits the number of concurrent downloads.
HTTPBACKUP_MAX_PARALLEL=10 ./httpbackupgoDefault: 5
httpBackupGo/
├── backup/ Backup execution logic
│ └── runner.go
├── config/ Config load/save/validation
│ └── config.go
├── retention/ Retention cleanup logic
│ └── cleanup.go
├── web/ Web UI (handlers, templates, static assets)
│ ├── server.go
│ ├── templates/
│ └── static/
├── logging/ Structured logging (slog)
│ └── logging.go
├── main.go Scheduler & application orchestration
├── go.mod
├── go.sum
└── README.md
The following are intentionally ignored:
config.json- Backup zip files
- Temporary
.tmpfiles - Log files
- IDE and OS artifacts
See .gitignore for details.
- Offline-first operation
- Minimal external dependencies
- Predictable scheduling
- Safe concurrency (no race conditions)
- Clear separation of concerns
- Production-ready defaults
MIT License
© 2026 krootjes