vmbb — a small, self-contained CLI for exploring Virtualmin
backup archives without needing Perl, GNU tar, or the matching compression
tools installed. A single static binary (~2.5 MB) understands every container
format Virtualmin produces, including the nested "tar inside a tar" layout.
Virtualmin backups are an outer archive of per-feature files, and some of those
files (notably the home directory) are themselves archives. On Windows and
macOS the bundled archive tools often have incomplete support for GNU
tar extensions, making backups awkward to inspect. vmbb reads them directly.
| Extension | Container |
|---|---|
.tar |
uncompressed tar |
.tar.gz |
gzip |
.tar.bz2 |
bzip2 |
.tar.zst |
zstd |
.zip |
zip |
Compression is detected by magic bytes, not the filename.
vmbb list <backup> Summarise domains and features
vmbb tree <backup> [--deep] List every member (--deep recurses nested archives)
vmbb info <backup> [domain] Show decoded domain metadata
vmbb categorize <backup> [domain] Group backed-up data by where it restores
vmbb cat <backup> <entry> Write a member to stdout (nested: outer::inner)
vmbb extract <backup> [entry] [-o dir] [--raw] Extract to disk
extract with no entry unpacks the whole backup into -o (default: the
current directory), expanding nested archives — the home directory, the Webmin
config tar — into subdirectories so everything is browsable as ordinary files.
--raw leaves those as their original .tar files. Given an entry (a member
name from vmbb tree), it extracts just that one member; -o directories are
created as needed.
<backup> is either a single archive file or a directory-format backup —
a directory of per-domain archives (<domain>.tar.gz) with .info/.dom
sidecars. Members from every per-domain archive are aggregated, so the same
commands work on both; info reads the richer .dom sidecar when present.
A nested path uses :: to descend one archive level, e.g.
vmbb cat backup.tar.gz "example.com_dir.tar::public_html/index.html"
Members are named [.backup/]<domain>_<feature>[_<sub>][archive-suffix]. The
domain never contains an underscore, so the first underscore separates it from
the feature id. Global configuration lives under the pseudo-domain
virtualmin. .info/.dom sidecar files (directory-format backups) use
Webmin's serialise_variable encoding, decoded by internal/serialise.
macOS / Linux (Homebrew):
brew install virtualmin/tap/vmbb
Windows (Scoop):
scoop bucket add virtualmin https://github.com/virtualmin/scoop-bucket
scoop install vmbb
Or grab a binary from the releases page.
A direct download may be flagged on first run because it is not notarized
(macOS) or lacks SmartScreen reputation (Windows); the package managers above
avoid that. To clear it manually on macOS: xattr -d com.apple.quarantine ./vmbb.
go build -o vmbb ./cmd/vmbb
CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build -ldflags="-s -w" -o vmbb.exe ./cmd/vmbb
Implemented: format detection, the five containers, single-file and
directory-format backups, nested _dir.tar recursion,
list/tree/info/categorize/cat/extract, .dom/.info
serialise_variable decoding, feature-aware categorisation.
Not yet implemented: GPG-encrypted backups; GNU --listed-incremental
differential metadata.