Built in Aqara Drivers - Weather/Contact/Vibration

Hi all. On my C-8 Pro (platform 2.5.3.123), the built-in Aqara drivers never update the battery attribute. Every one of my Aqara sensors has shown 100% since I moved them from a community driver to the built-in drivers in October 2024. The last battery event on each one dates from that switch. I only noticed when a temperature sensor's battery died and it went silent while still showing 100%.

Drivers and models affected:

  • Aqara Zigbee Weather Sensor, lumi.weather : 11 devices
  • Aqara Zigbee Contact Sensor, lumi.sensor_magnet.aq2 : 8 devices
  • Aqara Vibration Sensor, lumi.vibration.aq1 : 4 devices.

The sensors do send their battery level. With debug logging on, the Weather Sensor driver logs the hourly Xiaomi heartbeat, then does nothing with it:

description: read attr - raw: 89690100005201FF42250121E50B0421A8430521C6E1062401000100006429C2076521D313662BD58A01000A2112F1, dni: 8969, endpoint: 01, cluster: 0000, size: 52, attrId: FF01, encoding: 42, command: 0A, value: 250121E50B0421A8430521C6E1...

The value is the usual Xiaomi structure: a length byte, then tag / ZCL type / little-endian value. Tag 0x01, type 0x21 (uint16) is the battery in mV. Here that's E50B = 0x0BE5 = 3045 mV. The other tags in this example are 0x64 temperature, 0x65 humidity and 0x66 pressure.

To test it, I wrote a small user driver that reads tag 0x01 from 0xFF01 (and 0xFF02 for older models). It sets battery from the voltage on a linear scale (2.5 V = 0%, 3.0 V = 100%), and it works on both the weather sensor and the contact sensor. I'd much rather stay on the built-in drivers, though.

Request: could the built-in Aqara/Xiaomi drivers (Weather, Contact, Vibration, and probably the other Xiaomi end devices) decode the battery voltage from the 0xFF01/0xFF02 heartbeat and update battery? Optionally they could also expose a batteryVoltage attribute or a configurable empty/full voltage - that's what I have done in my mini driver. CR2032 voltage stays almost flat until the cell is nearly empty, so even the raw voltage would help catch a failing battery before the device drops off.

Thanks.

I reported this issue (along with a different one, since fixed) back when the built-in drivers were released, must have fallen through the proverbial cracks:

I ended up designing my own weather and contact sensor drivers, available here (or in HPM), if a community driver written with Claude Code is acceptable to you (@mike.maxwell you're welcome to have a look at the decoding logic for the check-in message):

I don't have a vibration sensor driver as I don't own one, but if you can send a trace from Hub Inspector's Zigbee Radio capture, it's fairly straightforward to create one.

.

Hi, thanks for a steer to your MCCGQ11LM and WSDCGQ11LM drivers. I compared them with a driver I was writing and noticed a possible issue with the button-press path. I am trying to educate myself a bit more :grinning_face:

On my C-8 Pro (platform 2.5.3.123), a short press on an MCCGQ11LM arrives like this:

read attr - raw: B20F01000076050042166C756D692E73656E736F725F6D61676E65742E61713201FF421D0121BD0B03280F0421A84305216B0D062400000300000A21139D641000, dni: B20F, endpoint: 01, cluster: 0000, size: 76, attrId: 0005, encoding: 42, command: 0A, value: 166C756D692E73656E736F725F6D61676E65742E61713201FF421D0121BD0B03280F0421A84305216B0D062400000300000A21139D641000

zigbee.parseDescriptionAsMap() does put FF01 in additionalAttrs, but on this platform version its value is the decoded character string, cut short at the first 0x00 byte (\u0001!½\u000b\u0003(\u000f\u0004!¨C\u0005!k), not hex. So parseCheckinFromMap() passes a ~16-character non-hex string to parseCheckin(), which stops with "payload too short". The pushed event still fires, but no battery reading is taken from the press.

What worked for me was taking the TLV from the raw value: hex of the 0x0005 report instead. The layout is [len][model id string][01FF][42][TLV len][TLV…]: skip 1 + len bytes, check for 01FF42 (or 02FF42), and the rest is the length-prefixed TLV your parseCheckin() already handles. Here that gives tag 0x01 = BD0B = 3005 mV.

I haven't run your driver itself, so this comes from your code plus the description my hub delivered. If your firmware hands additionalAttrs over as hex, this may be version-dependent.

I've raised an issue in Github with a bit more info if you want to take a look and consider/ignore as you wish!

You were right, thanks for the report and the GitHub issue.

Aqara drivers (MCCGQ11LM 1.1.5, WSDCGQ11LM 2.15.8), in HPM now.

  • MCCGQ11LM: a button press updates battery and batteryVoltage.
  • WSDCGQ11LM: a button press sends pushed.

The weather sensor sends its check-in and the model report as two separate frames on a press, so its battery reading was not affected.

Great - thanks. Yep, agreed. I've commented on Github and closed the issue for completeness in case anyone else has an interest and stumbles across it separately.

Thanks again!