PVE 9.2.3 sets APIVER=15 in PVE::Storage. Our plugin was returning 14,
triggering "implementing an older storage API" on every pvedaemon/pveproxy
restart. No functional change — plugin loaded and worked correctly at 14.
Closes#282
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
dists/error was never written to gh-pages because the codename alias
code was added after the v3.2.0 tag. The stable publish job only runs
on v*.*.* tags, so all subsequent pushes to release/3.x only touched
dists/testing. Bumping to v3.2.1 triggers stable publish to create it.
Also fix: cp -r src dst when dst already exists puts src inside dst
rather than replacing it. Add rm -rf before cp -r to guarantee a clean
replace on every stable release.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
If /etc/multipath.conf already had a manual devices{} block before package
install, postinst would append a second identical block, causing multipathd
to emit "duplicate keyword: devices" warnings. Strip any unmanaged devices
block in the append path to keep the file clean.
Fixes#279. Discovered 2026-06-20 on pve01-hq during SCALE 25.04 multipath testing.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Without a registered JS panel the truenas-multipath type was invisible in
the PVE Datacenter → Storage → Add dropdown. Adds truenas-multipath.js
with all base TrueNAS fields plus the required truenas_portals field, and
wires it into the multipath package install/remove scripts and CI build.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
On install: if /etc/multipath.conf already exists, append a tagged
block rather than skipping silently (old) or overwriting (dangerous).
On upgrade: replace only the tagged block, leaving the rest untouched.
On remove/purge: strip the tagged block; rest of the file preserved.
This means admins who added their own stanzas during manual testing
(e.g. before the package existed) won't lose config on install or
upgrade. Closes the silent "file already exists" footgun.
Also fixes pre-existing SC2015 shellcheck warnings in postrm.
Refs #256
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Adds TrueNASMultipath.pm — a separate PVE storage type 'truenas-multipath'
that inherits all REST API and iSCSI resource management from TrueNAS.pm but
uses iscsiadm + dm-multipath for block device access:
path() → /dev/mapper/<wwid> (NAA from TrueNAS extent)
activate_volume() → iscsiadm login on each portal in truenas_portals;
waits for /dev/mapper device to appear
deactivate_volume()→ multipath flush + iscsiadm logout
qemu_blockdev_options → returns undef (path() used instead)
Packaging:
packaging/DEBIAN-multipath/ — control.j2, postinst, postrm,
changelog.Debian, multipath.conf.example
Distributed via the 'multipath' apt component (ADR-011)
Depends: truenas-proxmox >= 3.1.0, open-iscsi, multipath-tools
CI (build.yml):
- Third staging dir (dist-multipath) and .deb output
- multipath component pool under pool/multipath/v<major>
- Both stable and testing publish steps updated to generate
main + multipath components; Release lists both
- Lint checks TrueNASMultipath.pm and multipath packaging scripts
PoC confirmed 2026-06-07 on pve01-hq against TrueNAS SCALE 24.10:
- Two sessions (172.31.69.91 + 192.168.69.91), both active
- dm-multipath aggregated 3 disks × 2 paths each
- /dev/mapper/mpath* devices appeared correctly
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Adds packaging/changelog.Debian and packaging/DEBIAN-transitional/changelog.Debian
and wires them into the build staging steps. The gzipped changelog lands at
/usr/share/doc/truenas-proxmox/changelog.Debian.gz and
/usr/share/doc/freenas-proxmox/changelog.Debian.gz respectively, satisfying
Debian policy §12.7 and silencing the 'apt changelog' failure.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Introduces truenas-proxmox as the real package and freenas-proxmox as a
transitional meta-package that Depends on truenas-proxmox. Existing
users running apt upgrade automatically pull in the new package; the
migration one-liner (apt install truenas-proxmox && apt purge
freenas-proxmox) completes the transition. The freenas-proxmox package
name will not exist in v4.0.
Changes:
- packaging/DEBIAN/: Package renamed to truenas-proxmox, INSTALL_DIR
and LOG_FILE updated to /usr/share/truenas-proxmox and
/var/log/truenas-proxmox-install.log; Replaces/Breaks fields added
- packaging/DEBIAN-transitional/: new empty meta-package that pulls in
truenas-proxmox and prints a deprecation notice on configure
- build.yml: PACKAGE_NAME=truenas-proxmox; both debs built and
published to Cloudsmith; transitional postinst added to shellcheck
- All GitHub repo URLs updated to TheGrandWazoo/truenas-proxmox
- apt install/remove/purge commands in docs updated to truenas-proxmox
- GitHub repo rename to truenas-proxmox pending (gh repo rename step)
Closes#262
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Inject pveOnlineHelpInfo entry in truenas-storage.js so PVE wires
the Help button automatically via the StorageBase framework
- Add onlineHelp: 'storage_truenas' to the input panel definition
- Add ui/truenas-storage-help.html — local help page installed to
/usr/share/pve-docs/truenas-storage.html (no internet required)
- Add docs/getting-started.md and docs/architecture.md
- Update postinst/postrm to install and remove the help HTML file
- Update build.yml to include the help HTML in the package staging dir
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Instead of diffing and patching the 50k-line pvemanagerlib.js each PVE
release, we ship truenas-storage.js as our own file and inject one
<script> line into index.html.tpl (rarely changes, ~60 lines).
truenas-storage.js adds 'truenas' to PVE.Utils.storageSchema at runtime
and defines PVE.storage.TrueNASInputPanel with all config fields:
- TrueNAS host, API key, pool, dataset (column 1)
- SSL toggle, cert verify, portal IP, target IQN (column 2)
API key field: required on create, optional on edit (only submitted if
the user types a new value).
postinst: copies TrueNAS.pm + truenas-storage.js, adds script tag
postrm: removes both files, strips script tag
Closes#225 (core interface), #226 (iSCSI lifecycle activate/deactivate),
#227 (API pool listing replaces SSH).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Two install-time failures on PVE 8.4.x nodes:
1. 'patch' utility not in Depends — causes silent patch failure on fresh
nodes; all three PVE file patches silently skip, plugin appears to
install but storage operations fail. Added 'patch' to control.j2.
2. ZFSPlugin.pm routing not applied on PVE 8.4.x — tabs→spaces reformat
and get_base($scfg) signature change in 8.4 broke hunks #3 and #4
(the freenas elsif routing branches). Nodes with a prior partial
install are doubly affected: grep idempotency check passes on partial
freenas strings, so the routing is never applied, causing:
"freenas: unknown iscsi provider" on clone/migrate operations.
New ZFSPlugin-8.4.14_1.pm.patch generated against stock PVE 8.4.19,
bundled as patches/ZFSPlugin/8.4.patch alongside existing 8.patch.
Verified clean on pve01-hq (8.4.19) and pve02-hq (8.4.14).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Users on unsupported PVE versions now get clear guidance at every
layer — README, install time, and GitHub release notes — rather than
silently failing or getting confusing patch errors.
- README: replace bare compatibility table with a full matrix and
prominent callout blocks for PVE 7 (last v2.x), PVE 8 (EOL
2026-08-31), PVE 9+ (use v3.0), and PVE ≤6 (unsupported)
- postinst: add check_pve_version() that exits on PVE < 7, warns
loudly on PVE 7 (stay on v2.x, do not upgrade to v3.0), notes
the PVE 8 EOL date, and warns on PVE 9+ (v2.x not supported)
- build.yml release template: add a version compatibility table so
every GitHub release prominently states who should and should not
install it
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
PVE 8.4 reformatted pvemanagerlib.js (tabs→spaces, structural changes),
making the existing 8.0.5-era patch fail on all 8.4.x nodes.
- Add pvemanagerlib-8.4.14_1.js.patch covering PVE 8.4.x (all hunks
verified on 8.4.14 and 8.4.19)
- Update postinst to detect pve-manager major.minor (e.g. "8.4") and
try a minor-version-specific patch before falling back to the major
patch — 8.3.x nodes keep using 8.patch, 8.4.x nodes use 8.4.patch
- Update build.yml to bundle 8.4.patch alongside the existing 8.patch
Tested live on pve01-hq (8.4.19) and pve03-hq (8.3.2) — correct patch
selected in each case, pvemanagerlib patched successfully on 8.4.19.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
dpkg-deb --build reads a binary control file and rejects the two-stanza
source+binary format. Rewrote control.j2 as a single binary-only stanza.
Removed the source stanza (Source, Standards-Version, Build-Depends fields)
which are only meaningful in source packages built with dpkg-buildpackage.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
REST_CLIENT_PATH was defined but never referenced. REST/Client.pm is owned
by librest-client-perl and is intentionally not removed by our postrm
(documented in the comment above remove_plugin_files). Remove the dead variable.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>