mirror of
https://github.com/dockur/windows.git
synced 2026-02-03 17:27:21 +00:00
feat: Add ISO cache for winctl.sh to skip re-downloads
Cache downloaded ISOs so new instances of the same Windows version skip the 3-6 GB download. Adds `winctl cache` subcommands (save/list/rm/flush) and auto-restores cached ISOs when creating new instances with --new. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
parent
3330596879
commit
2b07b9cf07
6
.gitignore
vendored
6
.gitignore
vendored
@ -6,3 +6,9 @@ data/*
|
||||
!data/*/
|
||||
data/*/**
|
||||
!data/*/.gitkeep
|
||||
|
||||
# Instance compose files and registry (generated at runtime)
|
||||
instances/
|
||||
|
||||
# ISO cache (cached ISOs for faster instance creation)
|
||||
cache/
|
||||
|
||||
437
WINCTL_GUIDE.md
437
WINCTL_GUIDE.md
@ -8,6 +8,9 @@ A comprehensive guide to managing Windows Docker containers with `winctl.sh`.
|
||||
- [Prerequisites](#prerequisites)
|
||||
- [Quick Start](#quick-start)
|
||||
- [Commands Reference](#commands-reference)
|
||||
- [Snapshots & Restore](#snapshots--restore)
|
||||
- [Multi-Instance Support](#multi-instance-support)
|
||||
- [ISO Cache](#iso-cache)
|
||||
- [Configuration](#configuration)
|
||||
- [ARM64 Setup](#arm64-setup)
|
||||
- [Interactive Menus](#interactive-menus)
|
||||
@ -24,6 +27,10 @@ A comprehensive guide to managing Windows Docker containers with `winctl.sh`.
|
||||
- **22 Windows versions** from Windows 2000 to Windows 11
|
||||
- **Simple commands** to start, stop, and manage containers
|
||||
- **Interactive menus** when you don't specify a version
|
||||
- **Snapshot & restore** for backing up and restoring VM data
|
||||
- **LAN IP detection** with remote access URLs shown automatically
|
||||
- **Port conflict detection** before starting containers
|
||||
- **Disk usage monitoring** with per-VM and snapshot breakdowns
|
||||
- **Status caching** for fast performance
|
||||
- **Resource profiles** optimized for modern and legacy systems
|
||||
- **ARM64 auto-detection** with architecture-aware image selection and version filtering
|
||||
@ -104,6 +111,7 @@ Prerequisites Check
|
||||
|
||||
[OK] All critical prerequisites passed!
|
||||
Architecture: amd64
|
||||
LAN IP: 192.168.1.100
|
||||
```
|
||||
|
||||
On ARM64, the output also shows:
|
||||
@ -111,6 +119,7 @@ On ARM64, the output also shows:
|
||||
Architecture: arm64
|
||||
ARM64 image: dockurr/windows-arm
|
||||
Supported: win11 win11e win11l win10 win10e win10l
|
||||
LAN IP: 192.168.1.100
|
||||
```
|
||||
|
||||
### Fix Common Issues
|
||||
@ -148,10 +157,13 @@ After starting, you'll see connection details:
|
||||
Connection Details:
|
||||
→ Web Viewer: http://localhost:8011
|
||||
→ RDP: localhost:3311
|
||||
→ LAN Web: http://192.168.1.100:8011
|
||||
→ LAN RDP: 192.168.1.100:3311
|
||||
```
|
||||
|
||||
- **Web Viewer**: Open in browser for quick access
|
||||
- **RDP**: Use any RDP client for better performance
|
||||
- **LAN URLs**: Shown automatically when a LAN IP is detected — use these to access from other devices on your network
|
||||
|
||||
### 3. Check Status
|
||||
|
||||
@ -187,10 +199,11 @@ Start one or more containers.
|
||||
**What it does:**
|
||||
1. Checks prerequisites (Docker, KVM)
|
||||
2. Detects architecture and blocks unsupported versions on ARM64
|
||||
3. Creates data directory if missing
|
||||
4. Checks available resources
|
||||
5. Starts the container
|
||||
6. Shows connection details
|
||||
3. Verifies ports are not already in use
|
||||
4. Creates data directory if missing
|
||||
5. Checks available resources
|
||||
6. Starts the container
|
||||
7. Shows connection details (including LAN URLs)
|
||||
|
||||
---
|
||||
|
||||
@ -245,6 +258,8 @@ Example output:
|
||||
win11 Windows 11 Pro running 8011 3311
|
||||
win10 Windows 10 Pro stopped 8010 3310
|
||||
winxp Windows XP Professional not created 8005 3305
|
||||
|
||||
LAN IP: 192.168.1.100 — use http://192.168.1.100:<web-port> for remote access
|
||||
```
|
||||
|
||||
---
|
||||
@ -370,6 +385,10 @@ Container Details: win11
|
||||
RDP Port: 3311
|
||||
Resources: modern
|
||||
Compose: compose/desktop/win11.yml
|
||||
Web URL: http://localhost:8011
|
||||
RDP: localhost:3311
|
||||
LAN Web: http://192.168.1.100:8011
|
||||
LAN RDP: 192.168.1.100:3311
|
||||
```
|
||||
|
||||
---
|
||||
@ -415,6 +434,337 @@ The cache is stored at `~/.cache/winctl/status.json` and auto-refreshes when:
|
||||
|
||||
---
|
||||
|
||||
### open
|
||||
|
||||
Open the web viewer in your default browser.
|
||||
|
||||
```bash
|
||||
./winctl.sh open win11
|
||||
```
|
||||
|
||||
If the container is not running, you'll be prompted to start it first.
|
||||
|
||||
---
|
||||
|
||||
### pull
|
||||
|
||||
Pull the latest Docker image.
|
||||
|
||||
```bash
|
||||
./winctl.sh pull
|
||||
```
|
||||
|
||||
Automatically selects `dockurr/windows` or `dockurr/windows-arm` based on detected architecture. Shows whether the image was updated or already up to date.
|
||||
|
||||
---
|
||||
|
||||
### disk
|
||||
|
||||
Show disk usage per VM data directory.
|
||||
|
||||
```bash
|
||||
# All VMs
|
||||
./winctl.sh disk
|
||||
|
||||
# Specific versions
|
||||
./winctl.sh disk win11 win10
|
||||
```
|
||||
|
||||
Example output:
|
||||
```
|
||||
Disk Usage
|
||||
────────────────────────────────────────────────────────────
|
||||
|
||||
VERSION SIZE STATUS
|
||||
────────────────────────────────────
|
||||
win11 45.2G running
|
||||
win10 32.1G stopped
|
||||
────────────────────────────────────
|
||||
Total: 77.3G
|
||||
|
||||
Snapshots: 12.5G (2 snapshots)
|
||||
win11 12.5G (2 snapshots)
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### snapshot
|
||||
|
||||
Back up a VM's data directory.
|
||||
|
||||
```bash
|
||||
# Auto-named with timestamp
|
||||
./winctl.sh snapshot win11
|
||||
|
||||
# Custom name
|
||||
./winctl.sh snapshot win11 before-update
|
||||
```
|
||||
|
||||
The snapshot is saved to `snapshots/<version>/<name>/`. The container is stopped during the copy and restarted automatically.
|
||||
|
||||
---
|
||||
|
||||
### restore
|
||||
|
||||
Restore a VM's data directory from a snapshot.
|
||||
|
||||
```bash
|
||||
# Interactive snapshot selection
|
||||
./winctl.sh restore win11
|
||||
|
||||
# Restore specific snapshot
|
||||
./winctl.sh restore win11 before-update
|
||||
```
|
||||
|
||||
If no snapshot name is given, a list of available snapshots is shown for selection. Requires typing `yes` to confirm (destructive: replaces current data).
|
||||
|
||||
---
|
||||
|
||||
### clean
|
||||
|
||||
Remove stopped containers and optionally purge their data directories.
|
||||
|
||||
```bash
|
||||
# Remove stopped containers only
|
||||
./winctl.sh clean
|
||||
|
||||
# Also delete data directories for stopped containers
|
||||
./winctl.sh clean --data
|
||||
```
|
||||
|
||||
Requires typing `yes` to confirm. Shows freed disk space on completion.
|
||||
|
||||
---
|
||||
|
||||
## Snapshots & Restore
|
||||
|
||||
`winctl.sh` supports snapshot and restore for VM data directories, stored under `snapshots/`.
|
||||
|
||||
### Creating a Snapshot
|
||||
|
||||
```bash
|
||||
# Snapshot with auto-generated timestamp name
|
||||
./winctl.sh snapshot win11
|
||||
|
||||
# Snapshot with custom name
|
||||
./winctl.sh snapshot win11 before-update
|
||||
```
|
||||
|
||||
The container is stopped during the copy to ensure data consistency, then restarted automatically.
|
||||
|
||||
### Listing Snapshots
|
||||
|
||||
```bash
|
||||
# Via disk command
|
||||
./winctl.sh disk
|
||||
|
||||
# Or browse directly
|
||||
ls snapshots/win11/
|
||||
```
|
||||
|
||||
### Restoring a Snapshot
|
||||
|
||||
```bash
|
||||
# Interactive selection
|
||||
./winctl.sh restore win11
|
||||
|
||||
# Direct restore
|
||||
./winctl.sh restore win11 before-update
|
||||
```
|
||||
|
||||
**Warning:** Restore replaces all current data for the version. The container is stopped during restore and restarted automatically.
|
||||
|
||||
### Snapshot Directory Structure
|
||||
|
||||
```
|
||||
snapshots/
|
||||
├── win11/
|
||||
│ ├── 20260129-143022/ # Auto-named
|
||||
│ └── before-update/ # Custom-named
|
||||
└── win10/
|
||||
└── 20260128-091500/
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Multi-Instance Support
|
||||
|
||||
Run multiple instances of the same Windows version with auto-managed ports and a JSON registry.
|
||||
|
||||
### Creating an Instance
|
||||
|
||||
```bash
|
||||
# Create winxp-1 with auto-allocated ports
|
||||
./winctl.sh start winxp --new
|
||||
|
||||
# Create winxp-lab with a custom name
|
||||
./winctl.sh start winxp --new lab
|
||||
|
||||
# Create winxp-lab and clone data from base winxp
|
||||
./winctl.sh start winxp --new lab --clone
|
||||
```
|
||||
|
||||
The `--new` flag:
|
||||
1. Allocates unique ports (web: 9000+, RDP: 4000+)
|
||||
2. Generates a compose file in `instances/<name>.yml`
|
||||
3. Creates a data directory at `data/<name>/`
|
||||
4. Registers the instance in `instances/registry.json`
|
||||
5. Starts the container
|
||||
|
||||
### Managing Instances
|
||||
|
||||
Instances work transparently with all existing commands:
|
||||
|
||||
```bash
|
||||
# Stop an instance
|
||||
./winctl.sh stop winxp-lab
|
||||
|
||||
# Restart an instance
|
||||
./winctl.sh restart winxp-lab
|
||||
|
||||
# View logs
|
||||
./winctl.sh logs winxp-lab -f
|
||||
|
||||
# Open shell
|
||||
./winctl.sh shell winxp-lab
|
||||
|
||||
# Inspect details
|
||||
./winctl.sh inspect winxp-lab
|
||||
|
||||
# Open web viewer
|
||||
./winctl.sh open winxp-lab
|
||||
|
||||
# Snapshot and restore
|
||||
./winctl.sh snapshot winxp-lab before-update
|
||||
./winctl.sh restore winxp-lab before-update
|
||||
```
|
||||
|
||||
### Listing Instances
|
||||
|
||||
```bash
|
||||
# List all instances
|
||||
./winctl.sh instances
|
||||
|
||||
# Filter by base version
|
||||
./winctl.sh instances winxp
|
||||
```
|
||||
|
||||
Example output:
|
||||
```
|
||||
Instances
|
||||
────────────────────────────────────────────────────────────
|
||||
|
||||
INSTANCE BASE STATUS WEB RDP CREATED
|
||||
──────────────────────────────────────────────────────────────────────────────
|
||||
winxp-1 winxp running 9000 4000 2026-01-30
|
||||
winxp-lab winxp stopped 9001 4001 2026-01-30
|
||||
```
|
||||
|
||||
### Destroying an Instance
|
||||
|
||||
```bash
|
||||
./winctl.sh destroy winxp-lab
|
||||
```
|
||||
|
||||
This will:
|
||||
1. Stop and remove the container
|
||||
2. Delete the compose file
|
||||
3. Prompt to delete the data directory
|
||||
4. Remove the instance from the registry
|
||||
|
||||
### How It Works
|
||||
|
||||
- **Port allocation**: Web ports start at 9000, RDP at 4000, auto-incrementing to avoid conflicts
|
||||
- **Naming**: Instances are named `<version>-<suffix>` (e.g., `winxp-1`, `winxp-lab`)
|
||||
- **Registry**: All instances are tracked in `instances/registry.json`
|
||||
- **Compose files**: Generated in `instances/<name>.yml` with relative paths to env files and data
|
||||
- **No collisions**: Base versions never contain hyphens; instances always do
|
||||
|
||||
### Instance Directory Structure
|
||||
|
||||
```
|
||||
instances/
|
||||
├── registry.json # Instance registry
|
||||
├── winxp-1.yml # Generated compose file
|
||||
└── winxp-lab.yml # Generated compose file
|
||||
|
||||
data/
|
||||
├── winxp/ # Base version data
|
||||
├── winxp-1/ # Instance data
|
||||
└── winxp-lab/ # Instance data (cloned from base)
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## ISO Cache
|
||||
|
||||
Windows ISOs are large (3-6 GB) and re-downloaded every time a new container is created for the same version. The ISO cache saves downloaded ISOs so new instances can skip the download.
|
||||
|
||||
### How It Works
|
||||
|
||||
1. Start a VM and wait for the ISO to download
|
||||
2. Cache the ISO: `./winctl.sh cache save winxp`
|
||||
3. Create new instances — cached ISOs are auto-restored: `./winctl.sh start winxp --new`
|
||||
|
||||
When creating a new instance with `--new`, winctl checks `cache/<version>/` for ISOs and copies them into the new instance's data directory before starting the container. The container sees the ISO on startup and skips the download.
|
||||
|
||||
### Caching an ISO
|
||||
|
||||
```bash
|
||||
# Cache ISOs from an existing VM's data directory
|
||||
./winctl.sh cache save winxp
|
||||
./winctl.sh cache save win11
|
||||
```
|
||||
|
||||
The ISOs are copied from `data/<name>/` to `cache/<base-version>/`.
|
||||
|
||||
### Listing Cached ISOs
|
||||
|
||||
```bash
|
||||
./winctl.sh cache list
|
||||
```
|
||||
|
||||
Shows all cached ISOs grouped by version with file sizes and a total.
|
||||
|
||||
### Removing Cached ISOs
|
||||
|
||||
```bash
|
||||
# Remove cached ISOs for a specific version
|
||||
./winctl.sh cache rm winxp
|
||||
|
||||
# Remove all cached ISOs
|
||||
./winctl.sh cache flush
|
||||
```
|
||||
|
||||
Both commands require typing `yes` to confirm.
|
||||
|
||||
### Auto-Restore
|
||||
|
||||
When creating a new instance with `--new` (without `--clone`), winctl automatically checks the cache:
|
||||
|
||||
```bash
|
||||
# If cache/winxp/ has ISOs, they are copied to data/winxp-1/ before start
|
||||
./winctl.sh start winxp --new
|
||||
```
|
||||
|
||||
This is skipped when using `--clone`, since cloning copies all data from the base version including any ISOs.
|
||||
|
||||
### Cache Directory Structure
|
||||
|
||||
```
|
||||
cache/
|
||||
├── winxp/
|
||||
│ └── custom.iso
|
||||
├── win11/
|
||||
│ └── win11x64.iso
|
||||
└── win10/
|
||||
└── win10x64.iso
|
||||
```
|
||||
|
||||
> **Note:** The cache stores processed ISOs from the container's data directory, not raw downloads.
|
||||
|
||||
---
|
||||
|
||||
## Configuration
|
||||
|
||||
### Environment Files
|
||||
@ -683,6 +1033,55 @@ rm -rf data/win11/*
|
||||
./winctl.sh start win11
|
||||
```
|
||||
|
||||
### Scenario 8: Snapshot Before a Risky Change
|
||||
|
||||
```bash
|
||||
# Create a snapshot before installing something
|
||||
./winctl.sh snapshot win11 before-update
|
||||
|
||||
# Do your work...
|
||||
# If something goes wrong, restore:
|
||||
./winctl.sh restore win11 before-update
|
||||
```
|
||||
|
||||
### Scenario 9: Clean Up Disk Space
|
||||
|
||||
```bash
|
||||
# Check disk usage
|
||||
./winctl.sh disk
|
||||
|
||||
# Remove stopped containers
|
||||
./winctl.sh clean
|
||||
|
||||
# Remove stopped containers AND their data
|
||||
./winctl.sh clean --data
|
||||
```
|
||||
|
||||
### Scenario 10: Quick Access from Browser
|
||||
|
||||
```bash
|
||||
# Open web viewer directly in your browser
|
||||
./winctl.sh open win11
|
||||
|
||||
# Or pull latest image before starting
|
||||
./winctl.sh pull
|
||||
./winctl.sh start win11
|
||||
```
|
||||
|
||||
### Scenario 11: Access from Another Device on LAN
|
||||
|
||||
```bash
|
||||
# Check your LAN IP
|
||||
./winctl.sh check
|
||||
|
||||
# Start a VM — LAN URLs are shown automatically
|
||||
./winctl.sh start win11
|
||||
# → LAN Web: http://192.168.1.100:8011
|
||||
# → LAN RDP: 192.168.1.100:3311
|
||||
|
||||
# Use the LAN URL from any device on the same network
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Troubleshooting
|
||||
@ -701,8 +1100,8 @@ rm -rf data/win11/*
|
||||
|
||||
**Common issues:**
|
||||
- KVM not accessible → Add user to kvm group
|
||||
- Port already in use → Stop other containers or services
|
||||
- Not enough disk space → Free up space or reduce DISK_SIZE
|
||||
- Port already in use → `start` auto-detects port conflicts; stop the conflicting service or container
|
||||
- Not enough disk space → Run `./winctl.sh disk` to check usage, or free up space
|
||||
|
||||
### Slow Performance
|
||||
|
||||
@ -760,15 +1159,16 @@ Bookmark your commonly used VMs:
|
||||
|
||||
Each VM has a "Shared" folder on the desktop that maps to the host. Use this to transfer files.
|
||||
|
||||
### 4. Snapshots via Data Backup
|
||||
### 4. Snapshots
|
||||
|
||||
The VM disk is stored in `data/<version>/`. Back it up to create a snapshot:
|
||||
Use the built-in snapshot and restore commands:
|
||||
```bash
|
||||
./winctl.sh stop win11
|
||||
cp -r data/win11 data/win11-backup
|
||||
./winctl.sh start win11
|
||||
./winctl.sh snapshot win11 my-backup
|
||||
./winctl.sh restore win11 my-backup
|
||||
```
|
||||
|
||||
Snapshots are stored in `snapshots/<version>/<name>/`.
|
||||
|
||||
### 5. Running Multiple VMs
|
||||
|
||||
Check your available resources before starting multiple VMs:
|
||||
@ -801,10 +1201,25 @@ For servers, you can start VMs and access only via RDP:
|
||||
│ ├── legacy/ # Vista, XP, 2000
|
||||
│ ├── server/ # Server 2003-2025
|
||||
│ └── tiny/ # Tiny10, Tiny11
|
||||
├── instances/
|
||||
│ ├── registry.json # Instance registry
|
||||
│ ├── winxp-1.yml # Generated compose files
|
||||
│ └── winxp-lab.yml
|
||||
├── data/
|
||||
│ ├── win11/ # Win11 VM storage
|
||||
│ ├── win10/ # Win10 VM storage
|
||||
│ ├── winxp-1/ # Instance VM storage
|
||||
│ ├── winxp-lab/ # Instance VM storage
|
||||
│ └── ... # Other VM storage
|
||||
├── snapshots/
|
||||
│ ├── win11/ # Win11 snapshots
|
||||
│ │ ├── 20260129-143022/
|
||||
│ │ └── before-update/
|
||||
│ └── ... # Other version snapshots
|
||||
├── cache/
|
||||
│ ├── winxp/ # Cached winxp ISOs
|
||||
│ ├── win11/ # Cached win11 ISOs
|
||||
│ └── ... # Other cached ISOs
|
||||
└── ~/.cache/winctl/
|
||||
└── status.json # Status cache
|
||||
```
|
||||
|
||||
42
readme.md
42
readme.md
@ -106,6 +106,35 @@ Use `winctl.sh` for easy container management:
|
||||
# Rebuild container (preserves data)
|
||||
./winctl.sh rebuild win11
|
||||
|
||||
# Open web viewer in browser
|
||||
./winctl.sh open win11
|
||||
|
||||
# Pull latest Docker image
|
||||
./winctl.sh pull
|
||||
|
||||
# Show disk usage per VM
|
||||
./winctl.sh disk
|
||||
|
||||
# Snapshot and restore VM data
|
||||
./winctl.sh snapshot win11 before-update
|
||||
./winctl.sh restore win11 before-update
|
||||
|
||||
# Clean up stopped containers
|
||||
./winctl.sh clean
|
||||
|
||||
# Multi-instance support
|
||||
./winctl.sh start winxp --new # Create winxp-1 with auto ports
|
||||
./winctl.sh start winxp --new lab # Create winxp-lab
|
||||
./winctl.sh start winxp --new lab --clone # Clone data from base
|
||||
./winctl.sh instances # List all instances
|
||||
./winctl.sh destroy winxp-lab # Remove instance
|
||||
|
||||
# ISO cache (skip re-downloads for new instances)
|
||||
./winctl.sh cache save winxp # Cache ISO after first download
|
||||
./winctl.sh cache list # Show cached ISOs
|
||||
./winctl.sh cache rm winxp # Remove cached winxp ISO
|
||||
./winctl.sh cache flush # Clear all cached ISOs
|
||||
|
||||
# Full help (includes ARM64 info)
|
||||
./winctl.sh help
|
||||
```
|
||||
@ -153,9 +182,22 @@ compose/
|
||||
├── server/ # Server 2003-2025
|
||||
└── tiny/ # Tiny10, Tiny11
|
||||
|
||||
instances/ # Generated instance files
|
||||
├── registry.json # Instance registry
|
||||
└── *.yml # Instance compose files
|
||||
|
||||
data/ # VM storage (per-version folders)
|
||||
├── win11/
|
||||
├── winxp/
|
||||
├── winxp-1/ # Instance data
|
||||
└── ...
|
||||
|
||||
snapshots/ # VM data snapshots
|
||||
├── win11/
|
||||
└── ...
|
||||
|
||||
cache/ # ISO cache (skip re-downloads)
|
||||
├── winxp/
|
||||
└── ...
|
||||
```
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user