virtle

command module
v0.3.3 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Aug 21, 2026 License: MIT Imports: 19 Imported by: 0

README

Virtle the Space Turtle

virtle 🐢🪐

Virtle is a VM manager for sandbox workflows.

Status: Beta. Used day-to-day by a few people, feedback appreciated.

Background: Originally designed to be used with agentspace, a NixOS-based sandbox builder, but it virtle has been refined enough to act as a standalone tool.

How does it work?

virtle reads a manifest, starts the required host processes, launches QEMU, waits for guest SSH readiness, attaches an active session with --ssh.

It also handles teardown, QMP-based shutdown, disk-backed suspend/resume, runtime vsock CID allocation, QGA-based remote commands, and more.

Features
  • Runs a QEMU microvm.
  • Allocates block overlay images.
  • Manages virtiofsd daemons for virtiofs mounts.
  • Provisions SSH between host and guest.
  • Connects over SSH upon boot via signaling.
  • Write files between guest and host on boot or shutdown.
  • Suspend and resume.
  • Notification execution hooks.
  • Exposes a virtle.sock for RPC (also usable via virtle rpc sub-command).
  • (Experimental) Balloon memory: Auto-adjust memory available to the VM based on internal memory pressure metrics.
  • (Experimental) Hotplug: Attach/detach devices during runtime (requires full VM).

Usage

First, write a simple manifest and save it as manifest.toml. See: ./examples/manifest.*.toml.

Global flags:

  • virtle [--manifest=MANIFEST] ... - When --manifest is omitted, ./manifest.toml is used by default.
  • virtle -v ... - Show useful VM and SSH lifecycle information.
  • virtle -vv ... - Show debugging details and output from background commands.

Launch a VM:

  • virtle launch [--ssh] [--resume=no|auto|force] [-- <remote-cmd...>]

Other advanced features:

  • virtle suspend
  • virtle rpc METHOD [JSON_ARGS]
  • virtle hotplug ID (experimental)
  • virtle hotplug --detach ID (experimental)
Manifest

There are some handy sub-commands for working with manifest files:

  • virtle manifest defaults [--resolved]
  • virtle manifest validate
  • virtle manifest resolve
  • virtle manifest schema

Manifest exec arrays render each argv element as a Go text/template. The host process environment is available as .Env on every surface.

Surface Template values Injected environment
qemu.exec HostName, WorkingDir, StateDir, HostOS, HostArch, HostSystem, .Env none
qemu.fwd_tunnel_exec Host, Port, .Env none; QEMU starts the command
ssh.exec CID, User, Destination, .Env CID, USER, DESTINATION
mounts[type=virtiofs].virtiofs Socket, MountSource, MountTag, .Env SOCKET, MOUNT_SOURCE, MOUNT_TAG
run[].exec CID, StateDir, Workspace.GuestPath, Workspace.HostPath, user vars, .Env scalar top-level values only
notifications.exec State, Message, notification context values, .Env STATE, MESSAGE, normalized context values

Library

Virtle library docs: https://pkg.go.dev/github.com/shazow/virtle

Boot a VM, run a command, tear down:

spec := &vm.Spec{
	Kernel: vm.Kernel{Path: "vmlinuz", Initrd: "initrd.img"},
	Shares: []vm.Share{{Tag: "src", HostPath: ".", GuestPath: "/workspace"}},
	Memory: 2048 * units.Mebibyte,
}
b, err := qemu.New(qemu.Config{
	RemoteControl: qemu.QGA{},
	Logger:        slog.Default(),
})
if err != nil {
	log.Fatal(err)
}
inst, err := b.Start(ctx, spec)
if err != nil {
	log.Fatal(err)
}
defer backend.Shutdown(ctx, inst)

g, err := inst.RemoteControl()
if err != nil {
	log.Fatal(err) // this VM has no guest agent
}
out, err := g.Run(ctx, &vm.GuestCmd{Path: "make", Dir: "/workspace"})
fmt.Printf("exit=%d\n%s", out.ExitCode, out.Stdout)

Optional functionality is discovered by type assertion, as in database/sql/driver:

if s, ok := b.(backend.Suspender); ok {
	err = s.Suspend(ctx, inst, "")
} else {
	err = backend.Shutdown(ctx, inst)
}

Or drive it from a manifest, as the CLI does:

spec, b, err := manifest.Load(f)
inst, err := b.Start(ctx, spec)

License

MIT

Documentation

The Go Gopher

There is no documentation for this package.

Directories

Path Synopsis
Package backend defines the implementer contract for virtle VM backends, mirroring the database/sql/driver split: consumers hold the interfaces declared here, implementations live in backend-named subpackages (backend/qemu today).
Package backend defines the implementer contract for virtle VM backends, mirroring the database/sql/driver split: consumers hold the interfaces declared here, implementations live in backend-named subpackages (backend/qemu today).
qemu
Package qemu implements a virtle backend that launches virtual machines with QEMU.
Package qemu implements a virtle backend that launches virtual machines with QEMU.
qemu/internal/balloon
Package balloon implements the internal virtio-balloon feature.
Package balloon implements the internal virtio-balloon feature.
qemu/internal/hotplug
Package hotplug attaches and detaches runtime devices for a running VM.
Package hotplug attaches and detaches runtime devices for a running VM.
qemu/internal/launch
Package launch contains the host-side launch planning and startup helpers.
Package launch contains the host-side launch planning and startup helpers.
qemu/internal/qga
Package qga wraps the QEMU guest agent commands used by virtle.
Package qga wraps the QEMU guest agent commands used by virtle.
qemu/internal/qmpclient
Package qmpclient wraps the QEMU Machine Protocol commands used by virtle.
Package qmpclient wraps the QEMU Machine Protocol commands used by virtle.
qemu/internal/qmpwire
Package qmpwire shares line-delimited JSON socket helpers between the QMP and guest-agent clients, which speak the same wire framing over unix sockets.
Package qmpwire shares line-delimited JSON socket helpers between the QMP and guest-agent clients, which speak the same wire framing over unix sockets.
qemu/internal/runtime
Package runtime owns the live manager runtime exposed through the control socket.
Package runtime owns the live manager runtime exposed through the control socket.
qemu/internal/vmm
Package vmm is the qemu backend's VM machinery: the host-side launcher lifecycle behind backend/qemu and the virtle CLI.
Package vmm is the qemu backend's VM machinery: the host-side launcher lifecycle behind backend/qemu and the virtle CLI.
qemu/session
Package session is the virtle CLI's session layer over the qemu VM machinery: boot with CLI semantics, run the foreground session (the ssh-ready gate, the interactive SSH attach loop with autoprovision and retries, suspend-on-signal, stats), and the out-of-process suspend and hotplug commands.
Package session is the virtle CLI's session layer over the qemu VM machinery: boot with CLI semantics, run the foreground session (the ssh-ready gate, the interactive SSH attach loop with autoprovision and retries, suspend-on-signal, stats), and the out-of-process suspend and hotplug commands.
internal
control
Package control implements virtle's local runtime control socket protocol.
Package control implements virtle's local runtime control socket protocol.
executor
Package executor renders exec command templates and manages external processes.
Package executor renders exec command templates and manages external processes.
executor/executortest
Package executortest provides test doubles for the executor package.
Package executortest provides test doubles for the executor package.
manifest
Package manifest defines the internal virtle launch contract.
Package manifest defines the internal virtle launch contract.
manifest/schema
Package schema generates the JSON Schema for the manifest input format.
Package schema generates the JSON Schema for the manifest input format.
manifest/tagged
Package tagged decodes and encodes JSON-style tagged union lists.
Package tagged decodes and encodes JSON-style tagged union lists.
readiness
Package readiness contains generic token-based readiness helpers.
Package readiness contains generic token-based readiness helpers.
sshtools
Package sshtools contains reusable SSH command helpers.
Package sshtools contains reusable SSH command helpers.
units
Package units defines small typed units shared by virtle configuration.
Package units defines small typed units shared by virtle configuration.
Package manifest loads virtle manifests (TOML or JSON) and lowers them to a neutral vm.Spec plus the backend they configure.
Package manifest loads virtle manifests (TOML or JSON) and lowers them to a neutral vm.Spec plus the backend they configure.
Package units defines small typed scalars shared across the virtle API, so sizes and durations are never plumbed around as bare ints.
Package units defines small typed scalars shared across the virtle API, so sizes and durations are never plumbed around as bare ints.
Package vm holds the consumer-facing types for describing and controlling virtual machines: the neutral Spec a backend launches, and the Guest interface for operating inside a running VM.
Package vm holds the consumer-facing types for describing and controlling virtual machines: the neutral Spec a backend launches, and the Guest interface for operating inside a running VM.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL