
APC UPS
We have a large UPS for the NOC team, and we should monitor it appropriately.
It has a non-standard serial connector, and the plan is to connect it to a raspberry pi, add some exporter and maybe alerting also.
UPS and cable
It is an APC smart UPS 2200INET
Yes, it is old, but batteries has been replaced recently, so we continue to use it.
The serial connector must be wired in a non-default way. Source 1 and source 2 both agree
I didn’t succeed with connecting with minicom using “2400 8N1 SW flow control”, but with the correct settings, apcupsd
was able to connect.
We followed this guide, which boils down to installing apcupsd
and change two things in the config files. Remeber to restart service apcupsd restart
.
Working config is as follows
➜ grep -v -e '^#' -e '^$' /etc/default/apcupsd
ISCONFIGURED=yes
➜ grep -v -e '^#' -e '^$' /etc/apcupsd/apcupsd.conf
UPSCABLE 940-1524C
UPSTYPE apcsmart
DEVICE /dev/ttyUSB0
LOCKFILE /var/lock
SCRIPTDIR /etc/apcupsd
PWRFAILDIR /etc/apcupsd
NOLOGINDIR /etc
ONBATTERYDELAY 6
BATTERYLEVEL 5
MINUTES 3
TIMEOUT 0
ANNOY 300
ANNOYDELAY 60
NOLOGON disable
KILLDELAY 0
NETSERVER on
NISIP 127.0.0.1
NISPORT 3551
EVENTSFILE /var/log/apcupsd.events
EVENTSFILEMAX 10
UPSCLASS standalone
UPSMODE disable
STATTIME 0
STATFILE /var/log/apcupsd.status
LOGSTATS off
DATATIME 0
The only change I made is the UPSABLE
, UPSTYPE
and DEVICE
. The NIS
-stuff looks like a candidate for something to be disabled.
Use apcaccess
to verify the connection
sysuser@upsmon:~ $ sudo apcaccess
APC : 001,048,1017
DATE : 2025-06-09 20:37:55 +0100
HOSTNAME : upsmon
VERSION : 3.14.14 (31 May 2016) debian
CABLE : Custom Cable Smart
DRIVER : APC Smart UPS (any)
UPSMODE : Stand Alone
STARTTIME: 2025-06-09 20:37:47 +0100
MODEL :
STATUS : ONLINE REPLACEBATT
LINEV : 0.0 Volts
LOADPCT : 0.0 Percent
BCHARGE : 0.0 Percent
TIMELEFT : 0.0 Minutes
MBATTCHG : 5 Percent
MINTIMEL : 3 Minutes
MAXTIME : 0 Seconds
MAXLINEV : 0.0 Volts
MINLINEV : 0.0 Volts
OUTPUTV : 0.0 Volts
SENSE : Unknown
DWAKE : -1 Seconds
DSHUTD : -1 Seconds
DLOWBATT : -1 Minutes
LOTRANS : -1.0 Volts
HITRANS : -1.0 Volts
RETPCT : -1.0 Percent
ITEMP : 0.0 C
ALARMDEL : Always
BATTV : 0.0 Volts
LINEFREQ : 0.0 Hz
NUMXFERS : 0
TONBATT : 0 Seconds
CUMONBATT: 0 Seconds
XOFFBATT : N/A
STESTI : -1
STATFLAG : 0x05000088
DIPSW : 0x00
REG1 : 0x00
REG2 : 0x00
REG3 : 0x00
MANDATE :
SERIALNO :
BATTDATE :
NOMOUTV : -1 Volts
NOMBATTV : 0.0 Volts
EXTBATTS : 0
FIRMWARE :
END APC : 2025-06-09 20:37:55 +0100
To avoid the host with apcupsd to shutdown when the UPS runs out of power, add the doshutdown
file
sysuser@upsmon:/etc/apcupsd $ cat /etc/apcupsd/doshutdown
#!/usr/bin/env bash
logger "apcupsd requested shudown. But it is ignored but ignored by '$0'"
exit 99
Exporting values
Apparently someone has already made an exporter and the associated grafana dashboard is here. Nice.
The installer is made in go - how does that work with raspberry? Much the same apparently…. We install go following the pimylife guide
sysuser@upsmon:~ $ dpkg-architecture | grep BITS
DEB_BUILD_ARCH_BITS=32
DEB_HOST_ARCH_BITS=32
DEB_TARGET_ARCH_BITS=32
Ok, we install the 32 bit version of go.
Download and extract, update .bashrc and source it.
sysuser@upsmon:~ $ go version
go version go1.24.4 linux/arm
Looks ok.
Git pull acpupsd_exporter, build it and activate.
Add to prometheus and grafana dashboard.
Make it persistent by adding a systemd service
sysuser@upsmon:~ $ cat /lib/systemd/system/apcupsd_exporter.service
[Unit]
Description=Prometheus exporter for apcupsd
After=network.target
[Service]
Type=simple
User=sysuser
WorkingDirectory=/home/sysuser/apcupsd_exporter/cmd/apcupsd_exporter/
ExecStart=/home/sysuser/apcupsd_exporter/cmd/apcupsd_exporter/apcupsd_exporter
Restart=on-failure
[Install]
WantedBy=multi-user.target
and do daemon reload (systemctl daemon-reload
) and enable it (systemctl enable --now apcupsd_exporter.service
).
Just to reiterate, I am just following the guide mentioned above.
Verify that it is working by getting the data curl localhost:9162/metrics
.
Bootnore
- It is really cool that people make these things and share them
- I really ought to get better at handling go, so I don’t have to have entire build chains lying around and sources to. It would be noce to just build the binary and copy it.
- “Time remaining” estimates are completely way off. Also, when testing the UPS was working for 15 minutes with 0% battery.