Generic Presence Detection

All good to know, thanks for the explanation. I also like the nesting in the groups :ok_hand:

Hi,

Thought someone might be interested in the slight twist I’ve made to this presence detection…might help get someone’s ideas flowing…

Premise:

I have rlkoshak’s generic presence detection in a separate rule, controlled by the presence of my and my wife’s iPhones via icloud binding, if I am home it sets vPresent to ON, if I’m away, it’s OFF.

I wanted to have a secondary level of security based around my motion sensors, so created this little rule to check if someone is home when the motion sensors pick up something. The reason being is obviously if we aren’t at home then the wasp in a bottle thought is that someone is in our house but it can’t be us…

Items Used

    // counts the number of motion sensors items reporting ON
    Group:Number:SUM gMotion
    
    // Item to represent motion sensors
    Switch vMotion "Motion [:%s]" <motion>

Then you just need to add whatever sensor(s) item you have to the gMotion group.

The Rule

   val logName = "motion"

    rule "Reset vMotion to OFF on startup"
    when
        System started
    then
    	vMotion.sendCommand(OFF)
    	gMotion.members.forEach[ SwitchItem s | s.sendCommand(OFF)]
    end

    rule "A motion sensor updated"
    when
    	Item gMotion changed
    then
        // write to logfile
        logInfo(logName, "gMotion changed to " + gMotion.state.toString)
        // check if gMotion is > 0 and if someone is home
    	if(gMotion.state > 0 && vPresent.state == ON) 
            {
    		logInfo(logName, "Motion Detected but someone is home - nothing to do")
    	    }	
    	else
            {
    	    logInfo(logName, "Motion Detected - Checking if anyone is home")	
            // Refresh iPhone location to see if someone has come home but location hasn't caught up
            My_iphone_refresh_item.sendCommand("REFRESH")
            Wifes_iphone_refresh_item.sendCommand("REFRESH")
            //Wait 5 seconds for refresh to return results           
             Thread::sleep(5000)
                //is someone actually home?
                if(vPresent.state == ON) 
                    {
                    logInfo(logName, "Motion Detected - Phew, someone is home - nothing to do")
                    }
                else
                    {
                    //Set vMotion to ON which will trigger separate rule to arm cameras, flash lights etc
                    vMotion.sendCommand(ON) // set vMotion ON
                    logInfo(logName, "Motion Detected - ALERT - INTRUDER")
                    }
            }
end

Pretty simple really, but a little twist on the original…

It’s taken me a few iterations to make it this simple but this way it follows the generic presence ideal of just turning a dummy variable to ON and then you can run others things from it.

Hopefully someone will find it useful, and I’m very much open to thoughts and comments to make it more robust / better…

3 Likes

Hi,

I was hoping someone would be able to help, I’ve essentially copied the code from the OP to ensure I can get this working before I start making my changes.

Now, on the whole part works as expected. I just cannot get the Presence_Timer to go OFF once it has been switched ON.

Any ideas why this would be happening?

Many thanks,

Did you install the Expire binding?

Doh! That was exactly the culprit - Thank you so much for the rapid response, working as expected! :slight_smile:

One thing if i may; i noticed the Expire binding is v1, is this still supported/will there be a replacement for v2?

It will be re-implemented as part of the core or perhaps as a profile. It never should have been a binding in the first place. It is questionable whether the binding will continue to be supported in OH 3+. But I’ve implemented a drop in replacement for the binding in Python. Jython Drop-in Replacement for Expire 1.x Binding

1 Like

Thats great, thanks for the clarification @rlkoshak :slight_smile:

Just a question as I’ve not loaded a Python script in OH, is this pretty straight forward? I’d rather have this script if it is likely the binding will be deprecated.

Thanks once again.

See https://openhab-scripters.github.io/openhab-helper-libraries/index.html. NOTE that the way Jython get’s installed is changing shortly but likely not before the final release of OH 2.5. See [beta testers wanted!] Jython addon w/ helper libraries. Instead of the many manual steps described in the helper docs you just need to install it as an add-on like any other.

1 Like

That is awesome, thanks so much @rlkoshak - most appreciated :slight_smile:

Will give it a go and let you know how I get on!

Thanks a lot for the tip. Installing Monitor was easy enough. I don’t have much experience with MQTT, so I don’t know how to integrate this into OH2 yet. Do you have any hints or even rule code you could share? That would probably save me a lot of time :grinning:

Found other examples so it was easier to write than I thought. Now I’ve got something like this i.e. for the id and confidence level:

Thing topic monitor "Monitor" {
Channels:
    Type string : phone_id         "ID"             [ stateTopic="monitor/pizero/myphone", transformationPattern="JSONPATH:$.id" ]
    Type number : phone_confidence "Confidence"     [ stateTopic="monitor/pizero/myphone", transformationPattern="JSONPATH:$.confidence" ] 
}

Works very well so far, will write some rules with that.

I had this working great for a month or so. It was my first OpenHAB project and I has pleased to have presence detection working. I noticed recently that it is no longer working. After investigating a little, I found the the Group Switches that I rely on are not getting updated when the items that are members of the groups change.

I tried updating to 2.5.7-1 to see if that would help, but it didn’t. I also tried adding { autoupdate=“false” } based on https://github.com/openhab/openhab-core/issues/1330#issuecomment-590286273, but that didn’t help.

Here are the group and item defintions:

Switch Presence "Someone is Present" <present> // master presence switch, represents to the rest of OH where someone is home
Switch Long_Term_Presence "Someone is Staying Here" <present>
Switch Someone_Arrived "Someone Arrived" <present> 

Group:Switch:AND(OFF,ON) Presence_Sensors <present> { autoupdate="false" } // (added autoupdate when it stopped working which didn't help)
Group:Switch:AND(OFF,ON) Long_Term_Presence_Sensors <present>

Switch Presence_Timer "Anti-flapping Timer" {expire="4m,command=OFF"} // anti-flapping timer
Switch Long_Term_Presence_Timer {expire="1h,command=OFF"}
Switch Arrival_Timer {expire="5m,command=OFF"}

Switch Presence_Mobile_George         "George's Mobile"   <network>  (Presence_Sensors, Long_Term_Presence_Sensors, gPresence)   { channel="network:pingdevice:10_0_0_134:online" }
Switch Presence_Mobile_Kathleen       "Kathleen's Mobile" <network>  (Presence_Sensors, Long_Term_Presence_Sensors)   { channel="network:pingdevice:c9eed164:online" }  //Once it works with my phone, add others to group
Switch Presence_Mobile_Emily          "Emily's Mobile"     <network> (Presence_Sensors, Long_Term_Presence_Sensors)   {channel="network:pingdevice:f6585319:online"}

Switch Presence_Laptop_George         "George's Laptop"    <network> (Long_Term_Presence_Sensors)                     { channel="network:pingdevice:10_0_0_12:online"}
Switch Presence_Laptop_Kathleen       "Kathleen's Laptop"  <network> (Long_Term_Presence_Sensors)                     { channel="network:pingdevice:10_0_0_91:online"}
Switch Presence_iPad_George           "George's iPad"      <network> (Long_Term_Presence_Sensors)                     { channel="network:pingdevice:10_0_0_196:online"}
Switch Presence_iPad_Kathleen         "Kathleen's iPad"    <network> (Long_Term_Presence_Sensors)                     { channel="network:pingdevice:c9759e92:online"}
Switch Presence_Surface_Emily         "Emily's Surface"    <network> (Long_Term_Presence_Sensors)                     {channel="network:pingdevice:94169daf:online"}

Here is the log showing the changes in the items, with no corresponding change in the group. (The third item in the group is for an adult child. I confirmed that its status is OFF.)

2020-08-05 13:08:42.856 [vent.ItemStateChangedEvent] - Presence_Mobile_George changed from ON to OFF

2020-08-05 13:17:13.636 [vent.ItemStateChangedEvent] - Presence_Mobile_Kathleen changed from ON to OFF
2020-08-05 15:45:55.146 [vent.ItemStateChangedEvent] - Presence_Mobile_George changed from OFF to ON

2020-08-05 15:47:45.327 [vent.ItemStateChangedEvent] - Presence_Mobile_Kathleen changed from OFF to ON


I’m not sure what to try next to resolve this. Thanks for any suggestions.

(If it would be better to open a new thread rather than putting this at the end of this one, let me know and I will delete it and put it where it belongs. Trying to be a good citizen, but still learning).

Try it with 2 separate files. I’ve had the experience that it’s better to separate groups and items. I can’t promise if that will solve your problem.

groups.items

Group:Switch:AND(OFF,ON) Presence_Sensors <present> { autoupdate="false" } // (added autoupdate when it stopped working which didn't help)
Group:Switch:AND(OFF,ON) Long_Term_Presence_Sensors <present>

items.items

Switch Presence "Someone is Present" <present> // master presence switch, represents to the rest of OH where someone is home
Switch Long_Term_Presence "Someone is Staying Here" <present>
Switch Someone_Arrived "Someone Arrived" <present> 

Switch Presence_Timer "Anti-flapping Timer" {expire="4m,command=OFF"} // anti-flapping timer
Switch Long_Term_Presence_Timer {expire="1h,command=OFF"}
Switch Arrival_Timer {expire="5m,command=OFF"}

Switch Presence_Mobile_George         "George's Mobile"   <network>  (Presence_Sensors, Long_Term_Presence_Sensors, gPresence)   { channel="network:pingdevice:10_0_0_134:online" }
Switch Presence_Mobile_Kathleen       "Kathleen's Mobile" <network>  (Presence_Sensors, Long_Term_Presence_Sensors)   { channel="network:pingdevice:c9eed164:online" }  //Once it works with my phone, add others to group
Switch Presence_Mobile_Emily          "Emily's Mobile"     <network> (Presence_Sensors, Long_Term_Presence_Sensors)   {channel="network:pingdevice:f6585319:online"}

Switch Presence_Laptop_George         "George's Laptop"    <network> (Long_Term_Presence_Sensors)                     { channel="network:pingdevice:10_0_0_12:online"}
Switch Presence_Laptop_Kathleen       "Kathleen's Laptop"  <network> (Long_Term_Presence_Sensors)                     { channel="network:pingdevice:10_0_0_91:online"}
Switch Presence_iPad_George           "George's iPad"      <network> (Long_Term_Presence_Sensors)                     { channel="network:pingdevice:10_0_0_196:online"}
Switch Presence_iPad_Kathleen         "Kathleen's iPad"    <network> (Long_Term_Presence_Sensors)                     { channel="network:pingdevice:c9759e92:online"}
Switch Presence_Surface_Emily         "Emily's Surface"    <network> (Long_Term_Presence_Sensors)                     {channel="network:pingdevice:94169daf:online"}

Just to be clear, the way the Groups are defined they will be ON if any member of the Group is ON. Have you confirmed that all three members of Presence_Sensors and all five members of Long_Term_Presence_Timer are going to OFF? If not the Groups will remain ON.

Thanks for the quick response.

I found the problem, which, not surprisingly, was of my own making. Your comments prompted me to review the members of the group. I had hurriedly added the group to a PaperUI group as a quick way to make it appear in my sitemap. I removed it an everything works as at should.

Sorry for the inconvenience.

1 Like

Thank you for this helpful tutorial. It works perfectly. The only stumbling block I was that I didn’t have val logName = "Presence" in my rules since it wasn’t in the rules example.

One of my main uses for Presence is to get a notification when I left the home but left a door/window open. If I’m five minutes down the road before I get that notification, then it’ll be just that much longer to return home and close the item. I can easily change the anti-flapping timer to be something less but I was curious if five minutes was picked for a particular reason?

Thank you,
B34N

As with most tutorials you will find on this forum, they are intended to be adapted to your specific needs. I used 5 minutes so it wouldn’t count me as being away when I go get the mail (out of range of the presence sensors) or to the compost heap. Five minutes seemed a good compromise between not marking me as away too often when I’m not away and getting an alert soon enough to do something about it. Feel free to experiment with the optimal value for you.

Note, if you are on OH 3, at the same link to the Debounce rule listed under Python is a JavaScript YAML version of my debounce implementation. With that you don’t even need the rule.

2 Likes

Hi Rich,

I implemented the code exactly as on your Github page (java code), got the timer_mgr and time_utils installed and created items exactly as with your Github example (did change the names though).

However, my mainPresence item, witch is the proxy, does never switch to the OFF state (I set 5 mins as a start). Nothing shows up in the logs. Any ideas?

I have installed the Items 3 times now, just in case I messed up the metadata part of things but to no avail.

Best regards

So none of your rules are working, if they’re not producing logs?

Bear in mind this example was for OH2. Which version of rules are you running? What version of openHAB are you running? There are differences.

I figured, if the rule is broken or incorrect copied or an item is missing metadata, it will through an error. However, there is nothing in the log so I wandered where else the problem might lie.

The Java-version I got from @rlkoshak s Github page is, I think, the newest. I just got it a few days ago. The TimeOfDay rule works fine, also from his Github page.

I am running OH3.02 release build.