Embedded Python to determine the calling deviceID

Posted on
Wed Aug 25, 2021 1:48 pm
jjpmir04 offline
Posts: 15
Joined: Aug 25, 2021

Embedded Python to determine the calling deviceID

Hi, I want to enhance an embedded python script executing in the context of a trigger that can determine the deviceID of the device associated with trigger that is calling the script.

The reason for this is to be able to write generic scripts that will be able to configure themselves. Consider 100 sensors and the disadvantage to have a unique script for each of them with a hardcoded deviceID. Having an external script is something that I'm learning about but it has the same problem of not knowing it's deviceID

So here is my situation:

Device: Leak Sensor 1873696535
Trigger: 254412145

What I am asking for help with, is what resource is available so that within the embedded script, I can determine the calling device 1873696535

Something like:
myDeviceID = indigo.devices[ 'callingDeviceID' ]

Thank you very much in advance,

Jim

Posted on
Wed Aug 25, 2021 2:03 pm
jjpmir04 offline
Posts: 15
Joined: Aug 25, 2021

Re: Embedded Python to determine the calling deviceID

Some additional information:
plugin "Global Property Manager 2021.1.0" reveals the following but it still starts with the problem that I don't know the invoking triggerID either.

============== Print for each Trigger devices/variables that trigger them =============
Trigger Name Trig.ID Trig.Source DeviceID Type Dev/Var/Plugin-ID Source-D/V/P-Name Other info
Water Leak Detected - send log 285772180 device 1873696535 006 - Leak Sensor state: onOffState-- changeType: BecomesTrue-- compareTo:
Water Leak Sensor Activated 254412145 device 1873696535 006 - Leak Sensor state: onOffState-- changeType: BecomesTrue-- compareTo:
Water Leak Sensor Activated Si 1579500373 device 1873696535 006 - Leak Sensor state: onOffState-- changeType: BecomesTrue-- compareTo:
Water Leak Sensor High Temp Co 1020036654 device 77470459 006 - Temperature state: sensorValue-- changeType: BecomesGreaterThan-- compareTo: 72
Water Sensor Battery Low 98812762 device 1873696535 006 - Leak Sensor state: batteryLevel-- changeType: BecomesLessThan-- compareTo: 20

Posted on
Wed Aug 25, 2021 2:05 pm
jjpmir04 offline
Posts: 15
Joined: Aug 25, 2021

Re: Embedded Python to determine the calling deviceID

Here is a screen shot - easier to read
Attachments
Screen Shot 2021-08-25 at 3.03.44 PM.png
Screen Shot 2021-08-25 at 3.03.44 PM.png (44.24 KiB) Viewed 2525 times

Posted on
Wed Aug 25, 2021 2:14 pm
jay (support) offline
Site Admin
User avatar
Posts: 18220
Joined: Mar 19, 2008
Location: Austin, Texas

Re: Embedded Python to determine the calling deviceID

That's not currently possible using built-in capabilities because actions are scheduled asynchronously from whatever event started them and we don't pass through the triggering event information. It's on the request list, but it would be an extremely pervasive and low-level change to the server so it's never made it to the top of the priority list.

There are a couple of plugins that might do what you need: Group Change Listener and Group Trigger.

Jay (Indigo Support)
Twitter | Facebook | LinkedIn

Posted on
Wed Aug 25, 2021 6:15 pm
jjpmir04 offline
Posts: 15
Joined: Aug 25, 2021

Re: Embedded Python to determine the calling deviceID

Thanks Jay, I really appreciate the prompt response.
I was wishing for a different answer but I understand you can't customize your platform for everyone.

Just to confirm, I am not interested in Triggers ID, only getting the Device ID that is being handled by it's trigger.

In any case, I am working on a very large application, we will have over 600 sensors (not counting the multi-sensor devices). This is on the Indigo platform and my job is to design a device response programming and maintenance system that will allow us to customize the treatment of each sensor events.

It's going to be a maintenance challenge, as the handling information for the sensors experiences around 10% change each year.

Best regards,

Jim Prete

Posted on
Thu Aug 26, 2021 5:21 am
DaveL17 offline
User avatar
Posts: 6755
Joined: Aug 20, 2013
Location: Chicago, IL, USA

Re: Embedded Python to determine the calling deviceID

One option that you might consider -- If I'm thinking about this the right way and if it's within your capabilities -- is to consider a custom Indigo plugin to do what you need. You could:

  1. Subscribe to device updates where Indigo reports changes to your plugin with indigo.devices.subscribeToChanges().
  2. Filter those device updates to only the sensors you're interested in -- by type, or by naming convention, or something similar.
  3. Act on the information to fire the various triggers, log data, etc.

One benefit of Indigo plugins is that they can run 24/7 (unlike embedded scripts). They also have access to information that's exposed within the Indigo plugin framework. It may feel like a plugin is a big leap from an embedded script, but at their base, Indigo plugins are just Python scripts in themselves.

p.s. 600 sensors!

I came here to drink milk and kick ass....and I've just finished my milk.

[My Plugins] - [My Forums]

Posted on
Thu Aug 26, 2021 5:55 am
kw123 offline
User avatar
Posts: 8366
Joined: May 12, 2013
Location: Dallas, TX

Re: Embedded Python to determine the calling deviceID

That’s an idea for a cool plugin

Input: Config table for device/state/condition and action to follow


Sent from my iPhone using Tapatalk

Posted on
Fri Aug 27, 2021 6:13 am
jjpmir04 offline
Posts: 15
Joined: Aug 25, 2021

Re: Embedded Python to determine the calling deviceID

Still working on this... I am iterating through the indigo.devices to find the entity with the property onOffState set to on.

It's actually working fine - see here.
 1384093992 006 - Humidity 6 States : (dict)
     sensorValue : 64.000000 (real)
     sensorValue.ui : 64% (string)
   Script                          1873696535 006 - Leak Sensor 6 States : (dict)
     batteryLevel : 100 (integer)
     batteryLevel.ui : 100% (string)
     onOffState : off (on/off bool)
   Script                          316739640 006 - Tamper 6 States : (dict)
     onOffState : off (on/off bool)
   Script Error                    embedded script: 'ascii' codec can't encode character u'\xb0' in position 79: ordinal not in range(128)
   Script Error                    Exception Traceback (most recent call shown last):

     embedded script, line 15, at top level
UnicodeEncodeError: 'ascii' codec can't encode character u'\xb0' in position 79: ordinal not in range(128)

embedded script: 'key onOffState not found in dict'
   Script Error                    Exception Traceback (most recent call shown last):

     embedded script, line 16, at top level
KeyError: 'key onOffState not found in dict'


Just when it it hits an entity that does not have that property python then throws an exception which I am having trouble capturing in my flow.
Code: Select all
for scanDevice in indigo.devices:
   indigo.server.log ( str( scanDevice.id ), scanDevice.name )
   try:
      deviceState = str( scanDevice.onState )
   except:
      indigo.server.log ( "In the except section" )

Also, since everything is being scheduled async, I thought a sleep of 3 seconds would ensure that all of the various triggers and actions would be certain to be fired before I am inspecting the target property.

Thanks for the feedback. Jim

[MODERATOR NOTE]: I put your code snippit above in code tags so it's formatted correctly - you'll want to do that to any code that you post since indentation in Python is required for blocks so you want to show that as well.

Posted on
Fri Aug 27, 2021 6:36 am
kw123 offline
User avatar
Posts: 8366
Joined: May 12, 2013
Location: Dallas, TX

Re: Embedded Python to determine the calling deviceID

try this:
Code: Select all
indigo.server.log(u"             id, Name                                  onstate: ")
for dev in indigo.devices:
   if "onOffState" in dev.states:
      indigo.server.log(u"{:15d}, {:35s}, {}".format(dev.id, dev.name,dev.states["onOffState"]) )

returns something like this:
Code: Select all
   Script                                       id, Name                                 onstate:
   Script                               1917579118, 0-11-i2c-relay-1                   , False
   Script                                853890143, AP_3_balkony                       , True
   Script                               1805049652, AP_3_unifi                         , True

Karl

the >> u" << is important otherwise names with unicode characters throw an error

Posted on
Fri Aug 27, 2021 8:52 am
jay (support) offline
Site Admin
User avatar
Posts: 18220
Joined: Mar 19, 2008
Location: Austin, Texas

Re: Embedded Python to determine the calling deviceID

To more directly address your question about why the exception isn't being caught, I don't see how it's not. However, is that the full script? I don't see how your code snippit is generating the log snippit that you posted.

Jay (Indigo Support)
Twitter | Facebook | LinkedIn

Posted on
Fri Aug 27, 2021 1:34 pm
jjpmir04 offline
Posts: 15
Joined: Aug 25, 2021

Re: Embedded Python to determine the calling deviceID

Thanks for the continued support!! Greatly appreciated..

This is the code snippet:
Code: Select all
for scanDevice in indigo.devices:
   indigo.server.log ( str( scanDevice.id ), scanDevice.name )
   try:
      deviceState = str( scanDevice.onState )
   except:
      indigo.server.log ( "In the except section" )
   
   indigo.server.log ( str(scanDevice.onState ) )


How to classify log entries to demonstrate what's happening during an actual trigger event
Quote? List?
Will the sleep of 3 seconds give the underlying event enough time to populate this property?

Thank you in advance.
This log was recorded when the code was tested in the editing environment .
Log Entries:
    Aug 27, 2021 at 2:19:53 PM
    006 - Humidity 1384093992
    Script None
    006 - Leak Sensor 1873696535
    Script False
    006 - Tamper 316739640
    Script False
    006 - Temperature 77470459
    Script None
    007 - Z-Wave Repeater (ZW189) 1219598056
    Script In the except section
    Script Error embedded script: 'Device' object has no attribute 'onState'
    Script Error Exception Traceback (most recent call shown last):

    embedded script, line 17, at top level
    AttributeError: 'Device' object has no attribute 'onState'
This log below was recorded with an actual water leak event. You can see that the device that triggered 006 - Leak Sensor 1873696535 has a state of True, which is exact what I want to figure out the deviceID

    006 - Leak Sensor 1873696535
    Script True


      Sorry for the size, I would be grateful to learn a better way to handle these log entries.
        Aug 27, 2021 at 2:28:28 PM
        Z-Wave Debug RCVD requestAlarmSensorStatus: 01 0F 00 04 00 06 09 71 05 00 00 00 FF 05 02 00 16
        Z-Wave Debug . . requestAlarmSensorStatus: node 006, endpoint None, cmdClass 71, type 0, value 0, classSubKey 710000
        Z-Wave Debug . . requestAlarmSensorStatus: typeExt 5, valueExt 2, classSubKeyExt 7100000502
        Z-Wave Debug . . requestAlarmSensorStatus: defnStatusByte 255
        Z-Wave received "006 - Leak Sensor" status update is on
        Trigger Water Leak Sensor Activated
        Trigger Water Leak Sensor Activated Siren
        006 - Humidity 1384093992
        Script None
        006 - Leak Sensor 1873696535
        Script True
        006 - Tamper 316739640
        Script False
        006 - Temperature 77470459
        Script None
        007 - Z-Wave Repeater (ZW189) 1219598056
        Script In the except section
        Script Error embedded script: 'Device' object has no attribute 'onState'
        Script Error Exception Traceback (most recent call shown last):

        embedded script, line 17, at top level
        AttributeError: 'Device' object has no attribute 'onState'

        Z-Wave Debug SENT soundSwitchTonePlay: 01 0E 00 13 08 07 60 0D 01 07 79 08 15 25 1A DD
        Z-Wave Debug RCVD soundSwitchTonePlay: 01 18 00 13 1A 00 00 36 01 C4 A8 7F 7F 7F 00 00 03 07 00 00 00 03 01 00 00 CC (node ACK)
        Z-Wave Debug RCVD soundSwitchTonePlay: txTransmitTicks 54, txHopCount 1, txRSSIs 196 168 127 127 127, txACKChannelNum 0, txLastTxChannelNum 0, txRouteSchemeState 3, txRoute 7 0 0 0, txRouteSpeed 3, txRouteTries 1, txLastFailedLinkFrom 0, txLastFailedLinkTo 0
        Z-Wave sent "008 - Security Siren" on
        Z-Wave Debug RCVD requestReply1: 01 06 00 04 00 08 00 91 (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 15 80
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 15 FF (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 15 83
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 15 FF (hex)
        Z-Wave Debug RCVD requestAlarmSensorStatus: 01 10 00 04 00 06 0A 71 05 00 00 00 FF 05 00 01 02 01
        Z-Wave Debug . . requestAlarmSensorStatus: node 006, endpoint None, cmdClass 71, type 0, value 0, classSubKey 710000
        Z-Wave Debug . . requestAlarmSensorStatus: typeExt 5, valueExt 0, classSubKeyExt 7100000500
        Z-Wave Debug . . requestAlarmSensorStatus: defnStatusByte 0
        Z-Wave received "006 - Leak Sensor" status update is off
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 15 82
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 15 FF (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 15 82
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 15 FF (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 13 00 04 00 08 0D 60 0D 07 01 71 05 00 00 00 FF 0E 01 00 69
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestAlarmSensorStatus: 01 0F 00 04 00 08 09 71 05 00 00 00 FF 0E 01 00 FF
        Z-Wave Debug . . requestAlarmSensorStatus: node 008, endpoint 7, cmdClass 71, type 0, value 0, classSubKey 710000
        Z-Wave Debug . . requestAlarmSensorStatus: typeExt 14, valueExt 1, classSubKeyExt 7100000E01
        Z-Wave Debug . . requestAlarmSensorStatus: defnStatusByte 255
        Z-Wave received "008 - Security Siren" status update is on
        Z-Wave Debug SENT setBasicValue: 01 0E 00 13 08 07 60 0D 01 07 20 01 00 25 1B 99
        Z-Wave Debug RCVD setBasicValue: 01 18 00 13 1B 00 00 16 01 C0 A9 7F 7F 7F 00 00 03 07 00 00 00 03 01 00 00 E8 (node ACK)
        Z-Wave Debug RCVD setBasicValue: txTransmitTicks 22, txHopCount 1, txRSSIs 192 169 127 127 127, txACKChannelNum 0, txLastTxChannelNum 0, txRouteSchemeState 3, txRoute 7 0 0 0, txRouteSpeed 3, txRouteTries 1, txLastFailedLinkFrom 0, txLastFailedLinkTo 0
        Z-Wave sent "008 - Security Siren" off
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 00 91
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 00 FF (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 00 EE
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 00 FF (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 00 EE
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 00 FF (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 00 90
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 00 FF (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 00 90
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 00 FF (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 00 95
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 00 FF (hex)
        Z-Wave Debug RCVD multiEndPointPacket: 01 13 00 04 00 08 0D 60 0D 07 01 71 05 00 00 00 FF 0E 00 00 68
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestAlarmSensorStatus: 01 0F 00 04 00 08 09 71 05 00 00 00 FF 0E 00 00 FF
        Z-Wave Debug . . requestAlarmSensorStatus: node 008, endpoint 7, cmdClass 71, type 0, value 0, classSubKey 710000
        Z-Wave Debug . . requestAlarmSensorStatus: typeExt 14, valueExt 0, classSubKeyExt 7100000E00
        Z-Wave Debug . . requestAlarmSensorStatus: defnStatusByte 0
        Z-Wave received "008 - Security Siren" status update is off
        Z-Wave Debug RCVD multiEndPointPacket: 01 13 00 04 00 08 0D 60 0D 07 01 71 05 00 00 00 FF 0E 00 00 69
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestAlarmSensorStatus: 01 0F 00 04 00 08 09 71 05 00 00 00 FF 0E 00 00 FF
        Z-Wave Debug . . requestAlarmSensorStatus: node 008, endpoint 7, cmdClass 71, type 0, value 0, classSubKey 710000
        Z-Wave Debug . . requestAlarmSensorStatus: typeExt 14, valueExt 0, classSubKeyExt 7100000E00
        Z-Wave Debug . . requestAlarmSensorStatus: defnStatusByte 0
        Z-Wave received "008 - Security Siren" status update is off
        Z-Wave Debug RCVD multiEndPointPacket: 01 0D 00 04 00 08 07 60 0D 07 01 79 0A 00 94
        Z-Wave Debug . . multiEndPointPacket: node 008, endPoint 7
        Z-Wave Debug RCVD requestReply2: 01 09 00 04 00 08 03 79 0A 00 FF (hex)

          Posted on
          Fri Aug 27, 2021 1:47 pm
          kw123 offline
          User avatar
          Posts: 8366
          Joined: May 12, 2013
          Location: Dallas, TX

          Re: Embedded Python to determine the calling deviceID

          w
          if hasattribute(dev, "onState"):

          you can check if that dev has dev.onState

          Karl

          Posted on
          Fri Aug 27, 2021 1:56 pm
          jjpmir04 offline
          Posts: 15
          Joined: Aug 25, 2021

          Re: Embedded Python to determine the calling deviceID

          The sample code you shared with me has the following unexpected behavior - when running as a live alarm, the code fails with an exception
          Z-Wave Debug RCVD requestAlarmSensorStatus: 01 0F 00 04 00 06 09 71 05 00 00 00 FF 05 02 00 17
          Z-Wave Debug . . requestAlarmSensorStatus: node 006, endpoint None, cmdClass 71, type 0, value 0, classSubKey 710000
          Z-Wave Debug . . requestAlarmSensorStatus: typeExt 5, valueExt 2, classSubKeyExt 7100000502
          Z-Wave Debug . . requestAlarmSensorStatus: defnStatusByte 255
          Z-Wave received "006 - Leak Sensor" status update is on
          Trigger Water Leak Sensor Activated
          Trigger Water Leak Sensor Activated Siren
          006 - Humidity 1384093992
          Script None
          Z-Wave Debug SENT soundSwitchTonePlay: 01 0E 00 13 08 07 60 0D 01 07 79 08 15 25 1C DB
          006 - Leak Sensor 1873696535
          Script True

          006 - Tamper 316739640
          Script False
          006 - Temperature 77470459
          Script None
          007 - Z-Wave Repeater (ZW189) 1219598056
          Script In the except section
          Script Error embedded script: 'Device' object has no attribute 'onState'
          Script Error Exception Traceback (most recent call shown last):

          embedded script, line 17, at top level
          AttributeError: 'Device' object has no attribute 'onState'

          When running in the editor environment for the embedded script, it completes perfectly. Of course, since there is no underlying alarm state present, it does not report True as the state of the target device.
          Aug 27, 2021 at 2:53:42 PM
          Script id, Name onstate:
          Script 1873696535, 006 - Leak Sensor , False
          Script 316739640, 006 - Tamper , False
          Script 553374040, 008 - Button 1 , False
          Script 47791506, 008 - Button 2 , False
          Script 93060902, 008 - Button 3 , False
          Script 1451990799, 008 - Security Siren , False
          Script 1209823218, 008 - Tamper Alert , False

          Posted on
          Fri Aug 27, 2021 2:20 pm
          kw123 offline
          User avatar
          Posts: 8366
          Joined: May 12, 2013
          Location: Dallas, TX

          Re: Embedded Python to determine the calling deviceID

          Code: Select all
          for scanDevice in indigo.devices:
             indigo.server.log ( str( scanDevice.id ), scanDevice.name )
             try:
                deviceState = str( scanDevice.onState )
             except:
                indigo.server.log ( "In the except section" )
             
             indigo.server.log ( str(scanDevice.onState ) )


          will always execute: indigo.server.log ( str(scanDevice.onState ) )

          int should be:
          Code: Select all
          for scanDevice in indigo.devices:
             indigo.server.log ( u" {} {}".format( scanDevice.id, scanDevice.name ))
             try:
                deviceState = str( scanDevice.onState )
                indigo.server.log ( str(scanDevice.onState ) )
             except:
                indigo.server.log ( "In the except section" )
             

          Posted on
          Fri Aug 27, 2021 2:22 pm
          kw123 offline
          User avatar
          Posts: 8366
          Joined: May 12, 2013
          Location: Dallas, TX

          Re: Embedded Python to determine the calling deviceID

          or better:
          Code: Select all
          for scanDevice in indigo.devices:
             indigo.server.log ( u" {} {}".format( scanDevice.id, scanDevice.name ))
             if hasattrib(scanDevice,"onState"):
                    indigo.server.log ( str(scanDevice.onState ) )

          Who is online

          Users browsing this forum: No registered users and 5 guests