product_version is used as model only when it contains a space, indicating
a human-readable marketing name (e.g. "ThinkCentre M910x"). Part numbers
like "J26843-409" have no space and are skipped — product_name is used
instead (e.g. "NUC6CAYH" for Intel NUC).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
The combined printf approach silently produced empty values when
product_name/version contained special chars or the shell split tokens
incorrectly. Read each /sys/class/dmi/id/ file via a separate cat,
collect lines, then apply vendor-specific model name selection:
- Intel NUC: product_name='NUC6CAYH' (marketing) preferred over
product_version='J26843-409' (part number)
- Lenovo: product_name='10MYS03U00' (type code, all-caps+digits) →
prefer product_version='ThinkCentre M910x' (marketing name)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
On Lenovo (and some other vendors) product_name contains the machine-type
code (e.g. "10MYS03U00") while product_version holds the marketing name
(e.g. "ThinkCentre M910x"). Read both and prefer product_version when it
is set and different from product_name.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
vendor, model and serial_number now come from /sys/class/dmi/id/
(sys_vendor, product_name, product_serial) via SSH, reflecting the
actual physical server rather than the Proxmox software layer.
Falls back to "Proxmox Server Solutions GmbH" / status.model if SSH
or DMI files are unavailable (e.g. bare-metal without SSH creds).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Implements set_hostname on ProxmoxSystemMixin:
1. Writes /etc/hostname (short name, base64-safe transfer)
2. Replaces old hostname in /etc/hosts via Python regex + base64
3. Updates /etc/mailname if present
4. Updates Postfix myhostname via postconf -e if installed
5. Applies hostname immediately at runtime via hostname(1)
6. Regenerates Proxmox node TLS certificate via pvecm updatecerts -f
(falls back to pvenode cert create → pveproxy restart)
Accepts bare hostname or FQDN. A reboot is required for the Proxmox
node name to update in the web UI / cluster — the driver logs this.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
get_vlans() previously parsed 'bridge vlan show' which trunks all 4094
VIDs by default on VLAN-aware bridges, producing phantom VLAN entries.
Now derives real VLAN assignments from VM/container netN bridge=,tag=
config. get_device_warnings() now reports updates_available with
severity "warning" and a full package list/title, matching the format
used when the warning is refreshed via the updates API (previously
alternated between "info" and "warning" for the same content).
get_device_warnings() now reports lldpd_not_installed (action
install_lldpd) when lldpd is absent, matching the existing
OpenWrt pattern. run_device_action("install_lldpd") installs and
enables lldpd via apt/systemd so LLDP topology links to directly
connected switches can be discovered.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Mirrors the robust fallback pattern from napalm-opnsense so the driver
works regardless of which key name the caller passes in optional_args.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>