I need to make up one of these Home Assistant "Glow" interfaces.
These damned "smart" electricity meters aren't massively smart, so I'm not about to get one of them fitted. I'm currently with Outfox for both gas and electricity and will be until the current contract expires in several months time. On the other hand, Octopus Energy seem to have a good reputation when it comes to integrating with Home Assistant, as they expose their API. But for the time being, I'm not about to have one of Outfox's contractors rip out the existing meter(s) and fit a semi-smart meter if I'm going to have Octopus a few months later, doubtless of a different and possibly incompatible brand.
Most modern "dumb" meters have a little LED that blinks once every time a unit of energy is used. In this instance, it's one blink for every Wh (Watt hour) ie 1000 blinks per kWh. It's the left hand of those 2 sensors in the middle of the circular depression. I believe the other is a receiver that can be used by the utility company for doing stuff like reflashing the meter.
So this "Glow" interface simply registers each blink with a photo diode and uses an ESP32 to send the data back to your Home Assistant over the network using its built-in wifi. It's a sort of "stop-gap DIY smart meter".
There's a printable case linked on the website but it's for the full sizes ESP32, not the "Super Mini" (thumbnail sized) ones that are actually linked in the article or indeed the ones I have to hand. Here's the one I printed a few weeks ago when I ordered the parts from Aliexpress:
There are also some crude enclosures shown in Grabcad etc but they aren't what I want. For one thing, I'd like to integrate them into one assembly, not have 2 small housings flailing around for no reason.
The connection diagram for the various elements gives you an idea what's involved.
So, it seems there's nothing I can simply download and print out. We've been here before, I think. But... what better than to get my new mate Claude Code to flash something up? I started out with Google AI before opting to go the whole hog and get Claude Code to directly drive Fusion.
The MD file ended up looking like this, once I'd clarified the requirements:
# Task: Generate an Autodesk Fusion 360 Python Add-In / Script for an All-in-One Home Assistant Glow Enclosure
Write a complete, self-contained Autodesk Fusion 360 Python script (`adsk.core`, `adsk.fusion`) that parametrically generates a two-part 3D-printable enclosure (**Base** and **Snap-Fit Lid**) for an **ESP32-C3 Super Mini** + **LM393 Photodiode Sensor Module** + **5mm RGB Status LED**, designed to mount flat onto a UK **Ampy 5235A** single-phase electricity meter.
## 1. Coordinate System & Orientation
- **Units:** Millimeters (`mm`)
- **XY Plane (`Z = 0`):** Bottom exterior face of the Base (the flat surface that sticks to the electricity meter).
- **+Z Direction:** Outward away from the meter face (towards the lid).
- **+X Direction:** Right across the meter face.
- **+Y Direction:** Upward towards the top of the meter (`-Y` is downward towards the meter tails/cables).
## 2. User Parameters (Create as Fusion 360 `UserParameters` for easy tweaking)
Define all critical dimensions as Fusion 360 User Parameters at the start of the script:
- `wall_thick = 2.0` mm (Outer perimeter and floor/lid thickness)
- `inner_w = 42.0` mm (Total internal X width)
- `inner_h = 52.0` mm (Total internal Y height)
- `inner_d = 23.0` mm (Internal Z depth from floor top to lid bottom — must clear pre-soldered headers + female DuPont jumper plugs)
- `corner_r = 3.0` mm (Outer fillet radius on vertical edges)
- `tol = 0.25` mm (3D printing snap-fit/sliding clearance tolerance)
### Component & Cutout Parameters:
- **Photodiode Aperture (Bottom Floor, `Z = 0` to `wall_thick`):**
- `pd_hole_dia = 5.6` mm (Snug fit for a 5mm photodiode dome)
- `pd_x_offset = 10.0` mm (Measured from the inner left wall; aligns with the meter's right-hand pulse LED while keeping the outer left wall clear of the meter's LCD bezel)
- `pd_y_offset = 26.0` mm (Centered vertically on the inner Y axis)
- `pd_collar_h = 3.0` mm (Internal cylindrical shroud rising from the floor around `pd_hole_dia`, outer diameter `pd_hole_dia + 2.4` mm, to block stray light)
- **Internal Light Baffle (Separates Left Sensor Bay from Right ESP32 Bay):**
- `baffle_x = 18.0` mm (Measured from inner left wall)
- `baffle_thick = 1.5` mm
- `baffle_h = 20.0` mm (Rises from floor `Z = wall_thick` to `Z = wall_thick + 20.0`, leaving 3 mm at the top for 3-wire routing between bays)
- **ESP32-C3 Super Mini Bay (Right side, `X > baffle_x`):**
- `esp_w = 18.2` mm
- `esp_l = 22.8` mm
- `esp_standoff_h = 2.5` mm (Raised cradle/rails on the floor so underside solder joints sit flat)
- **USB-C Cutout (Bottom Perimeter Wall, `-Y` face, aligned with Right Bay):**
- `usbc_w = 9.6` mm
- `usbc_h = 4.0` mm
- `usbc_x_center = 30.0` mm (Centered in the right ESP32 bay, measured from inner left wall)
- `usbc_z_bottom = wall_thick + esp_standoff_h + 1.2` mm (Aligned with the USB-C receptacle sitting on top of the 1.6mm PCB)
- **Status LED Cutout (Top Lid):**
- `led_hole_dia = 5.2` mm (Press-fit/glue hole for 5mm RGB status LED)
- `led_x_offset = 30.0` mm (Centered over the right bay so it is isolated behind the light baffle)
- `led_y_offset = 38.0` mm (Upper section of the right bay, clear of the ESP32 PCB footprint)
## 3. Detailed Geometry Construction Requirements
### Component 1: `Base_Body`
1. **Main Shell:** Create a rounded-rectangle outer profile `(inner_w + 2*wall_thick)` × `(inner_h + 2*wall_thick)` with corner radius `corner_r`, extruded from `Z = 0` to `Z = wall_thick + inner_d`.
2. **Interior Cavity:** Cut an inner rounded-rectangle pocket `(inner_w)` × `(inner_h)` from `Z = wall_thick` through the top (`Z = wall_thick + inner_d`).
3. **Photodiode Hole & Light Collar:**
- Extrude-cut a vertical cylinder of `pd_hole_dia` through the bottom floor (`Z = 0` to `wall_thick`) at `(pd_x_offset, pd_y_offset)`.
- Extrude-join a hollow light-blocking collar around that exact hole from `Z = wall_thick` to `Z = wall_thick + pd_collar_h`.
4. **Internal Light Baffle:**
- Extrude-join a rectangular partition wall of thickness `baffle_thick` spanning the full internal Y height (`inner_h`) at `X = baffle_x`, rising from `Z = wall_thick` to `Z = wall_thick + baffle_h`.
5. **ESP32-C3 Super Mini Positioning Rails:**
- Add two low-profile positioning ribs (`1.5 mm` wide × `esp_standoff_h` tall × `esp_l` long) along the `-Y` bottom edge of the right bay (`Y = 0` to `esp_l` from the inner `-Y` wall), spaced `esp_w` apart and centered on `usbc_x_center`, to cradle the Super Mini PCB squarely against the USB-C cutout.
6. **USB-C Port Opening:**
- Extrude-cut a rounded slot (`usbc_w` × `usbc_h`, corner radius `1.5 mm`) through the `-Y` exterior wall centered at `usbc_x_center` and `usbc_z_bottom + usbc_h/2`.
7. **Lid Retention Groove:**
- Add a small internal snap-fit bead or detent lip (`0.6 mm` protrusion) `1.5 mm` below the top rim along the inner `-X` and `+X` walls.
### Component 2: `Lid_Body` (Generated side-by-side at `X = inner_w + 15 mm` for easy STL export)
1. **Top Cap:** Extrude the same outer rounded-rectangle profile `(inner_w + 2*wall_thick)` × `(inner_h + 2*wall_thick)` from `Z = 0` to `Z = wall_thick`.
2. **Friction/Snap Lip:** Extrude a perimeter skirt (`1.5 mm` wall thickness, `3.5 mm` tall) on the underside of the lid inset by `tol` (`0.25 mm`) from the inner wall dimensions so it slides snugly into `Base_Body`, with matching detent notches for the base's snap bead.
3. **RGB Status LED Hole:** Extrude-cut a `led_hole_dia` hole completely through the lid at `(led_x_offset, led_y_offset)`.
## 4. Script Best Practices
- Wrap all operations cleanly inside `run(context)` with proper `ui.messageBox` error handling.
- Create separate Fusion 360 `Component` occurrences (`Base_Component` and `Lid_Component`) so each body can be exported directly to `.stl` or `.3mf` without manual splitting.
- Name every timeline feature clearly (e.g., `Base_Outer_Shell`, `Photodiode_Aperture`, `Light_Baffle`, `USBC_Cutout`, `Lid_Cap`, `LED_Aperture`).
Phew, that was a bit of a mouthful. Imagine being stuck down the pub with this guy...
That generated a .py script that needed further work:
A few problems:
- The ESP32 has pin headers underneath the PCBA. i can't remove them, so the board needs to be lifted up so that the underside of the board is at least 9mm from the base. a feature across the cavity would constrain the ESP32 so it can't move upwards, noting that i need to be able to route the 7 wires from the ESP32 to the LED and the sensor board.
- There needs to be some means of fixing the PCBA so that it doesn't slide backwards when the USB connector is inserted.
- There should be a narrow slot for the wires to the opto diode to pass across to the other cavity.
- I've imported the ESP32 and the light sensor board. The sensor LED hole needs to be on the base, close to the top wall of the enclosure, not at the mid point of the base. It also needs some form of fixing. Note that there's a hole in the board near to the 3 pins.
Up until this point, Claude was driving Fusion by getting me to run a Python script. But that's not the modern way. Instead, I told him/it to use the MCP bridge to run Fusion directly without requiring me to play along.
And finally, we got to this point:
What I built
It is the updated design from my last message, with dimensions corrected from your imported models rather than my guesses:
| Item | Was | Now | Measured from |
|---|
| ESP32 board thickness | 1.6 mm | 1.0 mm | ESP32 model |
| ESP32 pocket length | 22.8 mm | 23.1 mm | Board is exactly 22.8 mm long |
| USB-C slot height | 4.0 mm | 4.8 mm | Shell is 4.1 mm tall and sits sunk into the board |
| Photodiode axis to mounting hole | 22.5 mm | 28.0 mm | Hole is 24.5 mm from the diode end of the board, plus 3.5 mm for the lead bend |
| Sensor boss height | 7 mm | 5 mm | Diode height above the board |
The USB connector’s nose sticks out 1.4 mm past the board edge, so it sits inside the wall slot and also holds the front of the board down.
Fit check
I moved your two imported models into their seated positions: the ESP32 on its rails against the USB wall, and the sensor board with its hole over the boss. When I went to do this the sensor model was facing the other way round (diode towards the USB wall); I turned it so the diode is at the top wall, as you described. If you had flipped it on purpose, tell me and I’ll rework the layout.
- ESP32: no interference with the base, or with the lid in its closed position. The lid fingers stop 2.0 mm above the top of the board.
- Sensor board: clear, apart from the diode’s flange touching the collar by 1 mm. That is only because the model’s diode is straight; bent down into the hole it seats on the collar.
- Lid on base: no overlap.
Still to confirm on the real parts
- Pin stub height: set
esp_hold_gap to the height of the header stubs above the ESP32 board plus about 0.3 mm. The model has no headers, so 2.0 mm is my assumption.
- Diode lead length: the 3.5 mm bend allowance in
sens_hole_dist depends on how long the leads are on your module.
- Meter fit: the box now hangs 48 mm below the pulse LED, onto the terminal cover.
And here it is. I could have got here more directly but this looks OK:
Here's the ESP32 sitting in a cavity that confines its movement. It's held down by 2 fingers that extend down from the cover (when fitted):
And the light sensor is fastened down with a small self tapper.
Note that the photo sensor in the detector I've ordered seems to be an LDR rather than a photo diode. It has a different shape and position, like this:
The lid has clips to hold it in place. There's a small slot between the 2 cavities for the wiring to pass through.
Let's make the thing and see how it looks.
I haven't used the printer for about a month and now it isn't working so well:
There's minimal fusion between some of the layers and horrible blotches in the surfaces. Despite having 100% fill, let's say the thing "has no structural integrity". Ooof.
This seems to be due to not keeping your filaments dry, from what I have previously gathered. I've not encountered it before but here we are. Let's try the other reel of (grey) PETG that's loaded on the machine, even though there's no obvious reason it should be any better.
Ooof (again). That was just as bad - it's simply a different colour. Ah well.
2 actions:
- Unleash a new reel of PETG from its dehumidified packaging and use that. Third time lucky?
- Put the 3 open reels of PETG and PLA on the workshop radiator. I should perhaps make a rack for the filaments so they are above the hot radiator by default. I may be wrong and will check up on it but AFAIK, most of the filament driers are simply heated cabinates.
I've printed out the enclosure and lid. There are a couple of problems to fix:
- The fingers that extend down from the lid to hold the ESP32 down break off when you remove the support raft. They need to be sturdier. Currently they are only 4mm long and are very fragile where they meet the lid. They can be wider at the top, tapering down to where they contact the ESP32.
- The latch that hods the lid down is too small. The tongue and groove need to be larger so they print better and the tongue has more to click into.
- The external wall thickness is only 2mm and could usefully be increased to 4mm to give more rigidity.
Make those improvements and I will print it again.
All three changes are made and the new base and lid are rebuilt in your “Housing” document, ready to export. Both built with no timeline errors, and with the lid in its closed position nothing interferes with the base, the ESP32 or the sensor board. I haven’t saved the document.
Each finger is now a tapered wedge instead of a thin post. It is still 2.5 mm wide where it meets the pin stubs, but widens to 8.5 mm where it joins the lid, and it is 8 mm long instead of 4 mm. The taper runs toward the middle of the bay, so the fingers stay clear of the baffle and the side wall.
Thickening the walls to 4 mm made them too stiff for a larger bead to snap past, so I changed how the latch works, not only its size.
- Tongues: the lid now has two flexible tongues, each 20 mm long, 14 mm deep and 1.6 mm thick, one on each side wall.
- Ridge and groove: each tongue carries a 1.0 mm ridge that clicks into a V-groove cut in the base wall. The old bead was 0.6 mm.
- Removal: the ridge has a long ramp on the way in and a 45° face on the way out, so the lid clicks shut but can still be pulled off.
If the click is too stiff or too loose when printed, latch_t (tongue thickness) and latch_bump (ridge height) are the two parameters to adjust.
The perimeter walls are 4 mm, so the box is now 50 × 60 mm outside. I left the floor and lid at 2 mm, since they are separate parameters now (floor_thick, lid_thick) and a thicker floor would move the photodiode further from the meter. Say if you want those at 4 mm too.
Changes that follow from the thicker wall
- USB plug recess: with a 4 mm wall the plug body would hit the outside before the plug seated. There is now a 13.5 × 8 mm recess around the slot on the outside, so the socket face sits flush with the bottom of the recess. Check your cable’s plug body fits that opening.
- Corner radius: raised from 3 to 5 mm so the inside corners keep a small radius.
- Meter fit: the box is 4 mm wider and taller than the one you printed.
Print the lid with its flat outer face on the bed and the fingers and tongues pointing up. Everything on it tapers or stands vertical in that orientation, so it should need no supports or raft, which is what broke the fingers last time.
That looks better. Let's print this:
And now let's get on with wiring up the various parts:
The LED requires 4 wires to the ESP32. And although the ESP32-C3 Super Mini board is different (with more pins etc), the GPIO numbering assignments are the same:
- Photodiode DO (Digital Out) > Pin 10 (third from bottom on the right side)
- Photodiode VCC > Pin 3.3 (third from top on the left side)
- Photodiode GND > Pin G (second from top on the left side)
- Status LED Red > Pin 0 (bottom-left corner)
- Status LED Green > Pin 1 (second from bottom on the left side)
- Status LED Blue > Pin 3 (fourth from bottom on the left side)
- Status LED Ground > Pin G (shared with the photodiode ground)
Note the Aliexpress "datasheet" says "Compatible with both common cathode and anode types. The kit includes both Common Cathode and Common Anode configurations, providing flexibility for various circuit designs and microcontroller setups.".
So I should get a meter out and check if there are indeed 2 flavours - and ideally select the right one! As luck would have it, the first one out of the bag is a common cathode, as shown in the Glow schematic.
Obvs the Chinesium diagram for the LED pinout is less use than the proverbial chocolate teapot / fireguard - WTF does this mean?Ah well. Moving on....
The LEDs have different forward voltages (Vf), so should have different series resistors. As opposed to none at all, as suggested by the schematic. We can do better than that:
| Colour | Typical Vf at 20 mA (V) | Voltage left for resistor (V) | Resistor (Ω) | Approx. current (mA) |
| Red | 2.0 | 1.3 | 270 | 5 |
| Green | 3.2 | 0.1 | 100 | 2 to 4 |
| Blue | 3.1 | 0.2 | 68 | 3 to 5 |
The “voltage left” column is at the datasheet’s 20 mA forward voltage. The green and blue currents are estimates that assume the forward voltage falls to about 2.8 to 2.9 V at these lower currents.
Next - wire up the LED and ESP32 - but the photo detector won't be here until late tomorrow....