Repository navigation
v2.9.0
ser2net 2.9.0 fixes the remaining problems found in 2.8.0 (issues #48–#90) and adds the features that came with them. Several fixes change behaviour on purpose: read Before you upgrade first.
- Two-factor sign-in (TOTP) and named REST API tokens with their own role and expiry;
PATCH, a bulk import and token-protected metrics in the REST API. config.jsonreloads without a restart (systemctl reload ser2net,ser2net --reload), and so do admin TLS certificates.- Reverse proxies (trusted proxies, a public URL, serving under a path) and several instances on one machine.
- Modbus RTU replies framed reliably on USB adapters and Windows; 64-bit, float64, string and bit points, word order, block reads, a unit map, unit health with Sparkplug B DDEATH; MQTT with a private CA and client certificates.
- The right adapter among identical USB adapters, listeners for IPv4 and IPv6 at once, telnet BREAK, UDP targets; retention and privacy controls; an event loop watchdog.
- A Docker image for 32-bit ARM,
ser2net-install.shto run a Linux executable as a systemd service, and new guides: Modbus and MQTT, moving from the classic ser2net, single sign-on, Linux serial ports.
Before you upgrade
config.json and data/ are used as they are, and the start-up log notes each stored value that 2.9.0 reads differently. Check what applies to you (coming from 2.8.0 or older, read the 2.8.1 notes too):
- Reverse proxy on the same machine: list it as
127.0.0.1under Settings → Reverse proxy → Trusted proxies, or every user shows as 127.0.0.1 and all share one sign-in limit. A plain-HTTP proxy that rewritesHostmust passX-Forwarded-Host, or forms get 403. See docs/REVERSE-PROXY.md. - Stricter checks when a mapping is saved (also on import and for the mappings a reload changes): two enabled mappings sharing MQTT command topics (
/set,/tx), a client ID or a Sparkplug B edge node, MQTT wildcards in a plain base topic, one serial port under two spellings, the admin UI's port, TLS files that don't load (a disabled mapping's too), Modbus point values of the wrong type and text for protective or only-true switches are refused, and a disabled mapping that would clash on MQTT can't be started. Stored mappings still load, with a note at start-up, but their next edit must fix them. - Text values in
config.jsonare read as their setting's type: numeric text is converted,"enabled": "false"leaves a mapping stopped,"writable": "false"makes a point read-only. Switches that turn something on only for JSONtrue(MQTTtx_enabled,poll_with_clients,proxy_hsts,dual_stack, …) read text as off; protective ones (read_only,tls,require_login,mask_personal_data, MQTTtls_check_hostname, …) read it as on. An allow-list with no usable entry admits nobody instead of everyone. The start-up log notes each case. - Modbus gateway: a reply must match its request, so slaves that miscount, don't echo FC5/FC6 exactly or answer reads of unit 0 get exception 0x0B; a broadcast write to unit 0 is answered with its echo, and a read of unit 0 gets 0x0B at once.
- Start no longer restarts a running mapping: scripts must use
restart. - A mapping listens before it opens its device, so a taken port fails without touching the device; a client can connect a moment earlier than before, and what it sends before the device is open is dropped.
- A telnet BREAK now reaches the device (0.25 s; not on read-only mappings).
- TLS mappings: connect-out TLS presents its configured certificate and key; an encrypted key needs its key password set, as it no longer asks at the console.
- SIGHUP reloads
config.jsoninstead of stopping ser2net (a reload is checked like an edit);kick_old_userno longer evicts priority clients. - Classic ser2net imports go through the preview only; merging a file again keeps what was set up here;
ipv6n4accepters listen on IPv4 and IPv6; port locking comes along. - Sign-in: 10 failures in 15 minutes give that user name HTTP 429 until they expire. Accounts get stronger password hashes at their next sign-in, which 2.8.1 and older can't read: after going back to 2.8.1, set a new password there (
ser2net --set-password NAME; on 2.8.0 and older, restore aconfig.jsonfrombackups/made before the upgrade). - New defaults: the event loop watchdog (90 s, then
data/hang.logand exit code 70;SER2NET_LOOP_WATCHDOG=0turns it off); traces pause below 256 MB free; new log and trace files are owner-only;::takes IPv6 only (All interfaces (IPv4 + IPv6) takes both); the first start deletes trace files of mappings that no longer exist. - systemd: copy the new
systemd/ser2net.serviceto/etc/systemd/system/and runsystemctl daemon-reload;systemctl reloadnow works with all three units (ser2net@.serviceandser2net-standalone.serviceare new). Instances ofser2net@.serviceshare onelib/: runsudo -u ser2net python3 /opt/ser2net/bootstrap.pyafter each upgrade. - Scripts: Settings forms answer 303 / 400 (follow redirects with the cookie jar to read a new token), and a save that switches admin TLS on or off answers 200 with the page; a dashboard bulk action that can't change a mapping answers 400 with the reasons, after doing the others; a page without a session redirects to
/login?next=<page>; REST errors are JSON (400 validation,500 save_failed); log times carry a UTC offset and IPv6 peers are bracketed; cookies on ports other than 8080 and over HTTPS have new names. - MQTT / Sparkplug B consumers:
.../set/resultcomes at QoS 1 with new error texts; Sparkplug B sends a DDEATH for a unit that stops answering andbdSeqas Int64. - LAN cluster: mixed versions work, and an older node's edit form offers only the settings it keeps, but upgrade every node (Upgrading a cluster).
- Windows: serial writes are paced to the line; if a virtual COM driver misbehaves,
SER2NET_WINDOWS_SERIAL=pyserialrestores the old write path. - Going back to 2.8.x: copy
data/first; older versions drop named API tokens, two-factor sign-in,dual_stackand the new TLS checks (README → Going back to an older version); put back that version's systemd unit, as 2.9'sExecReloadwould end it, and removenotify.conf.
How to upgrade
- Standalone executable (Linux): replace the file and restart ser2net, or install or upgrade it as a systemd service with
ser2net-install.sh(run it again to upgrade;--uninstallkeeps the data). - Windows service: run the new
ser2net-windows-x64.exe --install-servicefrom an elevated prompt. It upgrades the service in place, keeping its data directory, and now reports an error if the service doesn't start. - Docker:
docker pull ghcr.io/haliskilic/ser2net:2.9.0and recreate the container; addinit: trueandstop_grace_period: 30sto your compose file, as the shipped one has. - Source install: update the files and restart; the first start refreshes
lib/fromvendor/wheelsby itself, offline (all.log says what to run if it can't). Under systemd, copy the new unit first; forser2net@.serviceinstances, runbootstrap.pyas above.
Everything, with the upgrade notes in full: CHANGELOG.md.
Assets
| File | |
|---|---|
ser2net-linux-x64 |
Linux x86_64 executable (glibc ≥ 2.28) |
ser2net-linux-arm64 |
Linux arm64 executable (glibc ≥ 2.28; Raspberry Pi 3/4/5 with a 64-bit OS) |
ser2net-windows-x64.exe |
Windows x64 executable; --install-service runs it as a service |
ser2net-install.sh |
installs a Linux executable as a systemd service, checked against SHA256SUMS |
ser2net-standalone.service |
systemd unit for the Linux executables (data in /var/lib/ser2net) |
*.cdx.json |
CycloneDX SBOM of each executable |
*.THIRD-PARTY-LICENSES.txt |
license texts of the components inside each executable |
SHA256SUMS |
SHA-256 checksums of all of the above |
Docker image: ghcr.io/haliskilic/ser2net:2.9.0 (also 2.9 and latest), linux/amd64, linux/arm64 and linux/arm/v7. 2.9 and latest are rebuilt weekly when the Debian/Python base image changes; 2.9.0 stays the image this release published.
Verify a download: sha256sum -c SHA256SUMS --ignore-missing, and the build provenance with gh attestation verify ser2net-linux-x64 -R haliskilic/ser2net (add --signer-workflow haliskilic/ser2net/.github/workflows/release.yml to require the release workflow; each executable also has an SBOM attestation; the image: gh attestation verify oci://ghcr.io/haliskilic/ser2net:2.9.0 -R haliskilic/ser2net, while a weekly rebuild of 2.9 / latest is attested by image-refresh.yml). The Windows executable is not code-signed yet, so SmartScreen may warn; check it the same way (docs/WINDOWS.md).