Checking state of a bulb / Parsing JSON to variable All questions

Hey Derek,

First off, congrats on making such a fantastic service.  I just came across it yesterday after slamming my head against the limitations of IFTTT and already I can see the potential.  I'll certainly be donating.

One scenario I'd love some guidance with is this:  I have a Kasa light switch for some outdoor lights and a Wyze camera.  I have a sequence that can turn the Kasa light on for 5 minutes after motion is detected on a camera.  I'll add in the conditions of after sunset after.

That Kasa light is on a schedule from sunset to 11pm.  What I'd like is for a sequence is, after a motion trigger, to check the state of the light before deciding to turn it on (or off).  If it's already on (either due to it being before 10pm or if it's manually turned on OR if it's on due to previous motion) then don't run the on-delay-off sequence.

Kasa does have a convoluted method of getting the current state of the light through a through a curl command similar to this:

curl -s --request POST --data '{"method":"passthrough","params":{"deviceId":"XXX_SECRET_DEVICE_ID_XXX","requestData":"{\"system\":{\"get_sysinfo\":null},\"emeter\":{\"get_realtime\":null}}"}}' --header "Content-Type:application/json"

That results in a response like this:

{"error_code":0,"result":{"responseData":"{\"system\":{\"get_sysinfo\":{\"sw_ver\":\"1.5.11 Build 200214 Rel.152651\",\"hw_ver\":\"1.0\",\"mic_type\":\"IOT.SMARTPLUGSWITCH\",\"model\":\"HS220(US)\",\"mac\":\"XX:XX:XX:XX:XX:XX\",\"dev_name\":\"Smart Wi-Fi Dimmer\",\"alias\":\"Garage Soffits\",\"relay_state\":0,\"brightness\":68,\"on_time\":0,\"active_mode\":\"none\",\"feature\":\"TIM\",\"updating\":0,\"icon_hash\":\"\",\"rssi\":-50,\"led_off\":0,\"longitude_i\":-1135607,\"latitude_i\":535573,\"hwId\":\"XXXXXXXXXXXXXXXXXXXX\",\"fwId\":\"00000000000000000000000000000000\",\"deviceId\":\"XXX_DEVICE_ID_XXX\",\"oemId\":\"XXX_OEM_ID_XXX\",\"preferred_state\":[{\"index\":0,\"brightness\":100},{\"index\":1,\"brightness\":60},{\"index\":2,\"brightness\":30},{\"index\":3,\"brightness\":1}],\"next_action\":{\"type\":-1},\"err_code\":0}},\"emeter\":{\"get_realtime\":{\"err_code\":-1,\"err_msg\":\"module not support\"}}}"}}(base)

The piece to grab out of the JSON is the "relay_state" which will be 0 if off, 1 if on.  I understand it would be something like responseData-system-get_sysinfo-relay_state but I'm not sure how to store that variable, or evaluate it as a condition.

Hope that makes sense!  
Thanks again.

Asked by Rums on July 23, 2020, at 11:48pm

Following-up on this, I think the issue may be that the JSON is a full escaped JSON string inside of a JSON structure, so Sequematic can't pull the responseData-system-get_sysinfo-relay_state value.  

What I was able to do was put a page on my own server that takes the whole JSON string, decode it, get the value of responseData, then re-decode THAT value into another JSON object.  Finally I can access the relay_state value.  Ideally I wouldn't need to use another site to double-decode the data but I couldn't think of a better option at the time.

This leads to two (more) questions:

1.  Is there a set of IP addresses that SEQUEmatic uses for its webhook calls?  I'd like to restrict access to my JSON decoder page to *just* SEQUEmatic, if possible.

2.  My decoder page is able to spit out the following:


But I can't for the life of me assign soffitState to a variable.  It just keeps coming up as empty.  Help!
Here is a screenshot of the sequence:

Hi Rums, thanks for your positive feedback, I'm glad you're finding the service userful!

Regarding the webhook calls, this might take a bit of digging around to solve it.  Looking at your set up with the custom webhook call it should be working fine. I don't think this should make a difference, but does your script set the header to JSON?  If not, try adding this near the start of your PHP script:

header('Content-Type: application/json');

If this doesn't work, then I've added additional logging so can you trigger the sequence again then let me know once it's run so I can check the logs?

Going back to the original Kasa API call, even though SEQUEmatic might not be able to process the escaped JSON, the escaped version should still be stored in responseData which you should be able to access in your sequence by {result-responseData}. I think the example below should work. Give this a go as well and then I can take a closer look at the logs if it doesn't work to see where it's going wrong.

Thanks Derek!  I think adding the header type declaration seems to have worked, and now the soffitState value is being updated through my sanitizing php.

Going direct to the Kasa API call with your suggested 'contains' change did not work for me, however.  I ran the sequence at Sat 25 Jul 0:16:17 and the code just goes to the 'else' condition (setting the variable to 1).  This would be ideal if we could get it working directly as it removes another point of failure and complexity.

Perhaps if you can see in the logs what is actually being returned by my JSON POST to Kasa for checking state?  If there is an error in the body parameters, then I wouldn't know.  

I was able to directly call the Kasa API to turn the light ON and OFF, so that's pretty cool.  I had issues before with my token expiring which again is tough to know without seeing the response from the custom webhook, so I've added a triggerless sequence to run before turning the lights ON or OFF to hit my server, get the current token, set the variable, and use that in the URL of the custom webhook.  Again, what you've built here is fantastic!

Thanks for the help.

Great, thanks. I think I've found it in the logs.  You need to change the condition to check if {result-responseData} contains "relay_state":1

I'll also send you an email with the response from the Kasa webhook call so you can see what else is in there. I don't want to post it here as it contains tokens and other private data.

It works! Thanks Derek. Now for me to flesh-out the rest of my motion-sensor light logic...

Good to hear! Good luck with the rest of the sequence.

Post a reply

The SEQUEmatic bot is still new and learning. If you don't get the answer you need, just ask to speak with Derek and your chat will be transferred.