Page 18 of 19

Re: How to check presence of Beacon ?

Posted: Thursday 27 December 2018 11:53
by Artursd
This node is a type unknown to your installation of Node-RED.

Details
If you deploy with the node in this state, its configuration will be preserved, but the flow will not start until the missing type is installed.

Use the Menu - Manage Palette option to search for and install nodes, or npm install <module> to install, any missing modules and restart Node-RED and reimport the nodes.

It is possible this node type is already installed, but is missing a dependency. Check the Node-RED start-up log for any error
messages associated with the missing node type.

Otherwise, you should contact the author of the flow to obtain a copy of the missing node type.

Re: How to check presence of Beacon ?

Posted: Saturday 29 December 2018 17:38
by QuadRotas
I finally got it to work, with different BLE-tags.
These didn't work.
But these work fine.

Now the new challenge: switch stuff on and off based on presence of the BLE's.
So far I've managed to create this script:

Code: Select all

commandArray = {}

for variableName, variableValue in pairs(uservariables) do
    -- Alle Bluetooth_Tag-uservariables controleren op status AWAY
    if string.match(variableName, "Bluetooth_Tag_Green") and variableValue == "AWAY" then
       commandArray['SomeoneHome'] = "Off"
    elseif string.match(variableName, "Bluetooth_Tag_Green") and variableValue == "HOME" then
        commandArray['Someonehome'] = "On"
    end
end
return commandArray
This does the trick but the script is fired multiple times a second, according to logging. It fills up the log crazy fast and the SomeoneHome switched is turned On an equal amount of times. The end result is the same but it seems like overkill. Or is this intended behaviour of the Domoticz events?

Is there a way to have a script run on specific intervals?

Re: How to check presence of Beacon ?

Posted: Sunday 13 January 2019 11:01
by redfirebrooks
Hello, I just want to know if my keyring is home or not, I tested this script but it doesn't work.
Could you help me

Code: Select all

commandArray = {}

Fredbeacon=0
for variableName, variableValue in pairs(uservariables) do
    if string.sub(variableName,1,3)=="Tag_White" and variableValue ~= "HOME" then
      commandArray ['FredNut'] = 'On'
  elseif string.sub(variableName,1,3)=="Tag_White" and variableValue ~= "AWAY" then
      commandArray ['FredNut'] = 'Off'
    end
end

return commandArray

Re: How to check presence of Beacon ?

Posted: Sunday 13 January 2019 11:09
by QuadRotas
redfirebrooks wrote: Sunday 13 January 2019 11:01 Hello, I just want to know if my keyring is home or not, I tested this script but it doesn't work.
Could you help me

Code: Select all

commandArray = {}

Fredbeacon=0
for variableName, variableValue in pairs(uservariables) do
    if string.sub(variableName,1,3)=="Tag_White" and variableValue ~= "HOME" then
      commandArray ['FredNut'] = 'On'
  elseif string.sub(variableName,1,3)=="Tag_White" and variableValue ~= "AWAY" then
      commandArray ['FredNut'] = 'Off'
    end
end

return commandArray
Does it do anything or nothing at all? You could test that by putting a PRINT statement in the if and else if blocks, to see which (if any) are fired.
It looks like you are setting FredNut as ON when Tag_White is not equal to HOME, and OFF when the tag is not equal to AWAY. Isn't that the wrong way around?

I use

Code: Select all

...
if string.match(variableName, "Bluetooth_Tag_Green") and variableValue == "AWAY" then
...
to check my tag-presence.

Re: How to check presence of Beacon ?

Posted: Sunday 13 January 2019 11:27
by redfirebrooks
Thank for your quick reponse
I used blocky to manage it and it now it works

Image

Re: How to check presence of Beacon ?

Posted: Friday 18 January 2019 10:59
by aliferis
Hi 2 all, I'm new to domoticz and I am reading a lot these days, i gave a try before to hassio and open hab but domoticz is the best so far when it comes to user friendly.
I would like to ask if and where can i read on how to change the status of security panel (e.x. from disarm to arm) based on an event

also i would like to know if I can use RasPi bleutooth for the detection? do i need another usb bluetooth?
ty in advance

Re: How to check presence of Beacon ?

Posted: Friday 18 January 2019 11:43
by emme
rasPI bt is enough to detect BLE (note that for Pi3 and pi3b+ you will need to configure the WiFi Country in the wpasupplicant.conf or raspi-config to have the interface working)

adding a dongle will add another interface :P

Re: How to check presence of Beacon ?

Posted: Sunday 20 January 2019 21:17
by pimseb
Hello,

I've been using this script for one year and it woks great I'm now trying to add the battery check script from emme (here : https://www.domoticz.com/forum/viewtopi ... 63&t=16349 )
In emme's script I can chose to start and stop the beacon detection service during the battery check. But I don't want to do this. If I disable the service I'll receive alerts that someone left the house and of course that isn't true.

Then I've tried to add a bluetooth dongle. This way I can use an interface for presence and the other one for battery.
First problem : the onboard bluetooth device automatically turns from hci0 to hci1. As far as I know it's not possible to fix it on hci0
Second problem : I let the beacon presence script as it is, but it doesn't work anymore with the usb dongle (which is hci0). Check_beacon_presence.py thinks I'm away but the beacon is near the raspberry :

Code: Select all

2019-01-20 20:56:07,562 - root - DEBUG - Ok hci0 interface Up n running !
2019-01-20 20:56:07,563 - root - DEBUG - Connect to bluetooth device 0
2019-01-20 20:56:12,568 - root - WARNING - Tag Tag_pim not seen since 55 sec => update absence
ÉDIT : EVERYTHING WORKS FINE. BLUETOOTH DONGLE WAS TOO OLD AND NOT 4.0

Re: How to check presence of Beacon ?

Posted: Monday 21 January 2019 11:02
by pimseb
please delete

Re: How to check presence of Beacon ?

Posted: Monday 28 January 2019 9:05
by Adiizola
I suggest to get a class 1 BT v4 dongle as in theory can reach 100m coverage (50m in radius on open enviroment).


แทงหวยหุ้น-ออนไลน์

Re: How to check presence of Beacon ?

Posted: Friday 01 February 2019 18:36
by sp8ufw
Hello,

I have set up bluetooth and presence detection in my domotic, but the script only detects itage the first time it starts and after a while displays AWAY status.
I have an iTag with this auction https://www.banggood.com/Bluetooth-4_0- ... rehouse=CN

Is there any possibility of forcing the script to detect iTag after reconnecting with my bluetooth host?

The only thing that comes to my mind is the launching and stopping of the service by cron.

Thank you in advance for the information.

MJ

Re: How to check presence of Beacon ?

Posted: Friday 26 April 2019 22:10
by flyboarder
I've followed the wiki and got the beacon detection working. Yesterday I tested it by going out of the house and back and it worked fine. When I came home today I noticed that it never went to AWAY when I left for work in the morning. I found the service was not running, so I restarted the service with

Code: Select all

service check_beacon_presence start
This seemed to work and the user variable in Domoticz got updated. But checking a while later I saw the service was stopped again. Restarting a few more time shows the service run for 5-10 min and failes. Below the output:

Code: Select all

pi@raspberrypi:~ $ sudo systemctl status check_beacon_presence.service -l
● check_beacon_presence.service - check_beacon_presence Service
   Loaded: loaded (/lib/systemd/system/check_beacon_presence.service; enabled; vendor preset: enabled)
   Active: failed (Result: exit-code) since Fri 2019-04-26 21:37:21 CEST; 2min 14s ago
  Process: 24855 ExecStart=/usr/local/bin/check_beacon_presence.py (code=exited, status=1/FAILURE)
 Main PID: 24855 (code=exited, status=1/FAILURE)

Apr 26 21:28:13 raspberrypi sudo[24876]:     root : TTY=unknown ; PWD=/ ; USER=root ; COMMAND=/bin/hciconfig
Apr 26 21:28:13 raspberrypi sudo[24876]: pam_unix(sudo:session): session opened for user root by (uid=0)
Apr 26 21:28:13 raspberrypi sudo[24876]: pam_unix(sudo:session): session closed for user root
Apr 26 21:37:21 raspberrypi check_beacon_presence.py[24855]: Traceback (most recent call last):
Apr 26 21:37:21 raspberrypi check_beacon_presence.py[24855]:   File "/usr/local/bin/check_beacon_presence.py", line 195, in <module>
Apr 26 21:37:21 raspberrypi check_beacon_presence.py[24855]:     pkt = sock.recv(255)
Apr 26 21:37:21 raspberrypi check_beacon_presence.py[24855]: _bluetooth.error: (32, 'Broken pipe')
Apr 26 21:37:21 raspberrypi systemd[1]: check_beacon_presence.service: Main process exited, code=exited, status=1/FAILURE
Apr 26 21:37:21 raspberrypi systemd[1]: check_beacon_presence.service: Unit entered failed state.
Apr 26 21:37:21 raspberrypi systemd[1]: check_beacon_presence.service: Failed with result 'exit-code'.
Does anyone has an idea what is causing the service to fail after a few minutes?

Re: How to check presence of Beacon ?

Posted: Tuesday 30 April 2019 19:22
by flyboarder
flyboarder wrote: Friday 26 April 2019 22:10 I've followed the wiki and got the beacon detection working. Yesterday I tested it by going out of the house and back and it worked fine. When I came home today I noticed that it never went to AWAY when I left for work in the morning. I found the service was not running, so I restarted the service with

Code: Select all

service check_beacon_presence start
This seemed to work and the user variable in Domoticz got updated. But checking a while later I saw the service was stopped again. Restarting a few more time shows the service run for 5-10 min and failes. Below the output:

Code: Select all

pi@raspberrypi:~ $ sudo systemctl status check_beacon_presence.service -l
● check_beacon_presence.service - check_beacon_presence Service
   Loaded: loaded (/lib/systemd/system/check_beacon_presence.service; enabled; vendor preset: enabled)
   Active: failed (Result: exit-code) since Fri 2019-04-26 21:37:21 CEST; 2min 14s ago
  Process: 24855 ExecStart=/usr/local/bin/check_beacon_presence.py (code=exited, status=1/FAILURE)
 Main PID: 24855 (code=exited, status=1/FAILURE)

Apr 26 21:28:13 raspberrypi sudo[24876]:     root : TTY=unknown ; PWD=/ ; USER=root ; COMMAND=/bin/hciconfig
Apr 26 21:28:13 raspberrypi sudo[24876]: pam_unix(sudo:session): session opened for user root by (uid=0)
Apr 26 21:28:13 raspberrypi sudo[24876]: pam_unix(sudo:session): session closed for user root
Apr 26 21:37:21 raspberrypi check_beacon_presence.py[24855]: Traceback (most recent call last):
Apr 26 21:37:21 raspberrypi check_beacon_presence.py[24855]:   File "/usr/local/bin/check_beacon_presence.py", line 195, in <module>
Apr 26 21:37:21 raspberrypi check_beacon_presence.py[24855]:     pkt = sock.recv(255)
Apr 26 21:37:21 raspberrypi check_beacon_presence.py[24855]: _bluetooth.error: (32, 'Broken pipe')
Apr 26 21:37:21 raspberrypi systemd[1]: check_beacon_presence.service: Main process exited, code=exited, status=1/FAILURE
Apr 26 21:37:21 raspberrypi systemd[1]: check_beacon_presence.service: Unit entered failed state.
Apr 26 21:37:21 raspberrypi systemd[1]: check_beacon_presence.service: Failed with result 'exit-code'.
Does anyone has an idea what is causing the service to fail after a few minutes?
Since this issue I have played around with some Bluetooth settings on my pi (and returning them to the original setting). And now it has been running fine for over 3 days.

Re: How to check presence of Beacon ?

Posted: Friday 19 July 2019 14:28
by markjgabb
Hi all

anyone able to render assistance on this one?

ive installed the script as per below
test script works perfectly, but when i test run the main script, absolutely nothing happens...even with debug on there is literally no output the screen the cursor is just sitting there waiting for feedback from the script, domoticz log also shows no output at all


Code: Select all

#!/usr/bin/python
#   File : check_beacon_presence.py
#   Author: jmleglise
#   Date: 10-Nov-2016
#   Description : Check the presence of a list of beacon (BlueTooth Low Energy V4.0) and update uservariables in Domoticz accordingly. 
#   URL : https://github.com/jmleglise/mylittle-domoticz/edit/master/Presence%20detection%20%28beacon%29/check_beacon_presence.py
#   Version : 1.0
#   Version : 1.1   Log + Mac Adress case insensitive 
#   Version : 1.2   Fix initial AWAY state
#   Version : 1.3   Log + script takes care of hciconfig + Return the RSSI when detected and "AWAY" otherwise
#   Version : 1.4   Fix initial HOME state
#   Version : 1.5   Split loglevel warning / debug
#   Version : 1.6   Add le_handle_connection_complete +  Manage Domoticz login
#
# Feature : 
# Script takes care of Bluetooth Adapter. Switch it UP RUNNING.
# When the MACADRESS of a list of beacons are detected, update DOMOTICZ uservariable.
# Script operates now in 2 mode. Choose for each beacon witch one you want :
#       REPEAT MODE : For beacon in range, update the uservariable every 3 secondes with the RSSI. And "AWAY" otherwise.
#       SWITCH_MODE : For beacon in range, update only 1 time the uservariable with "HOME". And "AWAY" otherwise.
# Send "AWAY" when the beacons are not in range.
# The detection is very fast : around 4 secondes. And the absence is verified every 5 seconds by comparing the hour of the last presence with a time out for each beacon.
#
# References :
# https://www.domoticz.com/wiki/Presence_detection_%28Bluetooth_4.0_Low_energy_Beacon%29
# http://https://www.domoticz.com/forum/viewtopic.php?f=28&t=10640
# https://wiki.tizen.org/wiki/Bluetooth
# https://storage.googleapis.com/google-code-archive-source/v2/code.google.com/pybluez/source-archive.zip  => pybluez\examples\advanced\inquiry-with-rssi.py
#
# Required in Domoticz : An uservariable of type String for each BLE Tag
#
# Usefull command
# sudo /etc/init.d/check_beacon_presence [stop|start|restart|status] 
# 
# Configuration :
# Change your IP and Port here :  
URL_DOMOTICZ = 'https://127.0.0.1:443/json.htm?type=command&param=updateuservariable&idx=PARAM_IDX&vname=PARAM_NAME&vtype=2&vvalue=PARAM_CMD'
DOMOTICZ_USER=''
DOMOTICZ_PASS=''

REPEAT_MODE=1
SWITCH_MODE=0

#
# Configure your Beacons in the TAG_DATA table with : [Name,MacAddress,Timeout,0,idx,mode]
# Name : the name of the uservariable used in Domoticz
# macAddress : case insensitive
# Timeout is in secondes the elapsed time  without a detetion for switching the beacon AWAY. Ie :if your beacon emits every 3 to 8 seondes, a timeout of 15 secondes seems good.
# 0 : used by the script (will keep the time of the last broadcast) 
# idx of the uservariable in Domoticz for this beacon
# mode : SWITCH_MODE = One update per status change / REPEAT_MODE = continuous updating the RSSI every 3 secondes

TAG_DATA = [
            ["Watch_kez","f4:e5:a4:c0:ae:1d",30,0,2,REPEAT_MODE],
            ["Tag_Green","c2:98:b6:54:15:f3",30,0,3,REPEAT_MODE],
            ["Watch_Mark","53:31:20:99:97:2c",30,0,1,REPEAT_MODE],
            ["Tag_White","c5:f3:41:1b:0c:5c",30,0,4,REPEAT_MODE]
           ]

           
import logging

# choose between DEBUG (log every information) or warning (change of state) or CRITICAL (only error)
logLevel=logging.DEBUG
#logLevel=logging.CRITICAL
#logLevel=logging.WARNING

logOutFilename='/var/log/check_beacon_presence.log'       # output LOG : File or console (comment this line to console output)
ABSENCE_FREQUENCY=5  # frequency of the test of absence. in seconde. (without detection, switch "AWAY".

################ Nothing to edit under this line #####################################################################################

import os
import subprocess
import sys
import struct
import bluetooth._bluetooth as bluez
import time
import requests
import signal
import threading


LE_META_EVENT = 0x3e
OGF_LE_CTL=0x08
OCF_LE_SET_SCAN_ENABLE=0x000C
EVT_LE_CONN_COMPLETE=0x01
EVT_LE_ADVERTISING_REPORT=0x02

def print_packet(pkt):
    for c in pkt:
        sys.stdout.write("%02x " % struct.unpack("B",c)[0])

def packed_bdaddr_to_string(bdaddr_packed):
    return ':'.join('%02x'%i for i in struct.unpack("<BBBBBB", bdaddr_packed[::-1]))

def hci_disable_le_scan(sock):
    hci_toggle_le_scan(sock, 0x00)

def hci_toggle_le_scan(sock, enable):
    cmd_pkt = struct.pack("<BB", enable, 0x00)
    bluez.hci_send_cmd(sock, OGF_LE_CTL, OCF_LE_SET_SCAN_ENABLE, cmd_pkt)

def handler(signum = None, frame = None):
    time.sleep(1)  #here check if process is done
    sys.exit(0)   
    
for sig in [signal.SIGTERM, signal.SIGINT, signal.SIGHUP, signal.SIGQUIT]:
    signal.signal(sig, handler)

def le_handle_connection_complete(pkt):
    status, handle, role, peer_bdaddr_type = struct.unpack("<BHBB", pkt[0:5])
    device_address = packed_bdaddr_to_string(pkt[5:11])
    interval, latency, supervision_timeout, master_clock_accuracy = struct.unpack("<HHHB", pkt[11:])
    #print "le_handle_connection output"
    #print "status: 0x%02x\nhandle: 0x%04x" % (status, handle)
    #print "role: 0x%02x" % role
    #print "device address: ", device_address

def request_thread(idx,cmd, name):
    try:
        url = URL_DOMOTICZ
        url=url.replace('PARAM_IDX',str(idx))
        url=url.replace('PARAM_CMD',str(cmd))
        url=url.replace('PARAM_NAME',str(name))
        result = requests.get(url,auth=(DOMOTICZ_USER, DOMOTICZ_PASS))
        logging.debug(" %s -> %s" % (threading.current_thread(), result))
    except requests.ConnectionError, e:
        logging.critical(' %s Request Failed %s - %s' % (threading.current_thread(), e, url) )

class CheckAbsenceThread(threading.Thread):
    def __init__(self):
        threading.Thread.__init__(self)
    def run(self):

        time.sleep(ABSENCE_FREQUENCY)    
        for tag in TAG_DATA:
            elapsed_time_absence=time.time()-tag[3]
            if elapsed_time_absence>=tag[2] : # sleep execute after the first Home check.
                logging.warning('Tag %s not seen since %i sec => update absence',tag[0],elapsed_time_absence)
                threadReqAway = threading.Thread(target=request_thread,args=(tag[4],"AWAY",tag[0]))
                threadReqAway.start()

        while True:
            time.sleep(ABSENCE_FREQUENCY)
            for tag in TAG_DATA:
                elapsed_time_absence=time.time()-tag[3]
                if elapsed_time_absence>=tag[2] and elapsed_time_absence<(tag[2]+ABSENCE_FREQUENCY) :  #update when > timeout ant only 1 time , before the next absence check [>15sec <30sec]
                    logging.warning('Tag %s not seen since %i sec => update absence',tag[0],elapsed_time_absence)
                    threadReqAway = threading.Thread(target=request_thread,args=(tag[4],"AWAY",tag[0]))
                    threadReqAway.start()
            
FORMAT = '%(asctime)s - %(name)s - %(levelname)s - %(message)s'
if globals().has_key('logOutFilename') :
    logging.basicConfig(format=FORMAT,filename=logOutFilename,level=logLevel)
else:
    logging.basicConfig(format=FORMAT,level=logLevel)

#Reset Bluetooth interface, hci0
os.system("sudo hciconfig hci0 down")
os.system("sudo hciconfig hci0 up")

#Make sure device is up
interface = subprocess.Popen(["sudo hciconfig"], stdout=subprocess.PIPE, shell=True)
(output, err) = interface.communicate()

if "RUNNING" in output: #Check return of hciconfig to make sure it's up
    logging.debug('Ok hci0 interface Up n running !')
else:
    logging.critical('Error : hci0 interface not Running. Do you have a BLE device connected to hci0 ? Check with hciconfig !')
    sys.exit(1)
    
devId = 0
try:
    sock = bluez.hci_open_dev(devId)
    logging.debug('Connect to bluetooth device %i',devId)
except:
    logging.critical('Unable to connect to bluetooth device...')
    sys.exit(1)

old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14)
hci_toggle_le_scan(sock, 0x01)

for tag in TAG_DATA:
    tag[3]=time.time()-tag[2]  # initiate lastseen of every beacon "timeout" sec ago. = Every beacon will be AWAY. And so, beacons here will update 

th=CheckAbsenceThread()
th.daemon=True
th.start()

while True:
    old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14)
    flt = bluez.hci_filter_new()
    bluez.hci_filter_all_events(flt)
    bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT)
    sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt )
    
    pkt = sock.recv(255)
    ptype, event, plen = struct.unpack("BBB", pkt[:3])

    if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI:
            i =0
    elif event == bluez.EVT_NUM_COMP_PKTS:
            i =0 
    elif event == bluez.EVT_DISCONN_COMPLETE:
            i =0 
    elif event == LE_META_EVENT:
            subevent, = struct.unpack("B", pkt[3])
            pkt = pkt[4:]
            if subevent == EVT_LE_CONN_COMPLETE:
                le_handle_connection_complete(pkt)
            elif subevent == EVT_LE_ADVERTISING_REPORT:
                num_reports = struct.unpack("B", pkt[0])[0]
                report_pkt_offset = 0
                for i in range(0, num_reports):
                            #logging.debug('UDID: ', print_packet(pkt[report_pkt_offset -22: report_pkt_offset - 6]))
                            #logging.debug('MAJOR: ', print_packet(pkt[report_pkt_offset -6: report_pkt_offset - 4]))
                            #logging.debug('MINOR: ', print_packet(pkt[report_pkt_offset -4: report_pkt_offset - 2]))
                            #logging.debug('MAC address: ', packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9]))
                            #logging.debug('Unknown:', struct.unpack("b", pkt[report_pkt_offset -2])) # don't know what this byte is.  It's NOT TXPower ?
                            #logging.debug('RSSI: %s', struct.unpack("b", pkt[report_pkt_offset -1])) #  Signal strenght !
                            macAdressSeen=packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9])
                            for tag in TAG_DATA:
                                if macAdressSeen.lower() == tag[1].lower():  # MAC ADDRESS
                                    logging.debug('Tag %s Detected %s - RSSI %s - DATA unknown %s', tag[0], macAdressSeen, struct.unpack("b", pkt[report_pkt_offset -1]),struct.unpack("b", pkt[report_pkt_offset -2])) #  Signal strenght + unknown (hope it's battery life).                                    
                                    elapsed_time=time.time()-tag[3]  # lastseen
                                    if tag[5]==SWITCH_MODE and elapsed_time>=tag[2] : # Upadate only once : after an absence (>timeout). It's back again
                                        threadReqHome = threading.Thread(target=request_thread,args=(tag[4],"HOME",tag[0]))  # IDX, RSSI, name
                                        threadReqHome.start()
                                        logging.warning('Tag %s seen after an absence of %i sec : update presence',tag[0],elapsed_time)
                                    elif tag[5]==REPEAT_MODE and elapsed_time>3 : # in continuous, Every 2 sec
                                        rssi=''.join(c for c in str(struct.unpack("b", pkt[report_pkt_offset -1])) if c in '-0123456789')
                                        threadReqHome = threading.Thread(target=request_thread,args=(tag[4],rssi,tag[0]))   # IDX, RSSI, name
                                        threadReqHome.start()
                                        logging.debug('Tag %s is still there with an RSSI of %s  : update presence with RSSI',tag[0],rssi)
                                    tag[3]=time.time()   # update lastseen
                                    
    sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter )

Re: How to check presence of Beacon ?

Posted: Thursday 02 January 2020 18:32
by alarm_guy1
SORTED NEEDED A BLUETOOTH V4 ADAPTER

Any ideas on getting this working.
If I run sudo more /var/log/check_beacon_presence.log
I get this:
2020-01-02 17:00:22,176 - root - DEBUG - Ok hci0 interface Up n running !
2020-01-02 17:00:22,186 - root - DEBUG - Connect to bluetooth device 0
2020-01-02 17:00:27,192 - root - WARNING - Tag BT_Jo not seen since 35 sec => update absence
2020-01-02 17:00:27,204 - urllib3.connectionpool - DEBUG - Starting new HTTP connection (1): 192.168.2.49:8080
2020-01-02 17:00:27,217 - urllib3.connectionpool - DEBUG - http://192.168.2.49:8080 "GET /json.htm?type=command&param=updateuservariable&idx=4&vname=BT_Jo&vtype=2&vvalue=AWAY HTTP/1.1" 200

If I run:
sudo python test_beacon.py
2020-01-02 17:26:52,646 - root - DEBUG - Ok hci0 interface Up n running !
2020-01-02 17:26:52,646 - root - DEBUG - Connect to bluetooth device 0

However I can see my NUT
sudo hcitool lescan
LE Scan ...

FF:FF:F0:01:2A:CD nut
FF:FF:F0:01:2A:CD (unknown)
Any ideas what i'm missing

Cheers

Re: How to check presence of Beacon ?

Posted: Sunday 19 January 2020 22:52
by Damsee
Hi all,

Wanna try to get this working and it's kind of OK with "mini NUT".

Service is started :

Code: Select all

[Unit]
Description=Beaconing Service
After=multi-user.target

[Service]
User=root
Type=idle
ExecStart=/home/pi/beaconservice.py
Restart=always
RestartSec=5

[Install]
WantedBy=multi-user.target
I changed the script a little bit to use Python 3 and I'm using DZ switch only and no DZ variable :

Code: Select all

#!/usr/bin/python3
# Based on mybeaconservice.py by jmleglise
#   URL : https://github.com/jmleglise/mylittle-domoticz/
########################################################################
#
URL_DOMOTICZ = 'http://127.0.0.1:8080/json.htm?type=command&param=switchlight&idx=PARAM_IDX&switchcmd=PARAM_CMD'
DOMOTICZ_USER=''
DOMOTICZ_PASS=''
SWITCH_MODE=1

#
# Configure your Beacons in the TAG_DATA table with : [Name,MacAddress,Timeout,0,idx,mode]
# Name : the name of the uservariable used in Domoticz
# macAddress : case insensitive
# Timeout is in secondes the elapsed time  without a detection for switching the beacon AWAY. Ie :if your beacon emits every 3 to 8 seondes, a timeout of 15 secondes seems good.
# 0 : used by the script (will keep the time of the last broadcast) 
# idx of the uservariable in Domoticz for this beacon
# mode : SWITCH_MODE = One update per status change / REPEAT_MODE has been disabled and is only available if you use a DZ VAR instead of DZ switch

TAG_DATA = [
  ["Tag_White","ee:8d:ff:be:bd:54",15,0,39,SWITCH_MODE,1],
  ["Tag_Blue","f8:e2:5c:ad:eb:f9",15,0,38,SWITCH_MODE,1]
]

import logging

# choose between DEBUG (log every information) or WARNING (change of state) or CRITICAL (only error)
logLevel=logging.WARNING
logOutFilename='/var/log/beacon_presence.log'       # output LOG : File or console (comment this line to console output)
ABSENCE_FREQUENCY=5  # frequency of the test of absence. in seconde. (without detection, switch "AWAY")

################ Nothing to edit under this line #####################################################################################

import os
import subprocess
import sys
import struct
import bluetooth._bluetooth as bluez
import time
import requests
import signal
import threading

LE_META_EVENT = 0x3e
OGF_LE_CTL=0x08
OCF_LE_SET_SCAN_ENABLE=0x000C
EVT_LE_CONN_COMPLETE=0x01
EVT_LE_ADVERTISING_REPORT=0x02

def packed_bdaddr_to_string(bdaddr_packed):
  return ':'.join('%02x'%i for i in struct.unpack("<BBBBBB", bdaddr_packed[::-1]))

def hci_toggle_le_scan(sock, enable):
  cmd_pkt = struct.pack("<BB", enable, 0x00)
  bluez.hci_send_cmd(sock, OGF_LE_CTL, OCF_LE_SET_SCAN_ENABLE, cmd_pkt)

def handler(signum = None, frame = None):
  time.sleep(1)  #here check if process is done
  sys.exit(0)   
    
for sig in [signal.SIGTERM, signal.SIGINT, signal.SIGHUP, signal.SIGQUIT]:
  signal.signal(sig, handler)

def le_handle_connection_complete(pkt):
  status, handle, role, peer_bdaddr_type = struct.unpack("<BHBB", pkt[0:5])
  device_address = packed_bdaddr_to_string(pkt[5:11])
  interval, latency, supervision_timeout, master_clock_accuracy = struct.unpack("<HHHB", pkt[11:])

def request_thread(idx, cmd, name):
  try:
    url = URL_DOMOTICZ
    url=url.replace('PARAM_IDX',str(idx))
    url=url.replace('PARAM_CMD',str(cmd))
    url=url.replace('PARAM_NAME',str(name))
    result = requests.get(url,auth=(DOMOTICZ_USER, DOMOTICZ_PASS))
    logging.debug(" %s -> %s" % (threading.current_thread(), result))
  except requests.ConnectionError as e:
    logging.critical(' %s Request Failed %s - %s' % (threading.current_thread(), e, url) )

class CheckAbsenceThread(threading.Thread):
  def __init__(self):
    threading.Thread.__init__(self)
  def run(self):
    time.sleep(ABSENCE_FREQUENCY)    
    for tag in TAG_DATA:
      elapsed_time_absence=time.time()-tag[3]
      if elapsed_time_absence>=tag[2] : # sleep execute after the first Home check.
        tag[6]=1
        logging.warning('Tag %s not seen since %i sec => update absence',tag[0],elapsed_time_absence)
        threadReqAway = threading.Thread(target=request_thread,args=(tag[4],"Off",tag[0]))
        threadReqAway.start()
    while True:
      time.sleep(ABSENCE_FREQUENCY)
      for tag in TAG_DATA:
        elapsed_time_absence=time.time()-tag[3]
        if elapsed_time_absence>=tag[2] and elapsed_time_absence<(tag[2]+ABSENCE_FREQUENCY) :  #update when > timeout ant only 1 time , before the next absence check [>15sec <30sec]
          tag[6]=1
          logging.warning('Tag %s not seen since %i sec => update absence',tag[0],elapsed_time_absence)
          threadReqAway = threading.Thread(target=request_thread,args=(tag[4],"Off",tag[0]))
          threadReqAway.start()
            
FORMAT = '%(asctime)s - %(name)s - %(levelname)s - %(message)s'
if "logOutFilename" in globals() :
  logging.basicConfig(format=FORMAT,filename=logOutFilename,level=logLevel)
else:
  logging.basicConfig(format=FORMAT,level=logLevel)

#Reset Bluetooth interface, hci0
os.system("hciconfig hci0 down")
os.system("hciconfig hci0 up")

#Make sure device is up
interface = subprocess.Popen(["hciconfig"], stdout=subprocess.PIPE, shell=True)
(output, err) = interface.communicate()
output = output.decode()

if "RUNNING" in output: #Check return of hciconfig to make sure it's up
  logging.debug('OK hci0 interface is up and running !')
else:
  logging.critical('Error : hci0 interface is NOT running. Do you have a BLE device connected to hci0 ? Check with hciconfig !')
  sys.exit(1)
    
devId = 0
try:
  sock = bluez.hci_open_dev(devId)
  logging.debug('Connect to bluetooth device %i',devId)
except:
  logging.critical('Unable to connect to bluetooth device...')
  sys.exit(1)

old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14)
hci_toggle_le_scan(sock, 0x01)

for tag in TAG_DATA:
  tag[3]=time.time()-tag[2]  # initiate lastseen of every beacon "timeout" sec ago. = Every beacon will be AWAY. And so, beacons here will update 

th=CheckAbsenceThread()
th.daemon=True
th.start()

while True:
  old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14)
  flt = bluez.hci_filter_new()
  bluez.hci_filter_all_events(flt)
  bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT)
  sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt )
    
  pkt = sock.recv(255)
  ptype, event, plen = struct.unpack("BBB", pkt[:3])

  if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI:
    i =0
  elif event == bluez.EVT_NUM_COMP_PKTS:
    i =0 
  elif event == bluez.EVT_DISCONN_COMPLETE:
    i =0 
  elif event == LE_META_EVENT:
    subevent, = struct.unpack("B", pkt[3:4])
    pkt = pkt[4:]
    if subevent == EVT_LE_CONN_COMPLETE:
      le_handle_connection_complete(pkt)
    elif subevent == EVT_LE_ADVERTISING_REPORT:
      num_reports = struct.unpack("B", pkt[0:1])[0]
      report_pkt_offset = 0
      for i in range(0, num_reports):
        macAdressSeen=packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9])
        for tag in TAG_DATA:
          if macAdressSeen.lower() == tag[1].lower():  # MAC ADDRESS
            #rssi = struct.unpack("b", pkt[-1:])[0]
            #logging.debug('Tag %s Detected %s - RSSI %s - DATA unknown %s', tag[0], macAdressSeen, rssi,struct.unpack("b", pkt[-2:])[0]) #  Signal strenght + unknown (hope it's battery life).                                    
            elapsed_time=time.time()-tag[3]  # lastseen
            if tag[5]==SWITCH_MODE and tag[6]==1 : # Update only once : after an absence (>timeout). It's back again
              tag[6]=0
              threadReqHome = threading.Thread(target=request_thread,args=(tag[4],"On",tag[0]))
              threadReqHome.start()
              logging.warning('Tag %s seen after an absence of %i sec : update presence',tag[0],elapsed_time)
            tag[3]=time.time()   # update lastseen                           
  sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter )
However... I am facing quite a lot false/positive (too many actually) :

Code: Select all

2020-01-19 00:01:39,861 - root - WARNING - Tag Tag_White not seen since 27 sec => update absence
2020-01-19 00:01:43,322 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 00:04:50,028 - root - WARNING - Tag Tag_White not seen since 28 sec => update absence
2020-01-19 00:04:52,469 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 00:06:30,135 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 00:06:32,826 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 00:07:00,171 - root - WARNING - Tag Tag_White not seen since 23 sec => update absence
2020-01-19 00:07:03,684 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 00:24:21,041 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 00:24:21,907 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 00:29:01,286 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 00:29:03,668 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 01:14:23,523 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 01:14:24,705 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 01:26:34,147 - root - WARNING - Tag Tag_White not seen since 23 sec => update absence
2020-01-19 01:26:34,200 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 02:11:30,844 - root - WARNING - Tag Tag_White seen after an absence of 24 sec : update presence
2020-01-19 02:11:33,148 - root - WARNING - Tag Tag_Blue seen after an absence of 27 sec : update presence
2020-01-19 02:20:55,742 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 02:20:56,072 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 02:36:36,521 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 02:36:37,816 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 02:56:57,501 - root - WARNING - Tag Tag_White not seen since 23 sec => update absence
2020-01-19 02:56:57,539 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 03:40:19,738 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 03:40:22,818 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 03:41:29,813 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 03:41:32,270 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 04:26:21,907 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 04:26:30,214 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 04:30:32,131 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 04:30:33,395 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 04:52:13,169 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 04:52:14,134 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 05:05:53,888 - root - WARNING - Tag Tag_White not seen since 28 sec => update absence
2020-01-19 05:05:56,270 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 05:25:54,834 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 05:26:08,265 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 05:42:25,594 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 05:42:32,461 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 05:53:36,202 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
2020-01-19 05:53:36,302 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 06:08:37,021 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 06:08:39,446 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 06:26:28,090 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
2020-01-19 06:26:36,427 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 06:43:59,080 - root - WARNING - Tag Tag_White not seen since 27 sec => update absence
2020-01-19 06:44:02,409 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 06:53:39,633 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 06:53:41,379 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 07:09:30,328 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
2020-01-19 07:09:38,510 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 07:20:10,917 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 07:20:23,089 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 07:22:01,031 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 07:22:07,311 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 07:29:21,212 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 07:29:42,769 - root - WARNING - Tag Tag_White seen after an absence of 46 sec : update presence
2020-01-19 07:41:41,879 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 07:41:56,097 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 08:02:23,089 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
2020-01-19 08:02:23,458 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 08:08:13,435 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 08:08:14,684 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 08:14:23,766 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 08:14:25,231 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 08:19:04,047 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 08:19:06,990 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 08:21:24,155 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 08:21:25,949 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 08:49:35,666 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 08:49:36,483 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 08:52:55,872 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 08:53:04,955 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 09:03:16,462 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 09:03:18,630 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 09:20:57,489 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 09:21:00,166 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 09:32:38,116 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 09:32:38,745 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 09:44:28,735 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 09:44:28,991 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 10:02:19,752 - root - WARNING - Tag Tag_Blue not seen since 24 sec => update absence
2020-01-19 10:03:04,345 - root - WARNING - Tag Tag_Blue seen after an absence of 68 sec : update presence
2020-01-19 10:14:40,359 - root - WARNING - Tag Tag_White not seen since 28 sec => update absence
2020-01-19 10:17:20,116 - root - WARNING - Tag Tag_White seen after an absence of 187 sec : update presence
2020-01-19 10:17:40,542 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 10:38:41,564 - root - WARNING - Tag Tag_Blue not seen since 22 sec => update absence
2020-01-19 10:38:42,676 - root - WARNING - Tag Tag_Blue seen after an absence of 23 sec : update presence
2020-01-19 11:52:54,206 - root - WARNING - Tag Tag_Blue not seen since 24 sec => update absence
2020-01-19 11:53:24,184 - root - WARNING - Tag Tag_Blue seen after an absence of 54 sec : update presence
2020-01-19 11:53:44,262 - root - WARNING - Tag Tag_Blue not seen since 20 sec => update absence
2020-01-19 11:54:02,790 - root - WARNING - Tag Tag_Blue seen after an absence of 38 sec : update presence
2020-01-19 11:54:24,307 - root - WARNING - Tag Tag_Blue not seen since 21 sec => update absence
2020-01-19 12:30:27,773 - root - WARNING - Tag Tag_Blue seen after an absence of 2184 sec : update presence
2020-01-19 12:30:32,816 - root - WARNING - Tag Tag_White seen after an absence of 7992 sec : update presence
2020-01-19 12:30:56,187 - root - WARNING - Tag Tag_White not seen since 23 sec => update absence
2020-01-19 12:30:56,193 - root - WARNING - Tag Tag_Blue not seen since 28 sec => update absence
2020-01-19 12:45:11,713 - root - WARNING - Tag Tag_Blue seen after an absence of 883 sec : update presence
2020-01-19 12:46:03,066 - root - WARNING - Tag Tag_White seen after an absence of 930 sec : update presence
2020-01-19 12:46:06,888 - root - WARNING - Tag Tag_Blue not seen since 23 sec => update absence
2020-01-19 12:46:28,925 - root - WARNING - Tag Tag_Blue seen after an absence of 45 sec : update presence
2020-01-19 12:46:46,919 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 12:46:56,934 - root - WARNING - Tag Tag_Blue not seen since 28 sec => update absence
2020-01-19 12:52:22,590 - root - WARNING - Tag Tag_White seen after an absence of 361 sec : update presence
2020-01-19 12:52:33,920 - root - WARNING - Tag Tag_Blue seen after an absence of 364 sec : update presence
2020-01-19 12:52:47,282 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 12:52:57,298 - root - WARNING - Tag Tag_Blue not seen since 23 sec => update absence
2020-01-19 12:54:04,826 - root - WARNING - Tag Tag_Blue seen after an absence of 90 sec : update presence
2020-01-19 12:54:37,402 - root - WARNING - Tag Tag_Blue not seen since 20 sec => update absence
2020-01-19 12:54:49,529 - root - WARNING - Tag Tag_Blue seen after an absence of 33 sec : update presence
2020-01-19 12:55:47,472 - root - WARNING - Tag Tag_Blue not seen since 23 sec => update absence
2020-01-19 12:56:01,629 - root - WARNING - Tag Tag_Blue seen after an absence of 37 sec : update presence
2020-01-19 12:56:37,522 - root - WARNING - Tag Tag_Blue not seen since 20 sec => update absence
2020-01-19 12:57:41,242 - root - WARNING - Tag Tag_White seen after an absence of 318 sec : update presence
2020-01-19 12:58:47,629 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
Both TAGS were at home today...

Since i'm also using l2ping to ping the Bluetooth of my phone and i can't use l2ping to ping "mini NUT", is anyone knowing a bluetooth beacon which responds to l2ping command ?

Thank you

Re: How to check presence of Beacon ?

Posted: Friday 07 February 2020 13:45
by Artursd
pi@raspberrypi:~ $ sudo more /var/log/check_beacon_presence.log
2020-02-07 13:34:22,736 - root - CRITICAL - <Thread(Thread-2, started 1966077024)> Request Failed HTTPSConnectionPool(host='192.168.1.128', port=8080
): Max retries exceeded with url: /json.htm?type=command&param=updateuservariable&idx=7&vname=Nut_Egita&vtype=2&vvalue=HOME (Caused by SSLError(SSLErr
or("bad handshake: Error([('SSL routines', 'ssl3_get_record', 'wrong version number')],)",),)) - https://192.168.1.128:8080/json.htm?type=command&para
m=updateuservariable&idx=7&vname=Nut_Egita&vtype=2&vvalue=HOME
2020-02-07 13:34:24,412 - root - CRITICAL - <Thread(Thread-3, started 1966077024)> Request Failed HTTPSConnectionPool(host='192.168.1.128', port=8080
): Max retries exceeded with url: /json.htm?type=command&param=updateuservariable&idx=8&vname=Nut_Arturs&vtype=2&vvalue=HOME (Caused by SSLError(SSLEr
ror("bad handshake: Error([('SSL routines', 'ssl3_get_record', 'wrong version number')],)",),)) - https://192.168.1.128:8080/json.htm?type=command&par
am=updateuservariable&idx=8&vname=Nut_Arturs&vtype=2&vvalue=HOME

Re: How to check presence of Beacon ?

Posted: Friday 07 February 2020 13:46
by Artursd
Что это за ошибка ????

Re: How to check presence of Beacon ?

Posted: Friday 07 February 2020 14:11
by Artursd
pi@raspberrypi:~ $ sudo python /usr/local/bin/check_beacon_presence.py
2020-02-07 15:08:45,640 - root - DEBUG - Ok hci0 interface Up n running !
2020-02-07 15:08:45,641 - root - DEBUG - Connect to bluetooth device 0
2020-02-07 15:08:48,783 - root - DEBUG - Tag Nut_Egita Detected ed:c5:51:27:23:96 - RSSI (-76,) - DATA unknown (-106,)
2020-02-07 15:08:48,790 - root - WARNING - Tag Nut_Egita seen after an absence of 33 sec : update presence
2020-02-07 15:08:48,791 - urllib3.connectionpool - DEBUG - Starting new HTTPS connection (1): 192.168.1.128:8080
2020-02-07 15:08:48,850 - root - CRITICAL - <Thread(Thread-2, started 1967125600)> Request Failed HTTPSConnectionPool(host='192.168.1.128', port=8080): Max retries exceeded with url: /json.htm?type=command&param=updateuservariable&idx=7&vname=Nut_Egita&vtype=2&vvalue=HOME (Caused by SSLError(SSLError("bad handshake: Error([('SSL routines', 'ssl3_get_record', 'wrong version number')],)",),)) - https://192.168.1.128:8080/json.htm?typ ... value=HOME

Re: How to check presence of Beacon ?

Posted: Sunday 01 March 2020 14:17
by JPdom
Hello Damsee

Do you find a solution to avoid false detection ?

Thank you
Damsee wrote: Sunday 19 January 2020 22:52 Hi all,

Wanna try to get this working and it's kind of OK with "mini NUT".

Service is started :

Code: Select all

[Unit]
Description=Beaconing Service
After=multi-user.target

[Service]
User=root
Type=idle
ExecStart=/home/pi/beaconservice.py
Restart=always
RestartSec=5

[Install]
WantedBy=multi-user.target
I changed the script a little bit to use Python 3 and I'm using DZ switch only and no DZ variable :

Code: Select all

#!/usr/bin/python3
# Based on mybeaconservice.py by jmleglise
#   URL : https://github.com/jmleglise/mylittle-domoticz/
########################################################################
#
URL_DOMOTICZ = 'http://127.0.0.1:8080/json.htm?type=command&param=switchlight&idx=PARAM_IDX&switchcmd=PARAM_CMD'
DOMOTICZ_USER=''
DOMOTICZ_PASS=''
SWITCH_MODE=1

#
# Configure your Beacons in the TAG_DATA table with : [Name,MacAddress,Timeout,0,idx,mode]
# Name : the name of the uservariable used in Domoticz
# macAddress : case insensitive
# Timeout is in secondes the elapsed time  without a detection for switching the beacon AWAY. Ie :if your beacon emits every 3 to 8 seondes, a timeout of 15 secondes seems good.
# 0 : used by the script (will keep the time of the last broadcast) 
# idx of the uservariable in Domoticz for this beacon
# mode : SWITCH_MODE = One update per status change / REPEAT_MODE has been disabled and is only available if you use a DZ VAR instead of DZ switch

TAG_DATA = [
  ["Tag_White","ee:8d:ff:be:bd:54",15,0,39,SWITCH_MODE,1],
  ["Tag_Blue","f8:e2:5c:ad:eb:f9",15,0,38,SWITCH_MODE,1]
]

import logging

# choose between DEBUG (log every information) or WARNING (change of state) or CRITICAL (only error)
logLevel=logging.WARNING
logOutFilename='/var/log/beacon_presence.log'       # output LOG : File or console (comment this line to console output)
ABSENCE_FREQUENCY=5  # frequency of the test of absence. in seconde. (without detection, switch "AWAY")

################ Nothing to edit under this line #####################################################################################

import os
import subprocess
import sys
import struct
import bluetooth._bluetooth as bluez
import time
import requests
import signal
import threading

LE_META_EVENT = 0x3e
OGF_LE_CTL=0x08
OCF_LE_SET_SCAN_ENABLE=0x000C
EVT_LE_CONN_COMPLETE=0x01
EVT_LE_ADVERTISING_REPORT=0x02

def packed_bdaddr_to_string(bdaddr_packed):
  return ':'.join('%02x'%i for i in struct.unpack("<BBBBBB", bdaddr_packed[::-1]))

def hci_toggle_le_scan(sock, enable):
  cmd_pkt = struct.pack("<BB", enable, 0x00)
  bluez.hci_send_cmd(sock, OGF_LE_CTL, OCF_LE_SET_SCAN_ENABLE, cmd_pkt)

def handler(signum = None, frame = None):
  time.sleep(1)  #here check if process is done
  sys.exit(0)   
    
for sig in [signal.SIGTERM, signal.SIGINT, signal.SIGHUP, signal.SIGQUIT]:
  signal.signal(sig, handler)

def le_handle_connection_complete(pkt):
  status, handle, role, peer_bdaddr_type = struct.unpack("<BHBB", pkt[0:5])
  device_address = packed_bdaddr_to_string(pkt[5:11])
  interval, latency, supervision_timeout, master_clock_accuracy = struct.unpack("<HHHB", pkt[11:])

def request_thread(idx, cmd, name):
  try:
    url = URL_DOMOTICZ
    url=url.replace('PARAM_IDX',str(idx))
    url=url.replace('PARAM_CMD',str(cmd))
    url=url.replace('PARAM_NAME',str(name))
    result = requests.get(url,auth=(DOMOTICZ_USER, DOMOTICZ_PASS))
    logging.debug(" %s -> %s" % (threading.current_thread(), result))
  except requests.ConnectionError as e:
    logging.critical(' %s Request Failed %s - %s' % (threading.current_thread(), e, url) )

class CheckAbsenceThread(threading.Thread):
  def __init__(self):
    threading.Thread.__init__(self)
  def run(self):
    time.sleep(ABSENCE_FREQUENCY)    
    for tag in TAG_DATA:
      elapsed_time_absence=time.time()-tag[3]
      if elapsed_time_absence>=tag[2] : # sleep execute after the first Home check.
        tag[6]=1
        logging.warning('Tag %s not seen since %i sec => update absence',tag[0],elapsed_time_absence)
        threadReqAway = threading.Thread(target=request_thread,args=(tag[4],"Off",tag[0]))
        threadReqAway.start()
    while True:
      time.sleep(ABSENCE_FREQUENCY)
      for tag in TAG_DATA:
        elapsed_time_absence=time.time()-tag[3]
        if elapsed_time_absence>=tag[2] and elapsed_time_absence<(tag[2]+ABSENCE_FREQUENCY) :  #update when > timeout ant only 1 time , before the next absence check [>15sec <30sec]
          tag[6]=1
          logging.warning('Tag %s not seen since %i sec => update absence',tag[0],elapsed_time_absence)
          threadReqAway = threading.Thread(target=request_thread,args=(tag[4],"Off",tag[0]))
          threadReqAway.start()
            
FORMAT = '%(asctime)s - %(name)s - %(levelname)s - %(message)s'
if "logOutFilename" in globals() :
  logging.basicConfig(format=FORMAT,filename=logOutFilename,level=logLevel)
else:
  logging.basicConfig(format=FORMAT,level=logLevel)

#Reset Bluetooth interface, hci0
os.system("hciconfig hci0 down")
os.system("hciconfig hci0 up")

#Make sure device is up
interface = subprocess.Popen(["hciconfig"], stdout=subprocess.PIPE, shell=True)
(output, err) = interface.communicate()
output = output.decode()

if "RUNNING" in output: #Check return of hciconfig to make sure it's up
  logging.debug('OK hci0 interface is up and running !')
else:
  logging.critical('Error : hci0 interface is NOT running. Do you have a BLE device connected to hci0 ? Check with hciconfig !')
  sys.exit(1)
    
devId = 0
try:
  sock = bluez.hci_open_dev(devId)
  logging.debug('Connect to bluetooth device %i',devId)
except:
  logging.critical('Unable to connect to bluetooth device...')
  sys.exit(1)

old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14)
hci_toggle_le_scan(sock, 0x01)

for tag in TAG_DATA:
  tag[3]=time.time()-tag[2]  # initiate lastseen of every beacon "timeout" sec ago. = Every beacon will be AWAY. And so, beacons here will update 

th=CheckAbsenceThread()
th.daemon=True
th.start()

while True:
  old_filter = sock.getsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, 14)
  flt = bluez.hci_filter_new()
  bluez.hci_filter_all_events(flt)
  bluez.hci_filter_set_ptype(flt, bluez.HCI_EVENT_PKT)
  sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, flt )
    
  pkt = sock.recv(255)
  ptype, event, plen = struct.unpack("BBB", pkt[:3])

  if event == bluez.EVT_INQUIRY_RESULT_WITH_RSSI:
    i =0
  elif event == bluez.EVT_NUM_COMP_PKTS:
    i =0 
  elif event == bluez.EVT_DISCONN_COMPLETE:
    i =0 
  elif event == LE_META_EVENT:
    subevent, = struct.unpack("B", pkt[3:4])
    pkt = pkt[4:]
    if subevent == EVT_LE_CONN_COMPLETE:
      le_handle_connection_complete(pkt)
    elif subevent == EVT_LE_ADVERTISING_REPORT:
      num_reports = struct.unpack("B", pkt[0:1])[0]
      report_pkt_offset = 0
      for i in range(0, num_reports):
        macAdressSeen=packed_bdaddr_to_string(pkt[report_pkt_offset + 3:report_pkt_offset + 9])
        for tag in TAG_DATA:
          if macAdressSeen.lower() == tag[1].lower():  # MAC ADDRESS
            #rssi = struct.unpack("b", pkt[-1:])[0]
            #logging.debug('Tag %s Detected %s - RSSI %s - DATA unknown %s', tag[0], macAdressSeen, rssi,struct.unpack("b", pkt[-2:])[0]) #  Signal strenght + unknown (hope it's battery life).                                    
            elapsed_time=time.time()-tag[3]  # lastseen
            if tag[5]==SWITCH_MODE and tag[6]==1 : # Update only once : after an absence (>timeout). It's back again
              tag[6]=0
              threadReqHome = threading.Thread(target=request_thread,args=(tag[4],"On",tag[0]))
              threadReqHome.start()
              logging.warning('Tag %s seen after an absence of %i sec : update presence',tag[0],elapsed_time)
            tag[3]=time.time()   # update lastseen                           
  sock.setsockopt( bluez.SOL_HCI, bluez.HCI_FILTER, old_filter )
However... I am facing quite a lot false/positive (too many actually) :

Code: Select all

2020-01-19 00:01:39,861 - root - WARNING - Tag Tag_White not seen since 27 sec => update absence
2020-01-19 00:01:43,322 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 00:04:50,028 - root - WARNING - Tag Tag_White not seen since 28 sec => update absence
2020-01-19 00:04:52,469 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 00:06:30,135 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 00:06:32,826 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 00:07:00,171 - root - WARNING - Tag Tag_White not seen since 23 sec => update absence
2020-01-19 00:07:03,684 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 00:24:21,041 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 00:24:21,907 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 00:29:01,286 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 00:29:03,668 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 01:14:23,523 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 01:14:24,705 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 01:26:34,147 - root - WARNING - Tag Tag_White not seen since 23 sec => update absence
2020-01-19 01:26:34,200 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 02:11:30,844 - root - WARNING - Tag Tag_White seen after an absence of 24 sec : update presence
2020-01-19 02:11:33,148 - root - WARNING - Tag Tag_Blue seen after an absence of 27 sec : update presence
2020-01-19 02:20:55,742 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 02:20:56,072 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 02:36:36,521 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 02:36:37,816 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 02:56:57,501 - root - WARNING - Tag Tag_White not seen since 23 sec => update absence
2020-01-19 02:56:57,539 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 03:40:19,738 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 03:40:22,818 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 03:41:29,813 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 03:41:32,270 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 04:26:21,907 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 04:26:30,214 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 04:30:32,131 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 04:30:33,395 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 04:52:13,169 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 04:52:14,134 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 05:05:53,888 - root - WARNING - Tag Tag_White not seen since 28 sec => update absence
2020-01-19 05:05:56,270 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 05:25:54,834 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 05:26:08,265 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 05:42:25,594 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 05:42:32,461 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 05:53:36,202 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
2020-01-19 05:53:36,302 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 06:08:37,021 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 06:08:39,446 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 06:26:28,090 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
2020-01-19 06:26:36,427 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 06:43:59,080 - root - WARNING - Tag Tag_White not seen since 27 sec => update absence
2020-01-19 06:44:02,409 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 06:53:39,633 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 06:53:41,379 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 07:09:30,328 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
2020-01-19 07:09:38,510 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 07:20:10,917 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 07:20:23,089 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 07:22:01,031 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 07:22:07,311 - root - WARNING - Tag Tag_White seen after an absence of 30 sec : update presence
2020-01-19 07:29:21,212 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 07:29:42,769 - root - WARNING - Tag Tag_White seen after an absence of 46 sec : update presence
2020-01-19 07:41:41,879 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 07:41:56,097 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 08:02:23,089 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
2020-01-19 08:02:23,458 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 08:08:13,435 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 08:08:14,684 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 08:14:23,766 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 08:14:25,231 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 08:19:04,047 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 08:19:06,990 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 08:21:24,155 - root - WARNING - Tag Tag_White not seen since 21 sec => update absence
2020-01-19 08:21:25,949 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 08:49:35,666 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 08:49:36,483 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 08:52:55,872 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 08:53:04,955 - root - WARNING - Tag Tag_White seen after an absence of 34 sec : update presence
2020-01-19 09:03:16,462 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 09:03:18,630 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 09:20:57,489 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 09:21:00,166 - root - WARNING - Tag Tag_White seen after an absence of 27 sec : update presence
2020-01-19 09:32:38,116 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 09:32:38,745 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 09:44:28,735 - root - WARNING - Tag Tag_White not seen since 22 sec => update absence
2020-01-19 09:44:28,991 - root - WARNING - Tag Tag_White seen after an absence of 23 sec : update presence
2020-01-19 10:02:19,752 - root - WARNING - Tag Tag_Blue not seen since 24 sec => update absence
2020-01-19 10:03:04,345 - root - WARNING - Tag Tag_Blue seen after an absence of 68 sec : update presence
2020-01-19 10:14:40,359 - root - WARNING - Tag Tag_White not seen since 28 sec => update absence
2020-01-19 10:17:20,116 - root - WARNING - Tag Tag_White seen after an absence of 187 sec : update presence
2020-01-19 10:17:40,542 - root - WARNING - Tag Tag_White not seen since 20 sec => update absence
2020-01-19 10:38:41,564 - root - WARNING - Tag Tag_Blue not seen since 22 sec => update absence
2020-01-19 10:38:42,676 - root - WARNING - Tag Tag_Blue seen after an absence of 23 sec : update presence
2020-01-19 11:52:54,206 - root - WARNING - Tag Tag_Blue not seen since 24 sec => update absence
2020-01-19 11:53:24,184 - root - WARNING - Tag Tag_Blue seen after an absence of 54 sec : update presence
2020-01-19 11:53:44,262 - root - WARNING - Tag Tag_Blue not seen since 20 sec => update absence
2020-01-19 11:54:02,790 - root - WARNING - Tag Tag_Blue seen after an absence of 38 sec : update presence
2020-01-19 11:54:24,307 - root - WARNING - Tag Tag_Blue not seen since 21 sec => update absence
2020-01-19 12:30:27,773 - root - WARNING - Tag Tag_Blue seen after an absence of 2184 sec : update presence
2020-01-19 12:30:32,816 - root - WARNING - Tag Tag_White seen after an absence of 7992 sec : update presence
2020-01-19 12:30:56,187 - root - WARNING - Tag Tag_White not seen since 23 sec => update absence
2020-01-19 12:30:56,193 - root - WARNING - Tag Tag_Blue not seen since 28 sec => update absence
2020-01-19 12:45:11,713 - root - WARNING - Tag Tag_Blue seen after an absence of 883 sec : update presence
2020-01-19 12:46:03,066 - root - WARNING - Tag Tag_White seen after an absence of 930 sec : update presence
2020-01-19 12:46:06,888 - root - WARNING - Tag Tag_Blue not seen since 23 sec => update absence
2020-01-19 12:46:28,925 - root - WARNING - Tag Tag_Blue seen after an absence of 45 sec : update presence
2020-01-19 12:46:46,919 - root - WARNING - Tag Tag_White not seen since 25 sec => update absence
2020-01-19 12:46:56,934 - root - WARNING - Tag Tag_Blue not seen since 28 sec => update absence
2020-01-19 12:52:22,590 - root - WARNING - Tag Tag_White seen after an absence of 361 sec : update presence
2020-01-19 12:52:33,920 - root - WARNING - Tag Tag_Blue seen after an absence of 364 sec : update presence
2020-01-19 12:52:47,282 - root - WARNING - Tag Tag_White not seen since 24 sec => update absence
2020-01-19 12:52:57,298 - root - WARNING - Tag Tag_Blue not seen since 23 sec => update absence
2020-01-19 12:54:04,826 - root - WARNING - Tag Tag_Blue seen after an absence of 90 sec : update presence
2020-01-19 12:54:37,402 - root - WARNING - Tag Tag_Blue not seen since 20 sec => update absence
2020-01-19 12:54:49,529 - root - WARNING - Tag Tag_Blue seen after an absence of 33 sec : update presence
2020-01-19 12:55:47,472 - root - WARNING - Tag Tag_Blue not seen since 23 sec => update absence
2020-01-19 12:56:01,629 - root - WARNING - Tag Tag_Blue seen after an absence of 37 sec : update presence
2020-01-19 12:56:37,522 - root - WARNING - Tag Tag_Blue not seen since 20 sec => update absence
2020-01-19 12:57:41,242 - root - WARNING - Tag Tag_White seen after an absence of 318 sec : update presence
2020-01-19 12:58:47,629 - root - WARNING - Tag Tag_White not seen since 26 sec => update absence
Both TAGS were at home today...

Since i'm also using l2ping to ping the Bluetooth of my phone and i can't use l2ping to ping "mini NUT", is anyone knowing a bluetooth beacon which responds to l2ping command ?

Thank you