Sensor (or any device) Connection Check.
Sometimes, you’ll discover a sensor or other device doesn’t report it’s status or value anymore, but it does NOT notify you of being offline…
Well, this flow checks the, most recent update time of your sensors.
You can run the flow every day, twice a day, just add or remove a time triggercard.
The ‘inactive time’ can be edited as well (24hrs as default) and you can choose to not send notifications when all sensors did report inside the ‘inactive timer’ timeframe.
Apps used:
- HomeyScript
- (optional) Simple (Sys) Log
- For now, in the imported flow, you’ll have to replace the ‘dummy’ DeviceCapabilities cards with HomeyScript THEN card “
Run 'CODE' _with ARGUMENT_, and return 'TEXT-TAG'
”.
But first copy the script inside them:
-
- use CTRL+A and then CTRL+C,
-
- to paste it later on, use CTRL+A and then CTRL+V in the HomeyScript card.
A how-to screenvid (of a similar flowcard):
- to paste it later on, use CTRL+A and then CTRL+V in the HomeyScript card.
The script used here (latest version: check here):
Click to view the script
// Version 0.3b
// Script checks devices based on the last updated time against a threshold
// Focuses on temperature sensors and specified device classes
const NotReportingThreshold = 0.8; // 0.8 hours, which is 48 minutes
const thresholdInMillis = NotReportingThreshold * 3600000; // Convert hours to milliseconds
let DevicesNotReporting = [];
let devices = await Homey.devices.getDevices();
let notReportingCount = 0; // Variable to keep track of the count
// Function to format date as "dd-mm-yyyy, hh:mm:ss"
function formatDate(date) {
if (!date) return "Unknown"; // Return 'Unknown' if date is null or invalid
const day = date.getDate().toString().padStart(2, '0');
const month = (date.getMonth() + 1).toString().padStart(2, '0'); // Months are 0-indexed
const year = date.getFullYear().toString();
const hours = date.getHours().toString().padStart(2, '0');
const minutes = date.getMinutes().toString().padStart(2, '0');
const seconds = date.getSeconds().toString().padStart(2, '0');
return `${day}-${month}-${year}, ${hours}:${minutes}:${seconds}`;
}
for (const device of Object.values(devices)) {
// Exclude Virtual Devices and specific apps
if (device.driverUri && device.driverUri.match('vdevice|nl.qluster-it.DeviceCapabilities|nl.fellownet.chronograph|net.i-dev.betterlogic|com.swttt.devicegroups|com.gruijter.callmebot|com.netscan')) continue;
// Include by regex device name, focusing on temperature-related devices
if (!device.name || !device.name.match(/temperature/i)) continue;
// Exclude devices based on specific name patterns (if necessary, uncomment and modify)
// if (device.name.match(/Flood|TVOC|Netatmo Rain|Motion|Flora|Rear gate Vibration Sensor|Vibration Sensor Attic Doors/i)) continue;
// Include devices based on device class
if (!device.class || !device.class.match(/sensor|button|remote|socket|lights/i)) continue;
let IsReporting = false;
let lastUpdated = null;
for (const capability of Object.values(device.capabilitiesObj)) {
if (!capability.lastUpdated) continue; // Skip capabilities without lastUpdated info
let timeSinceReport = Date.now() - new Date(capability.lastUpdated).getTime();
if (timeSinceReport < thresholdInMillis) {
IsReporting = true;
break;
}
// Track the most recent update
if (!lastUpdated || new Date(capability.lastUpdated) > new Date(lastUpdated)) {
lastUpdated = new Date(capability.lastUpdated);
}
}
if (!IsReporting) {
let deviceInfo = `${device.name} (${formatDate(lastUpdated)} - ${device.class}) (NOK)`;
DevicesNotReporting.push(deviceInfo);
console.log('NOK:', deviceInfo);
// Increment the count
notReportingCount++;
} else {
let deviceInfo = `${device.name} (${formatDate(lastUpdated)} - ${device.class}) (OK)`;
console.log('OK:', deviceInfo);
}
}
// Output for script AND card
await tag('InvalidatedDevices', DevicesNotReporting.join('\n'));
await tag('notReportingCount', notReportingCount);
// Define a return value
const myTag = `Not Reporting Count: ${notReportingCount}\nDevices Not Reporting:\n${DevicesNotReporting.join('\n')}`;
// Return the defined value
return myTag;
// Original script by Robert Klep
// https://community.homey.app/t/a-script-to-check-sensor-last-update/63142/9
TEF:
[tef:FLOWS:"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":/tef]