printer-agent deployment guide
Turn a Linux host into a shared-printer node on the PrintHub community
printer-agent is a small Rust daemon that runs on the host sitting next to a printer. It holds a long-lived WebSocket to printhub-host, downloads the PDF when a job arrives, and submits it to the printer via IPP.
1. Architecture
Three hops make up the pipeline: the browser (Next.js frontend) → printhub-host (Go backend, auth, job scheduling, file storage) → printer-agent (Rust client) → IPP printer. The agent never opens inbound ports — it is a pure outbound client.
Browser ──HTTP──> printhub-host ──WebSocket──> printer-agent ──IPP──> Printer
│
└──Object storage (PDF jobs)──2. Prerequisites
Before you start, confirm:
- Supported distributions: Debian 11 (bullseye) / 12 (bookworm) / 13 (trixie); Ubuntu 20.04 / 22.04 LTS / 23.04+.
- A printer with IPP enabled (most Wi-Fi-enabled consumer / office printers ship with it), on the same LAN as the agent host.
- The agent host must be able to reach the printhub-host WebSocket port (443 or 80) and the printer's IPP port (default 631).
- A registration token issued by the PrintHub backend (see next section).
3. Get a registration token
Registration tokens are issued per user; one token = one printer.
- Sign in to PrintHub, then go to "Settings" → "Printers".
- On the "My printers" tab click the "Issue token" button.
- Confirm the dialog and copy the token (format: phb.<owner_uuid>.<secret>).
- ⚠️ The token is shown only once — write it to the agent's config file immediately.
Once the token is in config.toml and the agent connects for the first time, printhub-host auto-creates the printer and stores the token as key_prefix + bcrypt hash. For the full protocol details, see "Auto-registration mechanism" in the printhub-host docs.
4. Install — DEB package (recommended)
The DEB is built by Gitea Actions on every v*.*.* tag push; download it from the project's release page.
Go to https://git.duguying.net/cloudprinter/printer-agent/releases and download the latest printer-agent_<version>_amd64.deb.
Install with dpkg and auto-fix any missing dependencies:
sudo dpkg -i printer-agent_<version>_amd64.deb sudo apt-get install -f
File layout after install
/usr/local/printer-agent/bin/printer-agent /usr/local/printer-agent/bin/pdf2printable /usr/local/printer-agent/conf/config.toml /usr/bin/printer-agent (symlink) /usr/bin/pdf2printable (symlink)
5. Install — Docker
The official image is based on ubuntu:latest with WORKDIR /root/printer-agent. Mount the config directory and run detached:
Prepare the config directory
On the host, create /etc/printer-agent and drop your conf/config.toml in.
Start the container
docker run -d --name printer-agent \ --restart unless-stopped \ -v /etc/printer-agent/conf:/root/printer-agent/conf:ro \ -v /var/log/printer-agent:/root/printer-agent/log \ git.duguying.net/cloudprinter/printer-agent:latest
6. Install — build from source
For users who need custom patches or unreleased versions.
Build dependencies: Rust 1.70+, g++, libpoppler-glib-dev, libglib2.0-dev, libcairo2-dev, libjpeg-dev, libcurl4-openssl-dev, zlib1g-dev.
make build # debug build make pack # release build, output to dist/ make deb # rebuild the DEB (compiles ppm2pwg automatically)
Windows users should use the PowerShell script: powershell -ExecutionPolicy Bypass -File .\build.ps1 release
7. Install — Windows
For the graphical Windows installer, use the Windows entry (v1.0.27) inside the "Download printer-agent" dialog under "My Printers". Download printer-agent-setup-1.0.27.exe and double-click to install. This guide focuses on Linux deployment.
8. Configure conf/config.toml
All runtime behaviour is controlled by conf/config.toml. Every field is explained below.
[printer]
[printer] ipp_addr = "ipp://192.168.1.139:631/ipp/print" # IPP target; PDFs received from the host are submitted here
[remote]
[remote] addr = "wss://your-printhub-host.example.com" # required, must start with ws:// or wss:// # download_addr = "https://your-printhub-host.example.com" # optional; derived from addr if omitted
[agent]
[agent] token = "phb.<owner_uuid>.<secret>" # required, the token from section 3 # pong_timeout = 60 # heartbeat timeout in seconds, default 60 # reconnect_base_ms = 1000 # first reconnect delay in ms, default 1000 # reconnect_max_ms = 30000 # max reconnect delay in ms, default 30000
[log]
[log] path = "log/printer-agent.log" # relative to the working directory; consider a dedicated mount level = "info" # trace / debug / info / warn / error frag_size = 1024 # fragment size in KB frag_num = 10 # number of fragments to retain frag_gzip = false # gzip old fragments
9. Run as a daemon
After configuring, start the long-running process with the -d flag. Note: printer-agent has no `daemon` subcommand — use the top-level -d / --daemon flag.
printer-agent -d # equivalent: printer-agent --daemon
Use a non-default config path: printer-agent -d --config /etc/printer-agent/config.toml:
Foreground for debugging: printer-agent -d -v # also turns on verbose logs to stderr and the log file:
10. Supervise with systemd
The DEB package does not ship a systemd unit. Save the content below as /etc/systemd/system/printer-agent.service, then enable it:
[Unit] Description=PrintHub printer-agent After=network-online.target Wants=network-online.target [Service] Type=simple User=printer-agent Group=printer-agent ExecStart=/usr/local/printer-agent/bin/printer-agent -d --config /usr/local/printer-agent/conf/config.toml Restart=always RestartSec=5 # Hardening NoNewPrivileges=true ProtectSystem=strict ProtectHome=true PrivateTmp=true ReadWritePaths=/var/log/printer-agent /usr/local/printer-agent/log [Install] WantedBy=multi-user.target
sudo systemctl daemon-reload sudo systemctl enable --now printer-agent sudo systemctl status printer-agent
11. Verify & troubleshoot
After startup, check in this order:
- log/printer-agent.log should show "start daemon", "WebSocket connected", and "identify → status=online" lines.
- On printhub-host, "My printers" should show the device as "Online".
- Locally run printer-agent --show-printer; it should return IPP attributes, proving the printer is reachable.
- Submit a test job and watch its status in "Print records" go pending → printing → done.
Common issues
- 401 immediately on startup: check that the [agent].token in config.toml has no surrounding whitespace and that all three phb.<owner>.<secret> segments are present.
- Reconnect loop, never registers: the owner may have been deleted, or the token has been revoked. Re-issue under "My printers".
- Jobs reach the agent but fail at IPP: first run printer-agent --show-printer to verify reachability; check whether UDP/TCP 631 is open.
- Downloaded job file starts with { or [: the file is broken or the download URL is stale. Re-submit from the UI; the agent logs the first 256 bytes to help diagnosis.
- Log says "download_url is empty": printhub-host cannot find a token for this printer. Run printhub-host regenerate-printer-token <printer_id> to re-issue.
12. Uninstall & upgrade
- DEB: sudo dpkg -r printer-agent — also removes the /usr/bin symlinks.
- Docker: docker rm -f printer-agent; docker image rm for the image if no longer needed.
- Source: delete the build artifacts (dist/, target/) and the binary.
- Before upgrading, stop the service (systemctl stop printer-agent or docker stop printer-agent), replace the binary, then start. The config file can usually be reused across minor versions.
13. Protocol reference
Agent and host communicate via a JSON envelope, protocol version 1.0. See sections 8 and 9 of printhub-host's docs/AGENT_REGISTRATION.md for the full frame types, field semantics, and security considerations.