I, Mircea Anton, will participate in the next Devember. My Devember project will be “PiPDU”. I promise I will program for my Devember for at least an hour, every day of the next December. I will also write a daily weekly public devlog and will make the produced code publicly available on the internet. No matter what, I will keep my promise.
If the name is not suggestive enough, piPDU is a smart PDU, powered by Raspberry Pi and Arduino. I intend to build it and mount it in my Home Lab rack.
This project is basically going to dust off my Arduino/Raspberry skills which I haven’t really been using lately and hopefully get a usable product by the end of it!
Some rough requirements for this project are
the pdu itself to function as a plain old power strip if anything goes wrong
the pdu should have an API server to control each socket individually
the pdu should expose metrics in a prometheus endpoint for each socket
the controller should have 16 buttons, one to control each socket
the controller should have 16 leds to indicate the on/off status of the sockets
the controller should have an LCD display to show stats for the sockets
I want the controller and the PDU itself to be separate entities in a client-server relationship so that i can eventually expand this and maybe make a discord bot or mobile app or whatever else to control the pdu as well.
I did not know initially if devember was going to happen or not, so i started the blog post series on my own website as well. I think I will run these 2 in parallel.
Link to my website here
i had my CKAD exam so i did not get around to work today. Just like last week, i decided to take the rest of the day off to decompress
Tuesday
today I refactored some of the code for the controller into “arduino-style” functions, basically implementing a setup function and then a loop function that, as you might have guessed, loops indefinitely
I set up some functions to initialize the LEDs and the boilerplate for led updates
I set up the metrics singleton class to collect and cache metrics from the prometheus endpoint exposed by the server
Implemented singleton class to abstract away the button matrix, handling the long and short presses
Wednesday
today I was very sick, to the point that i couldn’t really get out of bed to do anything at all
Thursday
today i managed to get some coding done.
I worked on the controller code and I implemented the actual api calls for the long and short button presses
I implemented the LCD states to show both the overall power consumption during idle as well as per-socket power consumption when a button has been pressed
I implemented the led_array update function to turn leds on/off based on socket status
Friday
today i was unable to get any work done on the pipdu project as life managed to get in the way
Saturday
today i managed to get a tiny bit of work done.
i desoldered the screw terminals from my previous attempt of a protoboard in order to reuse them for the custom pcb i am working on
i tried to do some more troubleshooting by fixing errors reported by kicad on my pcb
Sunday
i was pretty behind on my CKS study for my exam tomorrow, so I decided to dedicate this day to studying only
Can’t immediately tell from the blog or the repo, what hardware are you using for the current/power measurements and are you using any external pin controller/pin muxer. (looked from my phone while on the go and couldn’t find a pdf or something I could open easily).
I was imagining how something like this might use esphome on esp32 with a bunch of mcp23017 daisy chained on i2c, or maybe even a pca9685 if you want to pwm the LEDs on the buttons.
Hello, @risk ! Thanks for your interest in the project!
Yeah, I did not spend too much effort on documentation yet. I hope to do that in the coming weeks this month, as I flush things out more.
So the way things are set up right now is that I have 16 ACS 715 Hall Current Sensors wired in alongside the 16 relay board in order to measure the current.
These sensors, alongside the relays themselves are then controlled by an Arduino Mega. The Arduino then in turn communicates via i2c with the Pi zero to complete the circuit. Basically, the Arduino interacts with the hardware itself and the Raspberry simply hosts the API server and communicates with the Arduino.
Now, it would have probably been a better design to get some I2C GPIO expanders and I2C ADCs and use those instead of the Arduino Mega, but I had that lying around so I tried to use as much of the parts I already had as I could.
For the buttons and LEDs, I am using a Pi zero again. It has just enough pins so that I can individually address the LEDs and use the buttons as an 8x2 matrix. The LCD in the controller is communicating over an I2C bus.
(tried to) print and etch the PCB v1 for the controller but it turned out bad
updated the controller PCB to version v1.1 to use 2mm tracks and larger viases to maybe have better results when etching
Tue
Created a circuit schematic for the server PCB to get an idea of the components and connections required;
Considered getting an I2C ADC for the Pi but I soon dropped the idea, mainly due to cost considerations, since I already had the Arduino Mega and even so, getting enough analog channels would be more expensive via ADC boards than by using an Arduino as an ADC
Wed
worked with dad to create a PCB for the pipdu server to connect all the current sensors by manually drawing with a paint marker
brainstormed and came with a layout for the components inside the server case
updated the PCB for the controller to v2 to use GPIO expanders for a much much simpler design
Thu
etched the server PCB and drilled some of the holes
cut the hole for the power socket in the controller case
Fri
N/A, had to take care of some university assignments
Sat
printed the controller PCB v2
etched the controller PCB v2 → turned out great, actually!
drilled the hole for the rj45 module in the back panel of the controller case
drilled the server PCB pin-holes
Sun
worked with dad on the server case:
cut the new front panel from a 3mm sheet of metal
cut the case into pieces
drilled the holes for the power plugs and mounting screws
As a final update, I unfortunately did not manage to accomplish all I set out to on time, as I still have to do the final assembly for the server case. That being said, I did make a lot of progress on this project and I am happy with it nonetheless.
I would like to thank the L1T community and team for setting up this challenge and would like to take this time to share my achievements for my Devember 2022:
Got my CKA certification in the 1st week of December
Got the CKAD certifications in the 2nd week of December
Got the CKS certifications in the 3rd week of December
Completed the PiPDU Controller (HW + SW)
Got ~85% done with the PiPDU Server (HW and SW)
Accomplished my goal of posting more on my personal blog and honestly I also improved it a lot. I started with no blog posts and I am currently at like 13. I improved the look and feel of my site since this challenge has started and I got it to a point I am quite happy with it.
To be fully honest, I could have probably finished this if i was more careful and didn’t spread myself too thin by setting too many goals, but I am always saying that it is better to aim for the stars and miss, as you will have gotten much further compared to aiming low and making it!
Overall, I am calling this Devember challenge a win! I hope you’ll tag along as I continue to work on this PiPDU project as I already have bigger plans for the v2, even if v1 is not really done yet Expect another post on my blog sometime in the next couple weeks about that!
To wrap things up, I want to outline what has been accomplished and what is left to do for this devember challenge, based on the initial plan:
Done:
Controller HW:
Designed custom PCB
Printed custom PCB at home
Modded a 2U case to fit all of the components
Assembled and wired all of the components into the case
Controller SW:
basic python client for the PiPDU server
LCD to display stats about the PDU (total power consumption, total Amps)
single button press to toggle the LCD from showing general pdu info to specific socket info
long button press to toggle the state of a relay (as well as the configured hooks)
LEDs to indicate the status of each relay
Server HW:
built a custom PCB for the current sensors
HEAVILY modded a 5U case that was meant for batteries in order to fit the components inside it. And I mean HEAVILY. We literally cut every panel off the case, replaced the front panel, redesigned the case closing system and cut a crap-ton of holes into it. I think it would have been easier to just make a new one but ohwell
Assembled and wired the components into the case (sans wiring the sockets into the relays yet)
Server SW:
set up a basic Flask API to handle the state of the relays by sending requests to the /api/v1/socket/<id>/{on/off} as well as socket status on /api/v1/socket/<id>/status
set up a Prometheus monitoring endpoint to expose the values collected by the sensors for each relay to easily integrate into Grafana
added functionality to trigger pre/post power on/off hooks. For example, sending a shutdown command to a Pi before turning off the socket or sending a notification to a discord channel after a socket has been turned on
YAML config for setting up names for the sockets and configuring the hooks
To Do:
Controller HW: N/A
Controller SW: some final testing once the server is also up and running
Server HW:
wire all of the power sockets into the terminal strips
final assembly
Server SW:
final testing once everything is assembled
“calibration” for the current sensors
Documentation: all of it, LOL
Frankly, depending on how long they take to rate the projects and pick a winner, I think I might be able to finish this, as there is very little left to do!