-
Notifications
You must be signed in to change notification settings - Fork 9
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Can't report temperatures below freezing on H5075 #16
Comments
@gawtDamn thank you for this bug report. I will see if I can reproduce the issue by putting my sensor into the freezer. This issue could be due to decoding from binary format. |
I added some additional debugging info in my instance to help track this down. Reading without error:
Reading with error (actual temperature was -11.5C and Humidity was 33%)
Here's the relevant code: export const decodeH5075Values = (streamUpdate: string) => {
// TODO would be great to find a way to validate
const encodedData = parseInt(streamUpdate.substring(6, 12), 16);
const battery = parseInt(streamUpdate.substring(12, 14), 16);
const tempInC = encodedData / 10000;
const tempInF = (tempInC * 9) / 5 + 32;
const humidity = (encodedData % 1000) / 10;
return {
battery,
humidity,
tempInC,
tempInF,
};
}; With that in mind, let's dig into what we're actually getting with each stream update:
Take note that when the temperature goes negative, there's a leading 8 in the part of the data for temperature which in turn is a leading 1 in the binary data. It's basically a signed 6-byte number? Here's the encodedData fleshed out:
What's baffling me about this is that the temperature and humidity are stored back to back in decimal, but for the resulting binary number, the first bit is positive or negative based on if the temperature is positive or negative. I don't have a lot of experience reasoning about bits so I expect there's a better way to handle all this, but I'm imagining the following fix:
This can also be represented as this truth table:
Here's the rewritten function I'm using in my HomeBridge. It passed a test with the device in the freezer. I edited this in-place in exports.decodeH5075Values = (streamUpdate) => {
// TODO would be great to find a way to validate
const encodedData = parseInt(streamUpdate.substring(6, 12), 16);
const dataAsBits = encodedData.toString(2);
var tempIsNegative = false;
var dataToUse = encodedData;
if (dataAsBits.length == 24) {
tempIsNegative = (dataAsBits.substr(0,1) == "1");
dataToUse = parseInt(dataAsBits.substr(1,23), 2);
}
const tempInC = dataToUse / 10000 * (tempIsNegative ? -1 : 1);
const battery = parseInt(streamUpdate.substring(12, 14), 16);
const tempInF = (tempInC * 9) / 5 + 32;
const humidity = (dataToUse % 1000) / 10;
return {
battery,
humidity,
tempInC,
tempInF,
};
}; |
Describe The Bug:
When the sensor of my H5075 goes below 32F (0C), the Home app displays the device's temperature as 212F. In the app "Controller for Homekit" the message traffic for the temperature is missing when the temperature is below freezing, although humidity messages still happen.
To Reproduce:
Put a H5075 sensor in the freezer, and watch the message traffic in Controller for Homekit, and in Home.app
Expected behavior:
The correct temperature is shown on the sensor display, so I would expect this to be shown in the apps and in the message traffic. I have verified using an Aqara Homekit-compatible temperature sensor that Homekit does support temperatures below freezing. My guess is that the plugin as-written uses a data type that doesn't support negative numbers, and that the native data computations are done in Celsius.
Logs:
Plugin Config:
Show your Homebridge config.json here, remove any sensitive information.
Screenshots:
Environment:
homebridge running on the official rasPi install, 1.1.17
The text was updated successfully, but these errors were encountered: