Skip to content

Commit ec875e6

Browse files
committed
Run app install live during image build
Change VM app deployer to run CT install scripts during image customization (virt-customize --run) instead of via a first-boot systemd service. Updated docs to reflect live installation, new update workflow (curl the ct/<app>.sh inside the VM), and new troubleshooting/reinstall guidance. misc/vm-app.func now injects function libs, runs a temporary wrapper inside virt-customize (with logging and error handling), removes the first-boot service and update wrapper injection, and updates summary/status messages to mark apps as pre-installed.
1 parent be8e448 commit ec875e6

2 files changed

Lines changed: 63 additions & 187 deletions

File tree

‎docs/vm/APP_DEPLOYER_VM.md‎

Lines changed: 30 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ Deploy LXC applications inside a full Virtual Machine instead of an LXC containe
44

55
## Overview
66

7-
The App Deployer VM bridges the gap between CT install scripts (`install/*.sh`) and VM infrastructure. It leverages the existing install scripts — originally designed for LXC containers — and runs them inside a full VM via a first-boot systemd service.
7+
The App Deployer VM bridges the gap between CT install scripts (`install/*.sh`) and VM infrastructure. It leverages the existing install scripts — originally designed for LXC containers — and runs them **live during image build** via `virt-customize --run`.
88

99
### Supported Operating Systems
1010

@@ -32,7 +32,13 @@ APP_SELECT=yamtrack bash -c "$(curl -fsSL https://git.community-scripts.org/comm
3232
### Update the application later (inside the VM)
3333

3434
```bash
35-
bash /opt/community-scripts/update-app.sh
35+
bash -c "$(curl -fsSL https://git.community-scripts.org/community-scripts/ProxmoxVED/raw/branch/main/ct/<app>.sh)"
36+
```
37+
38+
For example, to update Yamtrack:
39+
40+
```bash
41+
bash -c "$(curl -fsSL https://git.community-scripts.org/community-scripts/ProxmoxVED/raw/branch/main/ct/yamtrack.sh)"
3642
```
3743

3844
## How It Works
@@ -51,25 +57,14 @@ bash /opt/community-scripts/update-app.sh
5157
│ - Install base packages │
5258
│ - Inject install.func │
5359
│ - Inject tools.func │
54-
│ - Inject install script │
55-
│ - Create first-boot service │
56-
│ - Inject update mechanism │
60+
│ - Run install script LIVE │
61+
│ (virt-customize --run) │
62+
│ - Configure hostname & SSH │
5763
│ 6. Create VM (qm create) │
5864
│ 7. Import customized disk │
5965
│ 8. Start VM │
60-
└────────────┬────────────────────────┘
61-
│ First Boot
62-
┌────────────▼────────────────────────┐
63-
│ VM (Debian/Ubuntu) │
64-
│ │
65-
│ app-install.service (oneshot): │
66-
│ 1. Wait for network │
67-
│ 2. Set environment variables │
68-
│ (FUNCTIONS_FILE_PATH, etc.) │
69-
│ 3. Run install/<app>-install.sh │
70-
│ 4. Mark as installed │
7166
│ │
72-
│ → Application running in VM! │
67+
│ → Application pre-installed! │
7368
└─────────────────────────────────────┘
7469
```
7570

@@ -79,17 +74,17 @@ bash /opt/community-scripts/update-app.sh
7974
┌─────────────────────────────────────┐
8075
│ Inside the VM (SSH or console) │
8176
│ │
82-
│ bash /opt/community-scripts/ │
83-
│ update-app.sh │
77+
│ bash -c "$(curl -fsSL │
78+
│ $COMMUNITY_SCRIPTS_URL/ │
79+
│ ct/<app>.sh)" │
8480
│ │
85-
│ → Downloads ct/<app>.sh │
8681
│ → start() detects no pveversion │
8782
│ → Shows update/settings menu │
8883
│ → Runs update_script() │
8984
└─────────────────────────────────────┘
9085
```
9186

92-
The update mechanism reuses the existing CT script logic. Since `pveversion` is not available inside the VM, the `start()` function automatically enters the update/settings mode — the same path it takes inside LXC containers.
87+
The update mechanism reuses the existing CT script logic. Since `pveversion` is not available inside the VM, the `start()` function automatically enters the update/settings mode — exactly the same as running updates in LXC containers.
9388

9489
## Architecture
9590

@@ -106,13 +101,13 @@ The update mechanism reuses the existing CT script logic. Since `pveversion` is
106101

107102
1. **Install scripts run unmodified** — The same `install/*.sh` scripts that work in LXC containers work inside VMs. The environment (`FUNCTIONS_FILE_PATH`, exports) is replicated identically.
108103

109-
2. **Image customization via `virt-customize`** — All files are injected into the qcow2 image before the VM boots. No SSH or guest agent required during setup.
104+
2. **Image customization via `virt-customize`** — All dependencies are installed and the app install script runs live inside the qcow2 image during build. No SSH or guest agent required during setup.
110105

111-
3. **First-boot systemd service** — The install script runs automatically on first boot. Progress can be monitored via `/var/log/app-install.log`.
106+
3. **Live installation** — The install script runs during image build (not on first boot), so the application is ready immediately when the VM starts.
112107

113-
4. **Update via CT script** — The existing CT script's `start()` → `update_script()` flow works in VMs without modification.
108+
4. **Update via CT script URL** — Run the same `bash -c "$(curl ...ct/<app>.sh)"` command inside the VM, just like in an LXC container.
114109

115-
### Environment Variables (set during first-boot)
110+
### Environment Variables (set during image build)
116111

117112
| Variable | Description |
118113
| ----------------------- | ---------------------------------- |
@@ -131,43 +126,33 @@ The update mechanism reuses the existing CT script logic. Since `pveversion` is
131126
```
132127
/opt/community-scripts/
133128
├── install.func # Function library
134-
├── tools.func # Helper functions
135-
├── install/
136-
│ └── <app>-install.sh # Application install script
137-
├── ct/
138-
│ └── (downloaded on update) # CT script for updates
139-
└── update-app.sh # Update wrapper script
129+
└── tools.func # Helper functions
140130
```
141131

142132
## Limitations
143133

144134
- **Alpine-based apps**: Currently only Debian/Ubuntu VMs are supported. Alpine install scripts are not compatible.
145135
- **LXC-specific features**: Some CT features (FUSE, TUN, GPU passthrough) are configured differently in VMs.
146-
- **First-boot timing**: The app installation happens after the VM boots, so the application is not immediately available (monitor `/var/log/app-install.log`).
147136
- **`cleanup_lxc`**: This function works fine in VMs (it only cleans package caches), but the name is LXC-centric.
148137

149138
## Troubleshooting
150139

151-
### Check installation progress
140+
### Check build log
152141

153-
```bash
154-
# From inside the VM
155-
tail -f /var/log/app-install.log
142+
If the installation fails during image build, check the log on the Proxmox host:
156143

157-
# From the Proxmox host (via guest agent)
158-
qm guest exec <VMID> -- cat /var/log/app-install.log
144+
```bash
145+
cat /tmp/vm-app-install.log
159146
```
160147

161148
### Re-run installation
162149

163-
```bash
164-
# Remove the installed marker and reboot
165-
rm /root/.app-installed
166-
systemctl start app-install.service
167-
```
150+
Re-build the VM from scratch — since the app is installed during image build, there is no in-VM reinstall mechanism. Simply delete the VM and run the deployer again.
151+
152+
### Verify installation worked
168153

169-
### Check if installation completed
154+
After the VM boots, SSH in and check if the application service is running:
170155

171156
```bash
172-
test -f /root/.app-installed && echo "Installed" || echo "Not yet installed"
157+
systemctl status <app-service-name>
173158
```

0 commit comments

Comments
 (0)