jasonacox / tinytuya

Python API for Tuya WiFi smart devices using a direct local area network (LAN) connection or the cloud (TuyaCloud API).
MIT License
937 stars 167 forks source link

Tuya Protocol 3.5 - Globe lightbulb - Unexpected payload in scan & can't control #247

Closed Xilef11 closed 1 year ago

Xilef11 commented 1 year ago

Hi, I have an RGB lightbulb that I'm trying to control, and although the wizard managed to pull the device information and local key from the cloud, I can't control the device. The scan finds it, but gets an "unexpected payload":

python -m tinytuya scan -nocolor

TinyTuya (Tuya device scanner) [1.9.1]

[Loaded devices.json - 1 devices]

Scanning on UDP ports 6666 and 6667 for devices (16 retries)...

*  Unexpected payload=%r
 b'\x13@\x8d(H\x7f`\xe3\xb9Muf<\x97Ej\xaf)@\xd4\xe0\xdf\x19\xfa\x04,\xa6Bm\xceK\x0f;fuE j\x01\x129S\n\xb6\xb0"\xeb\xc7\xf9mn\xa0\x15\xd2T\xa8f\x93\x85\x94\xa5pEi\xd0\xeeY\x1100\'\xfao\x946\x07\xeb\x99\xe8\x17]\x1e\xdc\x87\xa20\xf4\t\x8d\xd4\xc5$\xd9\r\x94\xea6\xcc\x0c\x8c\xfb\x9b\xce /A\xa0\xfb\xb9gn\xcb\x04\x0e\xd4Hb\xb6t\xb1\xbe\xbeO\x18w\xdb\xbf\xad\xf0\xe90>r\xa4\xa1\x1a\xdf\xd1O$f\x10\xa6\xf9gt\x07\x01\x82\xa9\xd4\x87\x8f\xbb\xc6u\xeb\'\xbe\xbbv6\xe0\xc6\xae\xf6\xa4\\\xe9}\x1e\xa359B\x15\xb3W\xeb\x14\x11=q;\x96\xac\xcc8\xd3ZF\x19m\xb7\xf6"\x17\x9bA\xfe=\x97\xdbL\n\xcdt\x1d\xe3\x95T>I\x94\xfa\xa7p\xb1\x87x\x97\xb7\xbb\x81\xfe\xd9gH\xf2\x0e\x86B\xd1'
Unknown v Device   Product ID =   [Unknown payload]:
    Address = 192.168.2.46,  Device ID = , Local Key = ,  Version = , MAC =
    No Stats for 192.168.2.46: DEVICE KEY required to poll for status
*  Unexpected payload=%r
 b'\x13@\x8d(H\x7f`\xe3\xb9Muf<\x97Ej\xaf)@\xd4\xe0\xdf\x19\xfa\x04,\xa6Bm\xceK\x0f;fuE j\x01\x129S\n\xb6\xb0"\xeb\xc7\xf9mn\xa0\x15\xd2T\xa8f\x93\x85\x94\xa5pEi\xd0\xeeY\x1100\'\xfao\x946\x07\xeb\x99\xe8\x17]\x1e\xdc\x87\xa20\xf4\t\x8d\xd4\xc5$\xd9\r\x94\xea6\xcc\x0c\x8c\xfb\x9b\xce /A\xa0\xfb\xb9gn\xcb\x04\x0e\xd4Hb\xb6t\xb1\xbe\xbeO\x18w\xdb\xbf\xad\xf0\xe90>r\xa4\xa1\x1a\xdf\xd1O$f\x10\xa6\xf9gt\x07\x01\x82\xa9\xd4\x87\x8f\xbb\xc6u\xeb\'\xbe\xbbv6\xe0\xc6\xae\xf6\xa4\\\xe9}\x1e\xa359B\x15\xb3W\xeb\x14\x11=q;\x96\xac\xcc8\xd3ZF\x19m\xb7\xf6"\x17\x9bA\xfe=\x97\xdbL\n\xcdt\x1d\xe3\x95T>I\x94\xfa\xa7p\xb1\x87x\x97\xb7\xbb\x81\xfe\xd9gH\xf2\x0e\x86B\xd1'
*  Unexpected payload=%r
 b'\xbb\xcfh+@\x0b\xe6t\x0c\x83H\'\xb1-\xdc\xb9D\xc2\xc7\x08\x8a\x13\xaf]\x8b4\xda\x17\x847\xdfn\xb7\x81v\xcf\xf2\';\x10\x1f\x1bA;(#\xca3r\x83U\xdeh\xa6\xfe>\xd2"YH\xaf\xf0\'\x9aV}\x08uIs\xdf\xd0\x12\x826\xae\x1e%){+{ijJk\x18\x9e\xfb\xdetp\xe3V2\xa1\x1f\x02\xef@\xee\x05\xc2\xddy\xb4\x88oF\x97\xc2\x04\x1aW<rJ $\x89.y\x0b\x89\x86\x81\xd6\x08i\xc0\x0b\xf7\xa3~\xd1\x98%\x11\xb9\xe7\xc0\xb7\x9c+\x16\xc0\xf7\xb9\xe1\xc3\xb0\x89d\xd2\xb2\x0b\x19\xa5\xd6s\x01\x0e,/v~=iVe\tv\xa4 A0\xf5\x02\xf1\xae$\x18\xfc\x91\xaf\xc9?\xf74\x19z\xe9\x0e)\x02\xc1\xa2?5\xf1\xf02\x17N\xf6\xa1\xf3\x87\x81t\x0e\xa3(\x9d\xbf\x17\xa8jrE\x06\x1d\x92\xf0\xa8n\xd6\xa5\xf2\x82P\xa6;'
*  Unexpected payload=%r
 b'\xbb\xcfh+@\x0b\xe6t\x0c\x83H\'\xb1-\xdc\xb9D\xc2\xc7\x08\x8a\x13\xaf]\x8b4\xda\x17\x847\xdfn\xb7\x81v\xcf\xf2\';\x10\x1f\x1bA;(#\xca3r\x83U\xdeh\xa6\xfe>\xd2"YH\xaf\xf0\'\x9aV}\x08uIs\xdf\xd0\x12\x826\xae\x1e%){+{ijJk\x18\x9e\xfb\xdetp\xe3V2\xa1\x1f\x02\xef@\xee\x05\xc2\xddy\xb4\x88oF\x97\xc2\x04\x1aW<rJ $\x89.y\x0b\x89\x86\x81\xd6\x08i\xc0\x0b\xf7\xa3~\xd1\x98%\x11\xb9\xe7\xc0\xb7\x9c+\x16\xc0\xf7\xb9\xe1\xc3\xb0\x89d\xd2\xb2\x0b\x19\xa5\xd6s\x01\x0e,/v~=iVe\tv\xa4 A0\xf5\x02\xf1\xae$\x18\xfc\x91\xaf\xc9?\xf74\x19z\xe9\x0e)\x02\xc1\xa2?5\xf1\xf02\x17N\xf6\xa1\xf3\x87\x81t\x0e\xa3(\x9d\xbf\x17\xa8jrE\x06\x1d\x92\xf0\xa8n\xd6\xa5\xf2\x82P\xa6;'
*  Unexpected payload=%r
 b'RU8\xd9\t&\xec\xee]\xces6*:0\x02\xab\xe3\xfe\xa1\xf5\xf7a7\xde\xdc\xac\xb87\xa0\xc3\xe4\xc2\xfc\xff\xab.u\xeb\x93\x8bx\xc4>\xee\xafX%p\xb8\xa2\xd6L\x058M\xea\xb25\xdbs\x82\x0c\xad\xab\xfc\xa1`\xb3N7\xabM\xf4\xe9\x89D%So\xc0\x1fpG\xfc\xd5\xef\x1f\xabd\xda\xa0h\xbf\xf0cE\xdc)G\x87o\xe4\xc6=te\x1d\x0e:9\xf0\x0c\xb5\xf3\xb4\xc8\xcd\x81^zOU\xf9J\xd8\x9b\xb78\xe5\x92\x10Y\x93\xd30\xe2\xe6\xfe\xa6\xb3\t2\x84\xa8\xc9\x1b\xf3\xb8y\xeb\xdf\xa1*\xb6\xea\xf0\xcd\xebH\xac\xa1\xfa\xaa\x0e\x91\xa2\x1cD\x0eg\x81t\x0c\xf0Z\x8c\x8836"\xa1\xa4\xf1y+Y~Ot(\xee\x1eqF \xd4GsZ\xc2*\xa3}\x19\x15D.\xad\x19\xeb9\xfd\x9e\x9f>e\x80\xdd\xaf\xd44\xf4.\xc4\xf3\xd4\xd8+\xeb>!\xbc'
*  Unexpected payload=%r
 b'RU8\xd9\t&\xec\xee]\xces6*:0\x02\xab\xe3\xfe\xa1\xf5\xf7a7\xde\xdc\xac\xb87\xa0\xc3\xe4\xc2\xfc\xff\xab.u\xeb\x93\x8bx\xc4>\xee\xafX%p\xb8\xa2\xd6L\x058M\xea\xb25\xdbs\x82\x0c\xad\xab\xfc\xa1`\xb3N7\xabM\xf4\xe9\x89D%So\xc0\x1fpG\xfc\xd5\xef\x1f\xabd\xda\xa0h\xbf\xf0cE\xdc)G\x87o\xe4\xc6=te\x1d\x0e:9\xf0\x0c\xb5\xf3\xb4\xc8\xcd\x81^zOU\xf9J\xd8\x9b\xb78\xe5\x92\x10Y\x93\xd30\xe2\xe6\xfe\xa6\xb3\t2\x84\xa8\xc9\x1b\xf3\xb8y\xeb\xdf\xa1*\xb6\xea\xf0\xcd\xebH\xac\xa1\xfa\xaa\x0e\x91\xa2\x1cD\x0eg\x81t\x0c\xf0Z\x8c\x8836"\xa1\xa4\xf1y+Y~Ot(\xee\x1eqF \xd4GsZ\xc2*\xa3}\x19\x15D.\xad\x19\xeb9\xfd\x9e\x9f>e\x80\xdd\xaf\xd44\xf4.\xc4\xf3\xd4\xd8+\xeb>!\xbc'
*  Unexpected payload=%r
 b'\x99\xee\xe8L\xea\xb1\xf1\x83\xb2\xd5\xa8\xc0\xa9\x02/\xe5\x0b-\t\xaa]\x99\x8cy\x009\x0cp\x8eyd\xdeb\x97\x94\x94\xc6\x99r\xaa\x8a\xdcfM\xce\xa3\x8cB^\xbf\x92\xa0y_\xd5\xa1CT\xa9\x87\xd9\xbb#%\xcb\xbe%\x02\r\xa15\xad\xaaV\r\xfb\x17\xfd\xda,O\x03N8\x9c\x9a%\xd7\xc8\xd6\xaf\x02\x91\xb9\xc7\xf0\x81\x9c\xf0=\x08\xd3\xc3\\\xa1\x1a%\xb8\x82\xa3\xda\xa0\x03\x9d\x15y\x08\x7f\xc4\xb8h\xdc5\x18\xd0\xa6/\x03\xc1\xae\xe9P\x9e\x98\xfaT&(1\xf1\xe1oj$K\x88-\x89\xde\x1c>\xf1\x080\x82\x8d\x15\xad\xdad"\x8ds\xdd\x18\xa5\xb5rku\x07\xcf\xc6\xb5\xc0\x0e\xffp\xfa\xe0B\x00s\x13\xbc\xe3\xe61(\xe6\xa3\x84a{?\x1b\'\xc6\xa9\x8a\xce~\xbd\xc0\xd4\r\\\xcb];\t\x80$\xcf\xd6\xa3\xb0\xa3\x8eO\xf1I\x9c\xb6\x0b\xc3Q\xbc\xdekR\x18\x00'
*  Unexpected payload=%r
 b'\x99\xee\xe8L\xea\xb1\xf1\x83\xb2\xd5\xa8\xc0\xa9\x02/\xe5\x0b-\t\xaa]\x99\x8cy\x009\x0cp\x8eyd\xdeb\x97\x94\x94\xc6\x99r\xaa\x8a\xdcfM\xce\xa3\x8cB^\xbf\x92\xa0y_\xd5\xa1CT\xa9\x87\xd9\xbb#%\xcb\xbe%\x02\r\xa15\xad\xaaV\r\xfb\x17\xfd\xda,O\x03N8\x9c\x9a%\xd7\xc8\xd6\xaf\x02\x91\xb9\xc7\xf0\x81\x9c\xf0=\x08\xd3\xc3\\\xa1\x1a%\xb8\x82\xa3\xda\xa0\x03\x9d\x15y\x08\x7f\xc4\xb8h\xdc5\x18\xd0\xa6/\x03\xc1\xae\xe9P\x9e\x98\xfaT&(1\xf1\xe1oj$K\x88-\x89\xde\x1c>\xf1\x080\x82\x8d\x15\xad\xdad"\x8ds\xdd\x18\xa5\xb5rku\x07\xcf\xc6\xb5\xc0\x0e\xffp\xfa\xe0B\x00s\x13\xbc\xe3\xe61(\xe6\xa3\x84a{?\x1b\'\xc6\xa9\x8a\xce~\xbd\xc0\xd4\r\\\xcb];\t\x80$\xcf\xd6\xa3\xb0\xa3\x8eO\xf1I\x9c\xb6\x0b\xc3Q\xbc\xdekR\x18\x00'
*  Unexpected payload=%r
 b'Df\xa6L\xa4\xfc\xa4\x18\xb5\xceJ\x8dN`.j\x8c\xaf\x90)4\xfa\r\xach%p\x7f\x1e9h\xc2\xd62kP\xb9\xa7\xc1\x01\x83\xde\n\xdf\xca\xd0|\x19\xcfZ~\xc4\xb3\xd9x-M\xa2qk\xa5\x9evz3\xa5\xa2/%\x06\xf4\x8c\xe4\x86a\x9f\xc0^.Y\xabf\xd2\xc0\xce\xadF&T\x1c\x01.\x831\x11\xf07\xcb\x95M\x83cX\xba4%L^\xb1\x96\x13\x0c"\xb1;\xcc/\x93R\xbeX3t8\x16\xc6v*\x1a\xfe9\xfe0<=\xfc\x80\x12\x9e%B\xae\x1a\xcci\xfb\xf57\xe3\x04\xa3\x1b\xe9\xbc@aB\xfd{d\xf5[l{h\xe3\xd5n|j\x8c\x82*\xfe\xa2O.\xf3w(\x86%wg\x9b\x83c*\xe4J\x8as\xd8}\xa48\xc4\xb4Id\xad\x9a\xf7\x08P\x07!\xbc\x8c\xd2\xf6\xcd\xb8\xd3j\xe3?\xa7O\xe2\x86%\xac\xfc;|\xa7\xa3)\x83n\xf1\xcb'

Scan Complete!  Found 1 devices.

>> Saving device snapshot data to snapshot.json

When trying to send commands, I get {'Error': 'Timeout Waiting for Device', 'Err': '902', 'Payload': 'Check device key or version'}. I tried all protocol versions and the "device22" device type, to no avail. Enabling debug mode only reveals a "timeout in _send_receive()" and no reply from the bulb. Control using tinytuya.Cloud works perfectly. I can ping the bulb's IP with no problem.

I checked the datapoint codes on the website and they seem to match the "version 3.3 - light type (RGB)" table in the README. However, trying to set these values through code doesn't work.

Any ideas? Thanks!

jasonacox commented 1 year ago

Hi @Xilef11 - I may be reading this wrong since you mention sending commands (via python script), but in the example you pasted I see this...

Address = 192.168.2.46, Device ID = , Local Key = , Version = , MAC = DEVICE KEY required to poll for status

Did you remove the Device ID from the output or was that actually blank? In any case, it is reporting that you are missing the local key. The 3.3 devices require a valid local key. If you run wizard, it will create a devices.json file that will have the local key. Run the scan again in that same directory and TinyTuya will use that local key to poll the devices.

If that is not the issue, try to power cycle the device completely. I know that sounds odd, but I have seen it myself. Also, keep in mind that the local key will change if you every re-pair the device with the SmartLife app (e.g. factory reset).

Xilef11 commented 1 year ago

No, that's the output from the scan, all blank. devices.json was created correctly, so either it's not using the file or it can't match it to the device. I'd guess the latter since there's a [loaded devices.json - 1 devices] message at the start of the scan. devices.json (key is present in the file):

[
    {
        "name": "36819",
        "id": "ebf310edb88d15f0edyr5i",
        "key": "XXXXXXXXXXXXXXXX",
        "mac": "38:1f:8d:36:d2:03",
        "category": "dj",
        "product_name": "",
        "product_id": "qlbfchuhqdbmeheo",
        "biz_type": 0,
        "model": "Litech",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1514166115504M4mB5/059dcd620d85996a42b54c681a6b5ba9.png",
        "uuid": "60b308e46e1b5871"
    }
]
uzlonewolf commented 1 year ago

Edit: if anyone's just looking for an overview of the v3.5 protocol, check out https://github.com/jasonacox/tinytuya/discussions/260#discussion-4762410


That's really odd. Can you post the output from:

import socket

clients = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, socket.IPPROTO_UDP)
clients.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)
clients.bind(("", 6667))
clients.settimeout(7)

for i in range( 8 ):
    data, addr = clients.recvfrom(4048)
    print( addr, '=', data )
Xilef11 commented 1 year ago

Here it is, looks like the same block repeated 8 times

('192.168.2.46', 57749) = b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xef\xe6_\xba\xd0\x9a\x1eL\xcc\'F\x0ce\xe6\xb0AX\x94\x8c}\xc9\xd3\xdf\xf1[\x87U\x16a\xdc\xa6)O\x7f\x027v\x0e\x84\n\x9c12G\x14\n\x19\x13\x85\xd8\x9b_+\xb9&*7%\x8e\xe9b\xba\x90"\xb1Z\xb5\x9f\xaa\xcc\xdc\xad\xa2\x9a\x8f\xfbz=65G\x1c\xabZN\xc9E\x81\'\x90\xaa~KN\x8b\x13k\xccr\x13\x199\x8f\x92\xf5\x10\xf8\xb4\xeb\xe9\xa83\x80\xe0R\xc9\xe7\xde\x90\xd7\x90\x08\x11\xdc\xa0\x93\xc9@\xb40uf\xce\x82|\x94\x93\x8b\xe91_\x96\xdf3\xc2\x94\xc4\x05o\xc4\xafN1o!\x12^\xcb\x85\xa0\xce\xfd\xb8\xafG-D\xdb\xd8Xy\x87\xc2\xc0\xd8\x11\xcc\x05\xf3"s7\xac\x88\x8d\xec\x88\xf0jg.\xba\x01`\xde\xb3v\x9a\x03g\xa2X\x00\x01\xc2\xd0"\xc1A[\x1e\x0fu;&\x17\xf02\\\x9a\xf4^\x84t\x94\x01O\x9b\x148\xd7\xf7\xaeks\x82,\xff`\xad\x00\x00\x99f'

('192.168.2.46', 57749) = b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xef\\\x86\xc0v$y]\x96\xdd#Y)\x02\xa2"\\\xc2\xe0\xcf\xcd}\x89\xd4@\xcd\xcc6\xc7\xc1S\\\xe1\xdc,\xef\xfcu\x13\xae\x02\xff\xe0\xc6\xfa\xd7r"Y\x953\x1a\xc0\x10\xdc\x9cZe\x08\x1e\x97\xc8\xb1\xe7\x89j\xb6\xb56\x10u\x0e\xcd\xfdf\xf9\xcbA\xcf\x04\xff9\xa02\xe3\xe9\xc0\xe2V=\xc8\x17\xa8"\xaa[\xee\x84\x8aN\xf9\xd5\xcb:\xf4|\x0b\xcdT\x04\x03\x03\x82^\xd1\x1b\x7f\xb57\xaa,\x05{O\x04\x86\xd8\x0e\x8a0\x9e\xd6/\xd2\x0cE\xe9\x97\xfa\x92t\xfa\xa1}\x80\x9f\x01\x98\xf3\x07\xa9\xeb\xce\xb1 !`w\x92\x06\x14\xffT^\xe8\x19>~\xf4\x0b\x0f\x0c\xb6,\x11\xb9\x05^\xdc@\x97a\xfdOa\xb7\x9d\xd0M\xb4P\xdb+\xe3\x87\x9b\xd8d\xb0=\xa4\xb2Z\x04\xc2s\xa4_v\x9d#\x7f \xc1\x99\x97\xadF6\xf8U\x8aT\x1b\xac\xa2\x85\xf7\xb9 \x8d\xb4M\x02\xe2\xd7\x94\xd7\xa97\x00\x00\x99f'

('192.168.2.46', 57749) = b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xef\\\x86\xc0v$y]\x96\xdd#Y)\x02\xa2"\\\xc2\xe0\xcf\xcd}\x89\xd4@\xcd\xcc6\xc7\xc1S\\\xe1\xdc,\xef\xfcu\x13\xae\x02\xff\xe0\xc6\xfa\xd7r"Y\x953\x1a\xc0\x10\xdc\x9cZe\x08\x1e\x97\xc8\xb1\xe7\x89j\xb6\xb56\x10u\x0e\xcd\xfdf\xf9\xcbA\xcf\x04\xff9\xa02\xe3\xe9\xc0\xe2V=\xc8\x17\xa8"\xaa[\xee\x84\x8aN\xf9\xd5\xcb:\xf4|\x0b\xcdT\x04\x03\x03\x82^\xd1\x1b\x7f\xb57\xaa,\x05{O\x04\x86\xd8\x0e\x8a0\x9e\xd6/\xd2\x0cE\xe9\x97\xfa\x92t\xfa\xa1}\x80\x9f\x01\x98\xf3\x07\xa9\xeb\xce\xb1 !`w\x92\x06\x14\xffT^\xe8\x19>~\xf4\x0b\x0f\x0c\xb6,\x11\xb9\x05^\xdc@\x97a\xfdOa\xb7\x9d\xd0M\xb4P\xdb+\xe3\x87\x9b\xd8d\xb0=\xa4\xb2Z\x04\xc2s\xa4_v\x9d#\x7f \xc1\x99\x97\xadF6\xf8U\x8aT\x1b\xac\xa2\x85\xf7\xb9 \x8d\xb4M\x02\xe2\xd7\x94\xd7\xa97\x00\x00\x99f'

('192.168.2.46', 57749) = b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xef\x9c+\xd2\x1ax\xaa\xee\xf8\xf4\xf9\xee\xe9h3\xf1-\xa4\xda\xf2\xb9\xf5v\xf5\x99\xf7aH\xa4\xf8\xab\xc3\xfa>d\x7fq\x0f\xfa\x1e\xf8\x85\xe3\xa8\xe9\'~[\r\xf6*e\n\xee\x02\x06JMA\xfe\xc70\xa8{\xdd\xdc\xaaeIn\xf7t\xbc\x90\x1d\xb0\xfd(q?J\xfe\x90v+\xc0\xd1MW6,h\x19\xfe\x0b\xd7\xcc\x98\xec}L\xce7\n\xfa\x15\xe8Th\xccd\x84jX`\t~*\x80\x97?NL\xdb\xb0\xd3\xc8@-\xed;\xfb\xcdk\xcd\xa9\xa5\xb2s\x806\x1a\x9dlfM\x04\x062\xfbR\xc0\xab\xe5b~\x87\xe7\xd2\xb7\x87\xf5\x0e\xc0X\x1d\xf3:B\xe4\xa9\x8e\x03\x9e|\xbb\xf1\x02\xa1\x03U;\xab\x91\x03\xa3\x86_U_N\xa4\xc6\xb8]\xe9Ca*\x12d\x14\xb6\xec\xbd\xb9\x88\x1e\xd0r\xdb\x1e\x95\xbc\x13\xa8",\xb3&\xb9H\xa3\xd1\xdfgA\x1a\xe6\xd5\x04o\xe8\xc4\x86j\xab\xdb\xa7T\x00\x00\x99f'

('192.168.2.46', 57749) = b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xef\x9c+\xd2\x1ax\xaa\xee\xf8\xf4\xf9\xee\xe9h3\xf1-\xa4\xda\xf2\xb9\xf5v\xf5\x99\xf7aH\xa4\xf8\xab\xc3\xfa>d\x7fq\x0f\xfa\x1e\xf8\x85\xe3\xa8\xe9\'~[\r\xf6*e\n\xee\x02\x06JMA\xfe\xc70\xa8{\xdd\xdc\xaaeIn\xf7t\xbc\x90\x1d\xb0\xfd(q?J\xfe\x90v+\xc0\xd1MW6,h\x19\xfe\x0b\xd7\xcc\x98\xec}L\xce7\n\xfa\x15\xe8Th\xccd\x84jX`\t~*\x80\x97?NL\xdb\xb0\xd3\xc8@-\xed;\xfb\xcdk\xcd\xa9\xa5\xb2s\x806\x1a\x9dlfM\x04\x062\xfbR\xc0\xab\xe5b~\x87\xe7\xd2\xb7\x87\xf5\x0e\xc0X\x1d\xf3:B\xe4\xa9\x8e\x03\x9e|\xbb\xf1\x02\xa1\x03U;\xab\x91\x03\xa3\x86_U_N\xa4\xc6\xb8]\xe9Ca*\x12d\x14\xb6\xec\xbd\xb9\x88\x1e\xd0r\xdb\x1e\x95\xbc\x13\xa8",\xb3&\xb9H\xa3\xd1\xdfgA\x1a\xe6\xd5\x04o\xe8\xc4\x86j\xab\xdb\xa7T\x00\x00\x99f'

('192.168.2.46', 57749) = b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xef\xc0\x81\x89#\x8cr\xab\xdf\xaf\x80\xadH\xef\xd43\xa7\xcf\x1eTM\xd7[\r\xb5,\x176+\x1bV\x94w\xdb\x1fz\t5\x04\xa2\xaa\x93\xefPo_\xfd\xddY\xa9\xb0M\xbf\xc1\xee~0\xcc\n~\xe1\xfb\xc2\xef\xf6\x93\xa0\x8d\xb0,\xcc\xa0\t\xfe\t\xec\x93f\x9e\x12\x8a\xfa\'\x9f\xe6\x82\xb0}\xfb-\x19\xb2\x9b\x89\xd3-C\xb3\xd2\xd1,\x06Xr\x86\xa2\t\x8e*\xaa\x8b\x93\xe1J\xfd\xb1\t\x04\x89m\xa1\x8e\x8c+\xfd\xbf\x13C\x1fT\x96ky\x16\xb8\x10\x86s\x82""c^\\lC\xbe7\xb6\x0c\xd7\x9d\xf6n\xc0\xe1\xbc=h\xd7*\x91\xf1\x1b6!K\x17\r\xf0\x10\xf3X[m7\x99\xe8\x14\x92r\xaf\xc9M\x9a\xa7 WU\xf5\x91\x88\x89\xed\x9f,{:B\x93\n\xdf\xe6\x86 bP\xe0\x13:]\xb7<\xe7\xe0r jf\xccz)\xb0\x0c\xc0\xee\x15\x88\xeew5;\xf3\xac\x16\xda\xf7\x16\xb2\x9b\x00\x00\x99f'

('192.168.2.46', 57749) = b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xef\xc0\x81\x89#\x8cr\xab\xdf\xaf\x80\xadH\xef\xd43\xa7\xcf\x1eTM\xd7[\r\xb5,\x176+\x1bV\x94w\xdb\x1fz\t5\x04\xa2\xaa\x93\xefPo_\xfd\xddY\xa9\xb0M\xbf\xc1\xee~0\xcc\n~\xe1\xfb\xc2\xef\xf6\x93\xa0\x8d\xb0,\xcc\xa0\t\xfe\t\xec\x93f\x9e\x12\x8a\xfa\'\x9f\xe6\x82\xb0}\xfb-\x19\xb2\x9b\x89\xd3-C\xb3\xd2\xd1,\x06Xr\x86\xa2\t\x8e*\xaa\x8b\x93\xe1J\xfd\xb1\t\x04\x89m\xa1\x8e\x8c+\xfd\xbf\x13C\x1fT\x96ky\x16\xb8\x10\x86s\x82""c^\\lC\xbe7\xb6\x0c\xd7\x9d\xf6n\xc0\xe1\xbc=h\xd7*\x91\xf1\x1b6!K\x17\r\xf0\x10\xf3X[m7\x99\xe8\x14\x92r\xaf\xc9M\x9a\xa7 WU\xf5\x91\x88\x89\xed\x9f,{:B\x93\n\xdf\xe6\x86 bP\xe0\x13:]\xb7<\xe7\xe0r jf\xccz)\xb0\x0c\xc0\xee\x15\x88\xeew5;\xf3\xac\x16\xda\xf7\x16\xb2\x9b\x00\x00\x99f'

('192.168.2.46', 57749) = b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xefdJ\xa0\xf3\xc8:\xb7\xa7\xa7\x81\x0f$\xad\x04\x9d\x13\x00\x88\xe2x\x15\xc6\x88\x8b\x9b`\x98\xd6Hc^\xc6IKt\xe5\xb9\xf06\xba6\xc37\xf9\xdf\x8a\xed\xbd\xd7Y\xe3\xbaoR\xed\x92z\xbf\x98x\xea\xeag\xbd\xe2\xd0\xa2A6\xde}Y\xc8\xb1.Q\x03\x98\xef\xfd\x96#\xc7\x91\xcb\'\xc0\xfb\xb1\xaa\xa7\xf4\x1dV\x08Hpb\xdc\xf8\xa1\x11\xdbX`\xd1\x08\xbeD\xe8L^d\xc4\xd00\xc7\xe2u\xe1\xa6A,N\x1a\x86l(\x8c\x8e\x7f\xe2\x14\x12\x17%Ngnt\xd3\xdca\t#G\x103\xac\xcd\xa6\x80\xb1\x03t\xed>\xc71\x17R\x9b\xa2\xb6\xd3J,\x1f\xd3R\xa6mP"v!\xa2\x10\x91\x84^\xa7\xc9\xdb\x84:\x86\x19C\xd1\x1e\x8eT0\x15\xc16\x002\xc4y\x1a\xcc\xb64{:/?\x0fkEn\x11Z]\xa2D\xeb\x00\xe2X\xe8\x99\xfejU\xdd\xf1\x08\xd5;$.\x80o\x0c \xa3\x00\x00\x99f'

I also tried a scan in debug mode, which adds the following line after the "unexpected payload=%r..." : DEBUG:Invalid UDP Packet: {'ip': '192.168.2.46'}

uzlonewolf commented 1 year ago

b'\x00\x00\x66\x99'

o.O Well that's a new one, looks like it may be a new protocol (or at least a new encryption key). This is going to take some reverse engineering...

Xilef11 commented 1 year ago

I see... Anything I can do to help?

uzlonewolf commented 1 year ago

Do you have a link to the lightbulb you bought? We're probably going to need to buy one and dump the firmware. If it's similar to one of the existing versions we might be able to figure it out with just packet captures if you're able to get them (it's not trivial to set up if you've never done it before), but if it has substantial changes then that probably won't help.

Xilef11 commented 1 year ago

It's this product from costco, model number on the bulb is 36819 but I can't find it on the globe website.

I should be able to get you a packet capture no problem. Is there any specific part that you need?

uzlonewolf commented 1 year ago

I basically need all the packets the phone app sends and receives to/from the bulb while in offline local-only mode, as well as the local key (you can generate a new local key if you want by removing and re-adding the bulb).

I have some similar ones coming from Amazon tomorrow, no idea if they're the same or if the ones you have are Costco exclusives. I'm hoping the different part numbers are just due to the different packaging (4-pack vs 2-pack vs single).

Xilef11 commented 1 year ago

Getting the capture in offline mode was a bit trickier than I expected, but I think I managed to get something. Here's what I did:

  1. set up computer as AP with wireshark capturing
  2. connect the phone and lightbulb to said network
  3. play with lightbulb setting in the app to confirm that messages to/from the cloud are captured
  4. pull the localkey from the cloud using the wizard
  5. kill the internet connection (this happens around packet 2014 in the capture)
  6. confirm no internet access
  7. keep changing settings in the app.

Interestingly, I didn't find a direct connection between the lightbulb and the phone when the internet was offline. Just UDP broadcasts and RTPS packets. Hope I did it right. Do you have an email where I can send the capture and localkey? It doesn't look like there's any personal data that got in but I'd rather be safe.

uzlonewolf commented 1 year ago

Sure

uzlonewolf commented 1 year ago

Well that's odd. In that packet capture there's only a normal v3.3 device with the usual 000055aa header, it should work with TinyTuya as-is. The phone does appear to be broadcasting 00006699 packets on port 7000 though. I also do not see any local-offline communication, not sure if your computer's not seeing it as it's WiFi-to-WiFi or what.

Xilef11 commented 1 year ago

The scan is capture is from a second bulb in the same box, I just checked and this one is picked up by tinytuya scan and it works fine. The model number on the bulb is the same and they are identical in the app. strange.

If the local/offline communication is p2p and doesn't go through the "router" I won't be able to capture it with my setup. I found an older capture of the non-working bulb which also had the 000055aa UDP broadcasts, but now it's at 00006699 (port 66667) for some reason.

Edit: So the non-cooperating one says its firmware is version 1.5.10 while the working one is 1.2.16. Both say they are "up to date"

uzlonewolf commented 1 year ago

Well my bulbs came in today. The "tunable white" ones showed up with the name "34204 - V4" and firmware version 2.9.6 and use protocol v3.3. The RGB ones showed up with the name "34207" and firmware version 1.3.21 and use protocol v3.4.

@Xilef11 I would like to purchase the 00006699 bulbs you have if you don't mind selling them.

uzlonewolf commented 1 year ago

I ended up picking up some single-pack 34212 RGB+white bulbs, and they're both version 2.9.6. I think this company's nuts for having a completely different part for a 2-pack vs single vs 4-pack, but whatever.

I managed to decode the 6699 broadcast messages, though I won't be able to verify sending commands without a packet capture.

from Crypto.Cipher import AES
from hashlib import md5,sha256
import socket

clients = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, socket.IPPROTO_UDP)
clients.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)
clients.bind(("", 6667))
clients.settimeout(7)

amode = AES.MODE_GCM
key = md5( b'yGAdlopoPVldABfn' ).digest()

for i in range( 8 ):
    data, addr = clients.recvfrom(4048)

    header = data[:18]
    iv = data[18:30]
    payload = data[30:-4]

    print( addr, '=', payload )

    decrypted = AES.new(key, amode, nonce=iv).decrypt( payload )

    print( decrypted )
    print('')

Once decrypted these new devices are reporting protocol v3.5.

Xilef11 commented 1 year ago

Apologies for the delay. Unfortunately I won't be able to sell you the device, but the above code does give some legible information:

('192.168.2.46', 55125) = b'\x9b\xe6\x05\xf5\xf5r\xbe\xfb\x14/\x07\xca]\xe1_K\x88\x92\xad-J\xe4\xfa[Z\xc4>a\x94\x8a\xa5\x9f\xb6\xa8\xee\x94\xa8\xed\xe8P_\x8d\x85\xa1\xbf\xedN\x15\xe4\x1a|\xe5\xdbB1\x00\x0c\xa7\x89\tx\xb7u\xf8\xda\x11\x19i\xec\xcc,K\xf8\xd9\xf3\x8f=\xb45l\x19\xbd\xe2\xf0p\x9c*\xc7\xf1\xdf6v\xc6\xab\xf5\x8f\xea\x84\xceK\x7f\xd5\x03\x84\xad\x1dI/`U\xf3S\xa1\x85\nd[_\xa3TJ\x8d\xfe\xc4\xb4\x90gA\xb4\x8e\xb8.4\xc5\'"\xa2p\xcfQ\xeb\xca\xe5{B\xd1\xa5\xc3\n\x0c\xd3h\xa3\x8c\xee\xd2\xc5\xa16\x94BH\x07\xdf\xeb\x8b N\x04\x94\x80n\x05\xaet\xfb\xd8\xca\x08\xaad\x90\xf2A9x\x1d\x8e\x8e\xa0\xee-/\xc7\x97Q\xcd\xd3\x80\xb7\x0c\xc2\x87\xdb%,MX\xb2\x8aA\x9f\x00o\xa4\xc9\xd5XyX\x00v\x1d\xa1\x00\xdf\xe5'
b'\x00\x00\x00\x00{"ip":"192.168.2.46","gwId":"ebf310edb88d15f0edyr5i","uuid":"60b308e46e1b5871","active":2,"ablilty":0,"encrypt":true,"productKey":"key8u54q9dtru5jw","version":"3.5","token":true,"wf_cfg":true,"clientLink":3})\t\xf8W\x86\t\x8c\x057\xa8U\xb1r\xb6:\x9d'
uzlonewolf commented 1 year ago

It's fine, no worries.

At this point there's not much I can do without either a firmware dump or a packet capture of a local-offline transaction. I have the gateway from #248 coming, but it's been out for a few years now and I'm doubtful it'll arrive with the correct firmware version.

You can try running this while changing something in the app, but it probably won't work:

import socket
import time

ip = '192.168.2.46'

for i in range( 3 ):
    sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    sock.settimeout( 5 )
    sock.connect( (ip, 6668) )
    print( 'connected!' )
    stime = time.time()
    sock.settimeout( 300 )
    while True:
        try:
            rtime = time.time()
            data = sock.recv( 4096 )
        except:
            print( 'connection closed after ', (time.time() - stime) )
            break
        print( 'data:', data, 'in', (time.time() - rtime) )
        if not data:
            break
    sock.close()
    sock = None
Xilef11 commented 1 year ago

Yeah, it just prints empty data:

connected!
data: b'' in 31.303014278411865
connected!
connection closed after  1.3680005073547363
connected!
data: b'' in 30.56010413169861
Oglaf commented 1 year ago

I recently bought a smart light imported and rebranded from a brazilian company with the same issue. Datasheet in portuguese, but I believe the numbers are understandable.

Unfortunately as soon as I connected to Smart Life it's firmware got updated to version 1.5.10 image

Although the firmware number is lower than my other smart lights (2.9.16), on Smart Life I noticed this one has more features: image

Even on device list, it has a quick access toolbar unlike the others: image

My devices.json:

{
        "name": "EWS 410",
        "id": "eb68e355da1be4ae69ok5o",
        "key": "6434389541e96704",
        "mac": "38:1f:8d:4f:66:f6",
        "category": "dj",
        "product_name": "EWS 410",
        "product_id": "tgfkxkkbcwbz1pmo",
        "biz_type": 18,
        "model": "EWS 410",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1553088530507BVYGE/16522947904d7f64da11e.png",
        "uuid": "8b05ecd80b3d2553"
    }

The error messages from TinyTuya are exactly the same and wireshark results are probably similar.

uzlonewolf commented 1 year ago

Can @Xilef11 or @Oglaf run this and let me know if it reports anything? Make sure to fill in your IP and local key.

import socket
import time
import struct
from hashlib import md5,sha256
from Crypto.Cipher import AES

ip = '192.168..'
key = b'YOUR LOCAL KEY'

for i in range( 2 ):
    sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    sock.settimeout( 5 )
    sock.connect( (ip, 6668) )
    print( 'connected!' )
    stime = time.time()
    local_nonce = b'0123456789abcdef' # not-so-random random key
    local_iv = local_nonce[:12]       # not-so-random random iv

    pkt = struct.pack( ">IHIII", 0x6699, 0, 1, 3, len(local_nonce)+len(local_iv)+16 )

    c = AES.new(key, AES.MODE_GCM, nonce=local_iv)
    c.update( pkt[4:] )
    encrypted, tag = c.encrypt_and_digest( local_nonce )

    pkt += local_iv + encrypted + tag + struct.pack( ">I", 0x9966 )

    #print( pkt )
    #print( pkt.hex() )

    sock.sendall( pkt )

    try:
        data = sock.recv( 4096 )
    except:
        data = None

    print( 'data:', data, 'in', (time.time() - stime) )

    sock.close()
    sock = None
Oglaf commented 1 year ago

Nop, nothing... I confirmed the code works with my other lightbulbs .

Results:

connected! data: None in 5.004519939422607 connected! data: None in 5.019267559051514

uzlonewolf commented 1 year ago

:facepalm: It would help if I get the format right. Replace struct.pack( ">IBIII" with struct.pack( ">IHIII". Or just wait a few hours and I'll hopefully have a PR in.

Xilef11 commented 1 year ago

That actually works! I think. At least there's some data, not sure if it's meaningful

connected!
data: b"\x00\x00f\x99\x00\x00\x00\x00\xe9~\x00\x00\x00\x04\x00\x00\x00Pk\xac\x89\xac#1T\x90\xbfy\xdb\xd6q^\x1e\xc5\xe7\x852k\x04\x11\x9fv\n\xdc\x97:d&|'q\x10\x9c\x1e\x08\xfa\xd00\x8b\xd8\x83Y\xe0k\xcfg\xe0\xe8\xc6\r\x06\x87\xf6nr\x10X\t\xb87\xb8\x08V\xf3\xd4\xad\x97\x14\xe6!\xaa\xfb\x0e)\x1e(\xa1.\x00\x00\x99f" in 0.020395755767822266
connected!
data: b'\x00\x00f\x99\x00\x00\x00\x00M\x10\x00\x00\x00\x04\x00\x00\x00PM-\x0b\xa5<\xe7p\xe0\xcc\x81\xa6d\xcf\xc5\xd5\xf2\xb1\x14\x91)\x8b\x93\xdf\xe2\x8a\x04p\xb4/p\nAJ\x96e\xff\xd0k\x0e\xf6Q\x9c\x0e3\x96}\xaa\x97\xd2{\xff\xd7\x93?\xca\xfb\x9f\xd6Qqh\x8b/\x80\xdbLvi\xf1@"Uj\xfeS\xd5\xfa\x16]\xf1\x00\x00\x99f' in 0.03944563865661621
uzlonewolf commented 1 year ago

Great, that's exactly what I need! I'm almost done adding these encryption routines and should have a PR for people to test in a bit.

Oglaf commented 1 year ago

FYI, got positive results:

connected!
data: b'\x00\x00f\x99\x00\x00\x00\x00\\\xd3\x00\x00\x00\x04\x00\x00\x00P\x0c\x1c\xef\xea\xccm\xe9\x16e\xd0z\\X\xc6\xf6\xfc\xe4;R\xf4\xdf\x0fI\x88\x8e\xd64\xa7\x11b\xa2\x1b"\xaeBL\xd3[n\x17n\x96/\xceX\xa1\x1d\xbe%\x11\x1fu\xf7\xecB,ytr*\xf55y\xf9R\x82/\xc8\xd57\x89!h\x95\xb7\x86\x9c\x80\xf2b\x00\x00\x99f' in 0.05198383331298828
connected!
data: b'\x00\x00f\x99\x00\x00\x00\x00\xa9B\x00\x00\x00\x04\x00\x00\x00P\x80\x1fJ\xc1~\xce\xf7\xb8\x14a\xa6\x95Wi\xc9\xc1\\\x9f/"\x16\xfd\x12-\xde\x85v\xfd\x8b\x96\xb1\xc7\x97\x84\xc8\xff<\xff\x7f\xacv6&\x8bM\xb4\xf9\x0f\xfd\xb9\'\xa7\xdf/5\xcc\x88Q\xcf\x91\xa6\xbc\xa1\x1f\x94\xbe\xe3\xee6! \\\'\xe3\xa7\x8f\xd0\x86$Z\x00\x00\x99f' in 0.11254739761352539

Thank you for your help @uzlonewolf !

uzlonewolf commented 1 year ago

Can everyone checkout https://github.com/jasonacox/tinytuya/pull/256 (aka https://github.com/uzlonewolf/tinytuya/tree/pv35 ) and let me know if it works?

Oglaf commented 1 year ago

It didn't work for me, but I'm new to python and git, so take my words with a grain of salt:

TinyTuya Setup Wizard [1.9.2]

    Existing settings:
        API Key=###############
        Secret=###################
        DeviceID=eb099f68fc98defbd6vqcs
        Region=us

    Use existing credentials (Y/n): y

Device Listing
[
    {
        "name": "Smart Plug WiFi  2",
        "id": "eb597c0e524d178a80caat",
        "key": "bdf5b78fccf86c7b",
        "mac": "d8:1f:12:d2:55:d1",
        "category": "cz",
        "product_name": "Smart Plug WiFi ",
        "product_id": "2vdttet77fzapqdf",
        "biz_type": 18,
        "model": "Smart Plug WiFi HS",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1546425778531nm5KI/8e223d38c0e5d08e23643cae1c61c2a2.png",
        "uuid": "96361f89fedd8ddc"
    },
    {
        "name": "Smart Plug WiFi",
        "id": "eb099f68fc98defbd6vqcs",
        "key": "dfd4cb0ca6a36d8a",
        "mac": "d8:1f:12:d2:57:71",
        "category": "cz",
        "product_name": "Smart Plug WiFi ",
        "product_id": "2vdttet77fzapqdf",
        "biz_type": 18,
        "model": "Smart Plug WiFi HS",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1546425778531nm5KI/8e223d38c0e5d08e23643cae1c61c2a2.png",
        "uuid": "4786659e5e96a906"
    },
    {
        "name": "EWS 410",
        "id": "eb68e355da1be4ae69ok5o",
        "key": "6434389541e96704",
        "mac": "38:1f:8d:4f:66:f6",
        "category": "dj",
        "product_name": "EWS 410",
        "product_id": "tgfkxkkbcwbz1pmo",
        "biz_type": 18,
        "model": "EWS 410",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1553088530507BVYGE/16522947904d7f64da11e.png",
        "uuid": "8b05ecd80b3d2553"
    },
    {
        "name": "Smart L\u00e2mpada WiFi 2",
        "id": "ebd1b02d382049733dnq0u",
        "key": "c383f271346743c0",
        "mac": "d8:1f:12:c9:54:66",
        "category": "dj",
        "product_name": "Smart L\u00e2mpada WiFi",
        "product_id": "97jzv6zysedaddxc",
        "biz_type": 18,
        "model": "",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1546425778531nm5KI/5042cb632711438f355ce344a1bad399.png",
        "uuid": "ce2396cec3d3d7ec"
    },
    {
        "name": "Smart L\u00e2mpada WiFi",
        "id": "eb3dcc68131b35ae344alc",
        "key": "d9bb19e75b0aa051",
        "mac": "d8:1f:12:c9:54:c4",
        "category": "dj",
        "product_name": "Smart L\u00e2mpada WiFi",
        "product_id": "97jzv6zysedaddxc",
        "biz_type": 18,
        "model": "",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1546425778531nm5KI/5042cb632711438f355ce344a1bad399.png",
        "uuid": "554138b8f93113f4"
    },
    {
        "name": "Pet feeder",
        "id": "eb629cf13d51f2d0d5gv7t",
        "key": "99af400dccb3a41b",
        "mac": "7c:f6:66:22:b7:b0",
        "category": "cwwsq",
        "product_name": "",
        "product_id": "5xierbs16mkdnkpk",
        "biz_type": 18,
        "model": "HIPETCOM",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1555070288771Se8MY/c41451115e38e81ad43d26da4fdd8acf.png",
        "uuid": "03e3e6923baf1b9d"
    },
    {
        "name": "Smart Plug",
        "id": "eb06b9ad96cc645217ruup",
        "key": "5cd62b469b6d961e",
        "mac": "7c:f6:66:86:bf:06",
        "category": "cz",
        "product_name": "Smart Plug",
        "product_id": "xtnehyamtpkge0se",
        "biz_type": 18,
        "model": "RMC004",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1522040095440mxmVM/374fbfba8459e53760343b36cfc7206c.png",
        "uuid": "0317e4c00e2dc8a4"
    },
    {
        "name": "Temperature Sensor",
        "id": "ebf3e7c38a62e56ab4a8jf",
        "key": "4c5186b1731b332a",
        "mac": "cc:8c:bf:2a:11:0d",
        "category": "wsdcg",
        "product_name": "WiFi Temperature & Humidity Sensor",
        "product_id": "q29ebws5adwye1l8",
        "biz_type": 18,
        "model": "TH-02",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay15427647462366edzT/61478454256bce1df83842a74a02e9e8.png",
        "uuid": "0f5fba37ea08579b"
    },
    {
        "name": "Cleaner Robot",
        "id": "eb1f0804f3145f2189grsj",
        "key": "25b2c81f286581e7",
        "mac": "70:89:76:1b:67:f1",
        "category": "sd",
        "product_name": "KaBuM!Rob\u00f4 aspirador de p\u00f3",
        "product_id": "wexaeucvbdawkkpo",
        "biz_type": 18,
        "model": "XR011R",
        "sub": false,
        "icon": "https://images.tuyaus.com/smart/icon/ay1567915509987ktVbv/0b7e04acdbf9b7110def7a7ca08e6e09.png",
        "uuid": "e0dcac99701a2118"
    }
]

>> Saving list to devices.json
    9 registered devices saved

>> Saving raw TuyaPlatform response to tuya-raw.json

Poll local devices? (Y/n): y

Scanning local network for Tuya devices (retry 34 times)...
Traceback (most recent call last):
  File "C:\Program Files\WindowsApps\PythonSoftwareFoundation.Python.3.10_3.10.2544.0_x64__qbz5n2kfra8p0\lib\runpy.py", line 196, in _run_module_as_main
    return _run_code(code, main_globals, None,
  File "C:\Program Files\WindowsApps\PythonSoftwareFoundation.Python.3.10_3.10.2544.0_x64__qbz5n2kfra8p0\lib\runpy.py", line 86, in _run_code
    exec(code, run_globals)
  File "C:\Users\chris\OneDrive\Documents\GitHub\tinytuya\tinytuya\__main__.py", line 82, in <module>
    wizard.wizard(color=color, forcescan=force)
  File "C:\Users\chris\OneDrive\Documents\GitHub\tinytuya\tinytuya\wizard.py", line 270, in wizard
    devices = tinytuya.deviceScan(False, retries)
  File "C:\Users\chris\OneDrive\Documents\GitHub\tinytuya\tinytuya\core.py", line 1780, in deviceScan
    return scanner.devices(verbose=verbose, maxretry=maxretry, color=color, poll=poll, forcescan=forcescan, byID=byID)
TypeError: devices() got an unexpected keyword argument 'maxretry'
jasonacox commented 1 year ago

Thanks, @Oglaf please try python3 -m tinytuya scan

uzlonewolf commented 1 year ago

Ugh, looks like we have another scanner bug >_> I guess that wizard rewrite is going to happen sooner than I was expecting.

Oglaf commented 1 year ago

Thanks, @Oglaf please try python3 -m tinytuya scan

Same issue as before:

TinyTuya (Tuya device scanner) [1.9.2]

[Loaded devices.json - 9 devices]

Scanning on UDP ports 6666 and 6667 and 7000 for devices for 18 seconds...

Pet feeder   Product ID = 5xierbs16mkdnkpk  [Valid Broadcast]:
    Address = 192.168.1.200   Device ID = eb629cf13d51f2d0d5gv7t (len:22)  Local Key = 99af400dccb3a41b  Version = 3.3  Type = default, MAC = 7c:f6:66:22:b7:b0
    Status: {'4': 'standby', '14': 0, '15': 1}
Smart Plug WiFi   Product ID = keydnqmh87c8ajv4  [Valid Broadcast]:
    Address = 192.168.1.206   Device ID = eb099f68fc98defbd6vqcs (len:22)  Local Key = dfd4cb0ca6a36d8a  Version = 3.3  Type = default, MAC = d8:1f:12:d2:57:71
    Status: {'1': False, '9': 0, '17': 2, '18': 0, '19': 0, '20': 1266, '21': 1, '22': 625, '23': 31468, '24': 18126, '25': 1148, '26': 0}
Smart Lâmpada WiFi 2   Product ID = keytg5kq8gvkv9dh  [Valid Broadcast]:
    Address = 192.168.1.204   Device ID = ebd1b02d382049733dnq0u (len:22)  Local Key = c383f271346743c0  Version = 3.3  Type = default, MAC = d8:1f:12:c9:54:66
    Status: {'20': True, '21': 'white', '22': 332, '23': 0, '24': '0159023b0006', '25': '010e0d0000000000000003e801f4', '26': 0, '34': False}
*  Unexpected payload from '192.168.1.205' to port 6667: '\x00\x00\x00\x00{"ip":"192.168.1.205","gwId":"eb68e355da1be4ae69ok5o","uuid":"8b05ecd80b3d2553","active":2,"ablilty":0,"encrypt":true,"productKey":"key8u54q9dtru5jw","version":"3.5","token":true,"wf_cfg":true,"clientLink":3}' (b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xf0`\xc9~aP\xc7\xd4\xcaG\x93Y\xcf\x8a\x87;FAx\x0c\xbfNA\x1f7\xc4\x86$S\xd8xY.P\xee/\xee}\xf2"\xef\xfe\xf6^Ce\x15>\x07\xa3\x95G\x95\xd4)\xfe\x1b_\xccx\xb9\xd3\x96\xf1\xca\xd7\xc2\xdc\xe4\x8d\x8d{\xb2\xc0\x89\xda\x80\x0c\x93k\x1b\xd4\xccx\xc0\xe5\xb5\'\x0f\x1d\xd7c\xfa!\xcc\xec7\xc6\xcdTW\xe4\x940\x89\xe2 kR\x97\xd3\x9c\x03\xa7]\x89\x81\xc2\n.\x8ai\xe7\xb4l\x99QZ\xae]\xd3\xe0\xee\xb1\x85S\xe5\xb0I4\x18\x01\x86\x15@\xa1?g\xd2\x17*\x1e\xdc\xd4\x99@G\xdb\x85\xc5\x80\x03z\x8f\x8f\x98\xd0\xd9d\xc7Qc}4\xafXS\x9c\xa51\xca\xcdWg\xad\x8e\x7f\xa4\x17\x06!\x13yaL<\xa4\'\xf7[^\xab\xbe\x96C2\xb0\xaf\xfd\x89\x93\xfe\x99\xf4\xdf1\xde\xa3\x98\x96\xbe\xdf\x9a36\xcad\x18P\xf5z\x03\xc6%\xbfp\xa0\x17O@\xc2\x00\x00\x99f')

Smart Plug WiFi  2   Product ID = keydnqmh87c8ajv4  [Valid Broadcast]:
    Address = 192.168.1.207   Device ID = eb597c0e524d178a80caat (len:22)  Local Key = bdf5b78fccf86c7b  Version = 3.3  Type = default, MAC = d8:1f:12:d2:55:d1
    Status: {'1': True, '9': 0, '17': 99, '18': 1035, '19': 1270, '20': 1262, '21': 1, '22': 617, '23': 31090, '24': 17649, '25': 1180, '26': 0}
Smart Plug   Product ID = keym9qkuywghyrvs  [Valid Broadcast]:
    Address = 192.168.1.201   Device ID = eb06b9ad96cc645217ruup (len:22)  Local Key = 5cd62b469b6d961e  Version = 3.3  Type = default, MAC = 7c:f6:66:86:bf:06
    Status: {'1': False, '9': 0, '17': 4, '18': 0, '19': 0, '20': 1262, '21': 1, '22': 564, '23': 29000, '24': 15795, '25': 2640, '26': 0, '38': 'memory', '41': '', '42': '', '46': True}
Smart Lâmpada WiFi   Product ID = keytg5kq8gvkv9dh  [Valid Broadcast]:
    Address = 192.168.1.203   Device ID = eb3dcc68131b35ae344alc (len:22)  Local Key = d9bb19e75b0aa051  Version = 3.3  Type = default, MAC = d8:1f:12:c9:54:c4
    Status: {'20': False, '21': 'white', '22': 678, '23': 0, '24': '003c03e802d9', '25': '000e0d0000000000000000c80000', '26': 0, '34': False}
*  Unexpected payload from '192.168.1.205' to port 6667: '\x00\x00\x00\x00{"ip":"192.168.1.205","gwId":"eb68e355da1be4ae69ok5o","uuid":"8b05ecd80b3d2553","active":2,"ablilty":0,"encrypt":true,"productKey":"key8u54q9dtru5jw","version":"3.5","token":true,"wf_cfg":true,"clientLink":3}' (b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xf0\xeb\x8d\xea\xd80$\x07\xd6n\x16d\xcc\x8d\xf7t\x12\xf2\xd9~EM+f\xcbdwBf\xdc\xf5uS\x8c\x0b\xa7nH\x17h\x17\x18\xfd\xb8l/*\xabe\x03Z~?\xc5\x8agz\xa3 \x83q\xf7\x1f\xd0zT\x1d\xfb\xa5\x80\xd5\x8af\x054\t\xbd-L\x0c\x16\xb3n{\xce\xfc\xd6+M\xd9\xea.\x06\x01\xa8CD\xa5u\xb6\xce:\xceG_\x8a\xcal7\xea\x9c\xa2\xce\n\xaa\xa9\xb5\xc9\x90\x9b<\xcd\xd0*\x06\xd3\x97\xe5\xae&E5\x18\x90p.\x0b\xb7\x16_\x11K\xb3\x173Z@@\x96m0\xb6Efp\xfa\xe1g\x129;I\xb0\xfaw\xab\xa4\x88\xe7\x81\x90\x12m\x14k\xa5SN/\x86\n\xfdG%\x86\x07/z\xb3\xacK\x9f12#\xd7\xed\x1e6\x93\x05\xd6\xe0\x9cb\xfd\xe11\xf7\xfb\x85\xaa`\x95\xe5\xd9\x14^e\x99k\xf5\xf1x&\xbe\xca\x135OL\xd2-\xfe\xf6>\x08\xad\x08\xad\xb3\x00\x00\x99f')

*  Unexpected payload from '192.168.1.205' to port 6667: '\x00\x00\x00\x00{"ip":"192.168.1.205","gwId":"eb68e355da1be4ae69ok5o","uuid":"8b05ecd80b3d2553","active":2,"ablilty":0,"encrypt":true,"productKey":"key8u54q9dtru5jw","version":"3.5","token":true,"wf_cfg":true,"clientLink":3}' (b'\x00\x00f\x99\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00\xf0$3\xd6i\xe9\xa1\x9a\x07\x84@\xf2>{\xd9\x9bFH\x10\xce\xbb.\xc5\xf7\xba\xcb7U\x81\x91\xe7\x00\xd3H\x05Q\xf3+\x11\xcc\xa4\xb0\xe0\xa3\x1e\x18<\xdeG\xb1\xea_\xab\xd9\xe8"\xff\xc8j\xf7\xa4\x06Y\x14\xc3enf\xc2\x93\xf8\x83\xe3b\xb8\xf9\xabn\x87{\xd6p\ri\x02\\\xef?}j\x01\xec\xce\xf03\xe6\x18t\x8d[WF\xff\x03f2\x9d=Op\xb4\x18\xae\xe9S0\xe3\xcb\xf13\xb1}\xd2\xf9{\xd0)\xfd}\x13\x88\xb0\xc1q\x14\xca\xf9u\xa3{\xf9\xbd/\x1e\x89\xaeUh%pALd\x1b\xd74\xd53\x88\xc4\xf4\xc1\xbe\xa4\xaaTx \x95.W\xfd\x1d+\xafvg\xb8i\xb2;\x86\x1a\x83\xa3oqc>i\xb6\xfe\xb9\xf6\xed\xbe\x9b|\x88m\nk\xba\xadI\xd2\x83\xfcKF\xcad\xf2\xae\x99\'V\x99W\x86\xf6\xc9\xf9\x89E)\xdf\xa9a\xac6\x9d\x1b\xda\xe0\x91\x97LB\xb2\xf0\x00\x00\x99f')

Scan completed in 18.028 seconds

Scan Complete!  Found 6 devices.
Broadcasted: 6
Versions: 3.3: 6
uzlonewolf commented 1 year ago

Can you do a git pull and try the python3 -m tinytuya scan again? I fixed a few things ~30 minutes ago.

Oglaf commented 1 year ago

Not sure if it works...

PS C:\Users\chris\OneDrive\Documents\GitHub\tinytuya> python -m tinytuya scan

TinyTuya (Tuya device scanner) [1.9.2]

[Loaded devices.json - 9 devices]

Scanning on UDP ports 6666 and 6667 and 7000 for devices for 18 seconds...

Smart Plug   Product ID = keym9qkuywghyrvs  [Valid Broadcast]:
    Address = 192.168.1.201   Device ID = eb06b9ad96cc645217ruup (len:22)  Local Key = 5cd62b469b6d961e  Version = 3.3  Type = default, MAC = 7c:f6:66:86:bf:06
    Status: {'1': False, '9': 0, '17': 4, '18': 0, '19': 0, '20': 1266, '21': 1, '22': 564, '23': 29000, '24': 15795, '25': 2640, '26': 0, '38': 'memory', '41': '', '42': '', '46': True}
Smart Plug WiFi   Product ID = keydnqmh87c8ajv4  [Valid Broadcast]:
    Address = 192.168.1.206   Device ID = eb099f68fc98defbd6vqcs (len:22)  Local Key = dfd4cb0ca6a36d8a  Version = 3.3  Type = default, MAC = d8:1f:12:d2:57:71
    Status: {'1': False, '9': 0, '17': 2, '18': 0, '19': 0, '20': 1266, '21': 1, '22': 625, '23': 31468, '24': 18126, '25': 1148, '26': 0}
Pet feeder   Product ID = 5xierbs16mkdnkpk  [Valid Broadcast]:
    Address = 192.168.1.200   Device ID = eb629cf13d51f2d0d5gv7t (len:22)  Local Key = 99af400dccb3a41b  Version = 3.3  Type = default, MAC = 7c:f6:66:22:b7:b0
    Status: {'4': 'standby', '14': 0, '15': 1}
Smart Lâmpada WiFi   Product ID = keytg5kq8gvkv9dh  [Valid Broadcast]:
    Address = 192.168.1.203   Device ID = eb3dcc68131b35ae344alc (len:22)  Local Key = d9bb19e75b0aa051  Version = 3.3  Type = default, MAC = d8:1f:12:c9:54:c4
    Status: {'20': False, '21': 'white', '22': 678, '23': 0, '24': '003c03e802d9', '25': '000e0d0000000000000000c80000', '26': 0, '34': False}
Smart Lâmpada WiFi 2   Product ID = keytg5kq8gvkv9dh  [Valid Broadcast]:
    Address = 192.168.1.204   Device ID = ebd1b02d382049733dnq0u (len:22)  Local Key = c383f271346743c0  Version = 3.3  Type = default, MAC = d8:1f:12:c9:54:66
    Status: {'20': True, '21': 'white', '22': 235, '23': 0, '24': '0159023b0006', '25': '010e0d0000000000000003e801f4', '26': 0, '34': False}
Smart Plug WiFi  2   Product ID = keydnqmh87c8ajv4  [Valid Broadcast]:
    Address = 192.168.1.207   Device ID = eb597c0e524d178a80caat (len:22)  Local Key = bdf5b78fccf86c7b  Version = 3.3  Type = default, MAC = d8:1f:12:d2:55:d1
    Status: {'1': True, '9': 0, '17': 100, '18': 1304, '19': 1344, '20': 1269, '21': 1, '22': 617, '23': 31090, '24': 17649, '25': 1180, '26': 0}
EWS 410   Product ID = key8u54q9dtru5jw  [Valid Broadcast]:
    Address = 192.168.1.205   Device ID = eb68e355da1be4ae69ok5o (len:22)  Local Key = 6434389541e96704  Version = 3.5  Type = default, MAC = 38:1f:8d:4f:66:f6
    Polling 192.168.1.205 Failed: No response
Scan completed in 18.0115 seconds

Scan Complete!  Found 7 devices.
Broadcasted: 7
Versions: 3.3: 6, 3.5: 1

Edit: Wizard gave same error.

Scanning local network for Tuya devices (retry 34 times)...
Traceback (most recent call last):
  File "C:\Program Files\WindowsApps\PythonSoftwareFoundation.Python.3.10_3.10.2544.0_x64__qbz5n2kfra8p0\lib\runpy.py", line 196, in _run_module_as_main
    return _run_code(code, main_globals, None,
  File "C:\Program Files\WindowsApps\PythonSoftwareFoundation.Python.3.10_3.10.2544.0_x64__qbz5n2kfra8p0\lib\runpy.py", line 86, in _run_code
    exec(code, run_globals)
  File "C:\Users\chris\OneDrive\Documents\GitHub\tinytuya\tinytuya\__main__.py", line 82, in <module>
    wizard.wizard(color=color, forcescan=force)
  File "C:\Users\chris\OneDrive\Documents\GitHub\tinytuya\tinytuya\wizard.py", line 270, in wizard
    devices = tinytuya.deviceScan(False, retries)
  File "C:\Users\chris\OneDrive\Documents\GitHub\tinytuya\tinytuya\core.py", line 1780, in deviceScan
    return scanner.devices(verbose=verbose, maxretry=maxretry, color=color, poll=poll, forcescan=forcescan, byID=byID)
TypeError: devices() got an unexpected keyword argument 'maxretry'
Xilef11 commented 1 year ago

Scanning "kind of" works, but polling fails (commit #5e06641)

TinyTuya (Tuya device scanner) [1.9.2]

[Loaded devices.json - 3 devices]

Scanning on UDP ports 6666 and 6667 and 7000 for devices for 18 seconds...

36819   Product ID = key8u54q9dtru5jw  [Valid Broadcast]:
    Address = 192.168.2.46   Device ID = ebf310edb88d15f0edyr5i (len:22)  Local Key = [key here]  Version = 3.5  Type = default, MAC = 38:1f:8d:36:d2:03
    Polling 192.168.2.46 Failed: No response
Scan completed in 18.1071 seconds

Scan Complete!  Found 2 devices.
Broadcasted: 2
Versions: 3.3: 1, 3.5: 1
uzlonewolf commented 1 year ago

When you get a chance please do a git pull and try the scan/poll again.

Oglaf commented 1 year ago

Same results. Scan fails to obtain DP values Polling 192.168.1.205 Failed: No response and Wizard throws TypeError: devices() got an unexpected keyword argument 'maxretry error.

Xilef11 commented 1 year ago

Still polling xxx failed: No response. Side note is this the right commit? Just want to make sure I'm testing the right thing

commit 11a3e2eb9720bb8a791f4c46cbef44a375640c7f (HEAD -> pv35, origin/pv35, origin/master, origin/HEAD, master)
Author: Jason A. Cox <jason@jasonacox.com>
Date:   Sat Jan 14 22:55:36 2023 -0800

    Timeout error handling
jasonacox commented 1 year ago

@Oglaf the new scanner updates from @uzlonewolf changed maxretry to scantime, but there were shortcut function in the core library that still referenced maxretry. Good catch! I fixed the mapping and pushed the change. Are you pulling from https://github.com/jasonacox/tinytuya.git ?

import tinytuya

tinytuya.set_debug(True)
tinytuya.scan()
Oglaf commented 1 year ago

I initially did a checkout on @uzlonewolf last commit, but then I created a fork which I keep synchronized with master branch. Because I'm not familiar with VSCode and Git I'm checking every commit and manually comparing my local repository to make sure I'm up-to-date.

Your last commit 637c9aeefd03706741cd6f1e11a1c3a813458a86 fixed the reference error, now I'm able to proceed with Wizard and poll local devices:

Polling local devices...
    [Smart Plug WiFi  2] - 192.168.1.207 - On - DPS: {'1': True, '9': 0, '17': 37, '18': 483, '19': 681, '20': 1269, '21': 1, '22': 617, '23': 31090, '24': 17649, '25': 1180, '26': 0}
    [Smart Plug WiFi] - 192.168.1.206 - Off - DPS: {'1': False, '9': 0, '17': 43, '18': 0, '19': 0, '20': 1279, '21': 1, '22': 625, '23': 31468, '24': 18126, '25': 1148, '26': 0}
    [EWS 410] - 192.168.1.205 - No Response
    [Smart Lâmpada WiFi 2] - 192.168.1.204 - Off - DPS: {'20': False, '21': 'white', '22': 18, '23': 0, '24': '0159023b0006', '25': '010e0d0000000000000003e801f4', '26': 0, '34': False}
    [Smart Lâmpada WiFi] - 192.168.1.203 - Off - DPS: {'20': False, '21': 'white', '22': 678, '23': 0, '24': '003c03e802d9', '25': '000e0d0000000000000000c80000', '26': 0, '34': False}
    [Pet feeder] - 192.168.1.200 - DPS: {'4': 'standby', '14': 0, '15': 1}
    [Smart Plug] - 192.168.1.201 - Off - DPS: {'1': False, '9': 0, '17': 12, '18': 0, '19': 0, '20': 1270, '21': 1, '22': 564, '23': 29000, '24': 15795, '25': 2640, '26': 0, '38': 'memory', '41': '', '42': '', '46': True}
    [Temperature Sensor] - 0 - Error: No IP found
    [Cleaner Robot] - 0 - Error: No IP found

Debug results:

DEBUG:TinyTuya [1.10.0]

DEBUG:loaded=devices.json [9 devices]

TinyTuya (Tuya device scanner) [1.10.0]

[Loaded devices.json - 9 devices]

Scanning on UDP ports 6666 and 6667 and 7000 for devices for 18 seconds...

DEBUG:Listening for Tuya devices on UDP 6666 and 6667 and 7000
DEBUG:Received valid UDP packet: {'ip': '192.168.1.201', 'gwId': 'eb06b9ad96cc645217ruup', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keym9qkuywghyrvs', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"eb06b9ad96cc645217ruup","devId":"eb06b9ad96cc645217ruup","uid":"eb06b9ad96cc645217ruup","t":"1673812670"}'
DEBUG:payload encrypted=b'000055aa000000010000000a00000088ae824cd3c5ce254c02e5cef871d618279aedaf373afba7789d8b182f0261e0f7691d76f63f57f487fddb35cec93cb7c97d60147af2e50dd8636c8c771e9193508d2a62ec5ea47c98c9ce3b7eeb74aabe9aedaf373afba7789d8b182f0261e0f726e901426208685bf21a26c3c44753abdd71e6d3ade89a41a05b7908b8eb23087e7f2e420000aa55'
DEBUG:PollDevice: raw unpacked message = TuyaMessage(seqno=1, cmd=10, retcode=0, payload=b'\xea\xa3O3\xfe\xd4\xf6\xde-\x0f\xc7/\x7f\x1f\x06\xff\x1bF?32\xd7\xea\x9f\x8c,\xb9G"z\n\x07\x9e\xfa\x94\xd5\xe9\x17\xf3\x8e\x89\'\xef\xb0*\xe1\x02_\x02\x97\xfa\xdfi^\x9aRM\x86/\xedw\xa7\x08v\xf2|>\xb1\xf30QL\x8c\x9e\x91\x1fAaa(\x88\xde\xec\xef\x8e/\xf6*\xc9\x05j\xb8\xdaX5(\xabe\xf1\x8a\xbc\xdf\x97\x9c\xa6\xb8 J\x07\xda\xcc\xd0\xe1if\xd2\x97H\xc1\x0b\x8a\xf2\xe2Q\x86\xa8\xde\xcd\xcc\xef\x17\xa6\xec\xda\xe1\x1f\xe6\xe1\x15\x05\xce/,\xfb]K\xef-\xc3\x19\x9ff\x99d\x98\xd4\xcd7\xaa[', crc=3997760664, crc_good=True, prefix=21930, iv=None)
DEBUG:decode payload=b'\xea\xa3O3\xfe\xd4\xf6\xde-\x0f\xc7/\x7f\x1f\x06\xff\x1bF?32\xd7\xea\x9f\x8c,\xb9G"z\n\x07\x9e\xfa\x94\xd5\xe9\x17\xf3\x8e\x89\'\xef\xb0*\xe1\x02_\x02\x97\xfa\xdfi^\x9aRM\x86/\xedw\xa7\x08v\xf2|>\xb1\xf30QL\x8c\x9e\x91\x1fAaa(\x88\xde\xec\xef\x8e/\xf6*\xc9\x05j\xb8\xdaX5(\xabe\xf1\x8a\xbc\xdf\x97\x9c\xa6\xb8 J\x07\xda\xcc\xd0\xe1if\xd2\x97H\xc1\x0b\x8a\xf2\xe2Q\x86\xa8\xde\xcd\xcc\xef\x17\xa6\xec\xda\xe1\x1f\xe6\xe1\x15\x05\xce/,\xfb]K\xef-\xc3\x19\x9ff\x99d\x98\xd4\xcd7\xaa['
DEBUG:decrypting=b'\xea\xa3O3\xfe\xd4\xf6\xde-\x0f\xc7/\x7f\x1f\x06\xff\x1bF?32\xd7\xea\x9f\x8c,\xb9G"z\n\x07\x9e\xfa\x94\xd5\xe9\x17\xf3\x8e\x89\'\xef\xb0*\xe1\x02_\x02\x97\xfa\xdfi^\x9aRM\x86/\xedw\xa7\x08v\xf2|>\xb1\xf30QL\x8c\x9e\x91\x1fAaa(\x88\xde\xec\xef\x8e/\xf6*\xc9\x05j\xb8\xdaX5(\xabe\xf1\x8a\xbc\xdf\x97\x9c\xa6\xb8 J\x07\xda\xcc\xd0\xe1if\xd2\x97H\xc1\x0b\x8a\xf2\xe2Q\x86\xa8\xde\xcd\xcc\xef\x17\xa6\xec\xda\xe1\x1f\xe6\xe1\x15\x05\xce/,\xfb]K\xef-\xc3\x19\x9ff\x99d\x98\xd4\xcd7\xaa['
DEBUG:decrypted 3.x payload='{"dps":{"1":false,"9":0,"17":12,"18":0,"19":0,"20":1266,"21":1,"22":564,"23":29000,"24":15795,"25":2640,"26":0,"38":"memory","41":"","42":"","46":true}}'
DEBUG:payload type = <class 'str'>
DEBUG:decoded results='{"dps":{"1":false,"9":0,"17":12,"18":0,"19":0,"20":1266,"21":1,"22":564,"23":29000,"24":15795,"25":2640,"26":0,"38":"memory","41":"","42":"","46":true}}'
Smart Plug   Product ID = keym9qkuywghyrvs  [Valid Broadcast]:
    Address = 192.168.1.201   Device ID = eb06b9ad96cc645217ruup (len:22)  Local Key = 5cd62b469b6d961e  Version = 3.3  Type = default, MAC = 7c:f6:66:86:bf:06
    Status: {'1': False, '9': 0, '17': 12, '18': 0, '19': 0, '20': 1266, '21': 1, '22': 564, '23': 29000, '24': 15795, '25': 2640, '26': 0, '38': 'memory', '41': '', '42': '', '46': True}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.200', 'gwId': 'eb629cf13d51f2d0d5gv7t', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': '5xierbs16mkdnkpk', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"eb629cf13d51f2d0d5gv7t","devId":"eb629cf13d51f2d0d5gv7t","uid":"eb629cf13d51f2d0d5gv7t","t":"1673812671"}'
DEBUG:payload encrypted=b'000055aa000000010000000a0000008854f69e139e34719bd6a58465f68154c3f0be41a501d50ded9a5952d23e7cb2fff75dc63d516f68ba63f3eee73b1e66d5121ab4251b5d0a727bbb350d14b37cb8c421d7dfbf63c3f8f4d462f1593447e1f0be41a501d50ded9a5952d23e7cb2ffca6a28a79257deb7aca4912adf4689d22051719b55b0b6ece8c06379e421d21525b74a410000aa55'
DEBUG:PollDevice: raw unpacked message = TuyaMessage(seqno=1, cmd=10, retcode=0, payload=b'[\n\x1f\x99j\x15N\x9a\x95\xc2\xa9r*\xa6_\xccb\xed\xaa~\xba\x90C\x13NFi\t.\xec]*\xe7\x82\x8f9\xf3Yi)7\x8fbB\x98":)', crc=1440328528, crc_good=True, prefix=21930, iv=None)
DEBUG:decode payload=b'[\n\x1f\x99j\x15N\x9a\x95\xc2\xa9r*\xa6_\xccb\xed\xaa~\xba\x90C\x13NFi\t.\xec]*\xe7\x82\x8f9\xf3Yi)7\x8fbB\x98":)'
DEBUG:decrypting=b'[\n\x1f\x99j\x15N\x9a\x95\xc2\xa9r*\xa6_\xccb\xed\xaa~\xba\x90C\x13NFi\t.\xec]*\xe7\x82\x8f9\xf3Yi)7\x8fbB\x98":)'
DEBUG:decrypted 3.x payload='{"dps":{"4":"standby","14":0,"15":1}}'
DEBUG:payload type = <class 'str'>
DEBUG:decoded results='{"dps":{"4":"standby","14":0,"15":1}}'
Pet feeder   Product ID = 5xierbs16mkdnkpk  [Valid Broadcast]:
    Address = 192.168.1.200   Device ID = eb629cf13d51f2d0d5gv7t (len:22)  Local Key = 99af400dccb3a41b  Version = 3.3  Type = default, MAC = 7c:f6:66:22:b7:b0
    Status: {'4': 'standby', '14': 0, '15': 1}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.207', 'gwId': 'eb597c0e524d178a80caat', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keydnqmh87c8ajv4', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"eb597c0e524d178a80caat","devId":"eb597c0e524d178a80caat","uid":"eb597c0e524d178a80caat","t":"1673812672"}'
DEBUG:payload encrypted=b'000055aa000000010000000a00000088c06cdd1414d7dfae99780b501e2deadd9cad8483a9af03d5b62ea745d000ba28f6931b9c03fe14181b254666e0671a1d0d20c9fe80d9c8d5285d9134b27607c76c5bddf25ffe131901f4d9fce05b59789cad8483a9af03d5b62ea745d000ba28da0ac8fa36287fcd80184b6d18ddab41a6fd6b6a5fce3c15408b3176c2594fb0d099603f0000aa55'
DEBUG:PollDevice: raw unpacked message = TuyaMessage(seqno=1, cmd=10, retcode=0, payload=b'\xecU\xf0Me\xca\x01 \xa3\xe7\xab$\xd9?\xfc\x80\xa0\x0cY\xbc$p8\xc0\x17N\x02\xc0%G\x8aE5f\xf5\x1b_\x8ed\x1d\xbem\x04_\n\xc8\xfcB3\xfaK\x1f \xd8\xe8\xbd\xa8\xcd\xe9\xdf:\x01b\xd83\x0fL[\x16\xe7\x0e\xffY4zY/\xa2\xf7rh%<S\xfc8\x92<\x1f#\xb887\xe1+\x92S\xedP2[i \xd26^\xe5\xeb\xdf\xd5\xc5\x920:\xf5\xc5{\x93\x81L\xf1O\x01\xd5\xed\xf0\x8bx', crc=76159185, crc_good=True, prefix=21930, iv=None)
DEBUG:decode payload=b'\xecU\xf0Me\xca\x01 \xa3\xe7\xab$\xd9?\xfc\x80\xa0\x0cY\xbc$p8\xc0\x17N\x02\xc0%G\x8aE5f\xf5\x1b_\x8ed\x1d\xbem\x04_\n\xc8\xfcB3\xfaK\x1f \xd8\xe8\xbd\xa8\xcd\xe9\xdf:\x01b\xd83\x0fL[\x16\xe7\x0e\xffY4zY/\xa2\xf7rh%<S\xfc8\x92<\x1f#\xb887\xe1+\x92S\xedP2[i \xd26^\xe5\xeb\xdf\xd5\xc5\x920:\xf5\xc5{\x93\x81L\xf1O\x01\xd5\xed\xf0\x8bx'
DEBUG:decrypting=b'\xecU\xf0Me\xca\x01 \xa3\xe7\xab$\xd9?\xfc\x80\xa0\x0cY\xbc$p8\xc0\x17N\x02\xc0%G\x8aE5f\xf5\x1b_\x8ed\x1d\xbem\x04_\n\xc8\xfcB3\xfaK\x1f \xd8\xe8\xbd\xa8\xcd\xe9\xdf:\x01b\xd83\x0fL[\x16\xe7\x0e\xffY4zY/\xa2\xf7rh%<S\xfc8\x92<\x1f#\xb887\xe1+\x92S\xedP2[i \xd26^\xe5\xeb\xdf\xd5\xc5\x920:\xf5\xc5{\x93\x81L\xf1O\x01\xd5\xed\xf0\x8bx'
DEBUG:decrypted 3.x payload='{"dps":{"1":true,"9":0,"17":55,"18":735,"19":896,"20":1262,"21":1,"22":617,"23":31090,"24":17649,"25":1180,"26":0}}'
DEBUG:payload type = <class 'str'>
DEBUG:decoded results='{"dps":{"1":true,"9":0,"17":55,"18":735,"19":896,"20":1262,"21":1,"22":617,"23":31090,"24":17649,"25":1180,"26":0}}'
Smart Plug WiFi  2   Product ID = keydnqmh87c8ajv4  [Valid Broadcast]:
    Address = 192.168.1.207   Device ID = eb597c0e524d178a80caat (len:22)  Local Key = bdf5b78fccf86c7b  Version = 3.3  Type = default, MAC = d8:1f:12:d2:55:d1
    Status: {'1': True, '9': 0, '17': 55, '18': 735, '19': 896, '20': 1262, '21': 1, '22': 617, '23': 31090, '24': 17649, '25': 1180, '26': 0}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.203', 'gwId': 'eb3dcc68131b35ae344alc', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keytg5kq8gvkv9dh', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"eb3dcc68131b35ae344alc","devId":"eb3dcc68131b35ae344alc","uid":"eb3dcc68131b35ae344alc","t":"1673812673"}'
DEBUG:payload encrypted=b'000055aa000000010000000a000000884aa176a65a996620a88c47436da6a3197dfe03150d2654b343d42e8fb8264e6bd71e49240b16e6f941d88d52d40bac4f668cb8d4d93bb3b5fb8948c809ca94010daa32f0aee7d457a4bae303ef5eac0d7dfe03150d2654b343d42e8fb8264e6b68d3a99f871a3f9f92d4e275d296f1c48a98eff3014875bdf1186180c935c735d8274dd80000aa55'
DEBUG:PollDevice: raw unpacked message = TuyaMessage(seqno=1, cmd=10, retcode=0, payload=b"\x02R~\x04Q\xb7}l\xca\xfd\x86[SeK\xae'\xb6\xc3:\x10]@\xee\xbcq\xf0\xd9\xe6'\x89+\xef2\xcf\xa2}M\xad\\\xb7'2\x03yQ\x1d\xc6\xc9{\x01BT\xa4\xc1\xe6\xc4\xd6\xcd\xf8\xdc\xc1\x10\xb7\xb6t\x9a\x11\x92Rp\x94\t\xe2\x87]\xb2\xe3\xed\xf0v\x19:\x0e\xf4T`\x8f;\xaa\xba`\xc1YuR\x9dJrF\xf2_\x15w\x1d\xe7'+\xd4\xa8\xf9y\xd5\x8f\x7f\x17\xbb\x91\xb46\x1c\x0bo\xf9\xe3\xdcr\x8a", crc=529369677, crc_good=True, prefix=21930, iv=None)
DEBUG:decode payload=b"\x02R~\x04Q\xb7}l\xca\xfd\x86[SeK\xae'\xb6\xc3:\x10]@\xee\xbcq\xf0\xd9\xe6'\x89+\xef2\xcf\xa2}M\xad\\\xb7'2\x03yQ\x1d\xc6\xc9{\x01BT\xa4\xc1\xe6\xc4\xd6\xcd\xf8\xdc\xc1\x10\xb7\xb6t\x9a\x11\x92Rp\x94\t\xe2\x87]\xb2\xe3\xed\xf0v\x19:\x0e\xf4T`\x8f;\xaa\xba`\xc1YuR\x9dJrF\xf2_\x15w\x1d\xe7'+\xd4\xa8\xf9y\xd5\x8f\x7f\x17\xbb\x91\xb46\x1c\x0bo\xf9\xe3\xdcr\x8a"
DEBUG:decrypting=b"\x02R~\x04Q\xb7}l\xca\xfd\x86[SeK\xae'\xb6\xc3:\x10]@\xee\xbcq\xf0\xd9\xe6'\x89+\xef2\xcf\xa2}M\xad\\\xb7'2\x03yQ\x1d\xc6\xc9{\x01BT\xa4\xc1\xe6\xc4\xd6\xcd\xf8\xdc\xc1\x10\xb7\xb6t\x9a\x11\x92Rp\x94\t\xe2\x87]\xb2\xe3\xed\xf0v\x19:\x0e\xf4T`\x8f;\xaa\xba`\xc1YuR\x9dJrF\xf2_\x15w\x1d\xe7'+\xd4\xa8\xf9y\xd5\x8f\x7f\x17\xbb\x91\xb46\x1c\x0bo\xf9\xe3\xdcr\x8a"
DEBUG:decrypted 3.x payload='{"dps":{"20":false,"21":"white","22":678,"23":0,"24":"003c03e802d9","25":"000e0d0000000000000000c80000","26":0,"34":false}}'
DEBUG:payload type = <class 'str'>
DEBUG:decoded results='{"dps":{"20":false,"21":"white","22":678,"23":0,"24":"003c03e802d9","25":"000e0d0000000000000000c80000","26":0,"34":false}}'
Smart Lâmpada WiFi   Product ID = keytg5kq8gvkv9dh  [Valid Broadcast]:
    Address = 192.168.1.203   Device ID = eb3dcc68131b35ae344alc (len:22)  Local Key = d9bb19e75b0aa051  Version = 3.3  Type = default, MAC = d8:1f:12:c9:54:c4
    Status: {'20': False, '21': 'white', '22': 678, '23': 0, '24': '003c03e802d9', '25': '000e0d0000000000000000c80000', '26': 0, '34': False}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.204', 'gwId': 'ebd1b02d382049733dnq0u', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keytg5kq8gvkv9dh', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"ebd1b02d382049733dnq0u","devId":"ebd1b02d382049733dnq0u","uid":"ebd1b02d382049733dnq0u","t":"1673812673"}'
DEBUG:payload encrypted=b'000055aa000000010000000a00000088d5459e27005f4b841c784ed7c61a2ee10ea7ff9a6141d3a94ec36b1b05193db736b00f5fe8b0a0a53e29a63f6757553a1fce67a2f3e3efd7aec7cc38e69492bf2cfc37f38d01ab1c2beb5040cb9ae1fb0ea7ff9a6141d3a94ec36b1b05193db775f2aee63417290d7ec385f378f10418ae136db03ed32bc559c1eb409e35e390386a9bce0000aa55'
DEBUG:PollDevice: raw unpacked message = TuyaMessage(seqno=1, cmd=10, retcode=0, payload=b'G\xa7\xbeHrB\xfc\xbd\x8e\x08\x96S\xfc\x1c\xb6)\x9a\x83\xa0\x1b\xe1L\x1b\xc3B\xe9\xfa\xba\x96\xa2\xac"5\xa2~k\xfa\x82\xda\xaf\x19\xe4p=\xc6\xec\xa8\x85\xcf\xed\xc1\xff\xb5w\xa3\xbb\xe5\x03\x81dE\xaa#\x16t\x9c\xf6\xcakq\x8d2v}3\x9a\x88\xa1N\xf9b\xdb\x84\xd6\x83\x17Yr\xf7{\x179%\xb9m\xb6b\xc3\xd3\x8eB\xc4\x1b/m~\x1c:\xa3\xb8\x8b\xadnNq\x03\xd6\xf9\xf4\xcc\xacVU\xc7\x047\xc6&', crc=2518061103, crc_good=True, prefix=21930, iv=None)
DEBUG:decode payload=b'G\xa7\xbeHrB\xfc\xbd\x8e\x08\x96S\xfc\x1c\xb6)\x9a\x83\xa0\x1b\xe1L\x1b\xc3B\xe9\xfa\xba\x96\xa2\xac"5\xa2~k\xfa\x82\xda\xaf\x19\xe4p=\xc6\xec\xa8\x85\xcf\xed\xc1\xff\xb5w\xa3\xbb\xe5\x03\x81dE\xaa#\x16t\x9c\xf6\xcakq\x8d2v}3\x9a\x88\xa1N\xf9b\xdb\x84\xd6\x83\x17Yr\xf7{\x179%\xb9m\xb6b\xc3\xd3\x8eB\xc4\x1b/m~\x1c:\xa3\xb8\x8b\xadnNq\x03\xd6\xf9\xf4\xcc\xacVU\xc7\x047\xc6&'
DEBUG:decrypting=b'G\xa7\xbeHrB\xfc\xbd\x8e\x08\x96S\xfc\x1c\xb6)\x9a\x83\xa0\x1b\xe1L\x1b\xc3B\xe9\xfa\xba\x96\xa2\xac"5\xa2~k\xfa\x82\xda\xaf\x19\xe4p=\xc6\xec\xa8\x85\xcf\xed\xc1\xff\xb5w\xa3\xbb\xe5\x03\x81dE\xaa#\x16t\x9c\xf6\xcakq\x8d2v}3\x9a\x88\xa1N\xf9b\xdb\x84\xd6\x83\x17Yr\xf7{\x179%\xb9m\xb6b\xc3\xd3\x8eB\xc4\x1b/m~\x1c:\xa3\xb8\x8b\xadnNq\x03\xd6\xf9\xf4\xcc\xacVU\xc7\x047\xc6&'
DEBUG:decrypted 3.x payload='{"dps":{"20":false,"21":"white","22":18,"23":0,"24":"0159023b0006","25":"010e0d0000000000000003e801f4","26":0,"34":false}}'
DEBUG:payload type = <class 'str'>
DEBUG:decoded results='{"dps":{"20":false,"21":"white","22":18,"23":0,"24":"0159023b0006","25":"010e0d0000000000000003e801f4","26":0,"34":false}}'
Smart Lâmpada WiFi 2   Product ID = keytg5kq8gvkv9dh  [Valid Broadcast]:
    Address = 192.168.1.204   Device ID = ebd1b02d382049733dnq0u (len:22)  Local Key = c383f271346743c0  Version = 3.3  Type = default, MAC = d8:1f:12:c9:54:66
    Status: {'20': False, '21': 'white', '22': 18, '23': 0, '24': '0159023b0006', '25': '010e0d0000000000000003e801f4', '26': 0, '34': False}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.205', 'gwId': 'eb68e355da1be4ae69ok5o', 'uuid': '8b05ecd80b3d2553', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
DEBUG:building command 10 payload=b'{"gwId":"eb68e355da1be4ae69ok5o","devId":"eb68e355da1be4ae69ok5o","uid":"eb68e355da1be4ae69ok5o","t":"1673812674"}'
DEBUG:final payload: b'{"gwId":"eb68e355da1be4ae69ok5o","devId":"eb68e355da1be4ae69ok5o","uid":"eb68e355da1be4ae69ok5o","t":"1673812674"}'
DEBUG:payload encrypted=b'00006699000000000001000000100000008e303132333435363738396162b10ee238fc0804d9bd022d3c390177abf7ad1b69c6f3a587b2160bf06b9c0e4218307660aa6fe8d35f60e015f6c492115d9b0f2cc5b182381300b3a1486208a91136b29c547881e5580989971ddeb6497d6f2fd4b9787d021457829a1cd78f64e69f26a78dd8d56575da7aa2e8ecbd9a5eea51f9e25a035cc77c500db03b30053d7600009966'
DEBUG:Received valid UDP packet: {'ip': '192.168.1.206', 'gwId': 'eb099f68fc98defbd6vqcs', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keydnqmh87c8ajv4', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"eb099f68fc98defbd6vqcs","devId":"eb099f68fc98defbd6vqcs","uid":"eb099f68fc98defbd6vqcs","t":"1673812674"}'
DEBUG:payload encrypted=b'000055aa000000010000000a00000088ffebc3b29bc1ab9c8c81488fc89d9b8bdb74addecadbeaf134758fc0fb1c0e3012940b0e76f0a5fd2dcb5fc712e79be0f85dcbca9041c8b72362f0375bebca1ef46375e9d48894e4bb315a0c2f7aaf4ddb74addecadbeaf134758fc0fb1c0e303cf0c1a3a79efa12f661d9f2e6f2089e12f968231e9111ff723beed482e9f48cc687e3f00000aa55'
DEBUG:PollDevice: raw unpacked message = TuyaMessage(seqno=1, cmd=10, retcode=0, payload=b'\xb6\xcdp\x9d\x8e}\x0b\xcc\xaaE\x99\xe8\x14!]\x9b\x93\xfa.X%\x99H\xa9\x95\xe2\x07\xa35\x7f\xd6\xd6R\xf7\xd7L\xd0\xb0|\xa7GgSAD+\xf1\xdd\xa0l\xaa\xd5U{\x90\xc3/\x9b\xf5\x9e\x9d\xc4cd\x00\xd5\xad,Lz\xd8\xe8\xedU\x98k\xad)\xe8\xc1T\xf8\x08\xa4\xfc\x00\xe5\xd5\x80\xa8\xf4\xbd\x95\x95\xf5\xd6|\x93=r~\xf14z \x95\x11\xf5X\xd8\xb2d*j\xe6\x87\xabi5\xa2\xa0\x04\xd7\x84\x16Hr7', crc=2004297946, crc_good=True, prefix=21930, iv=None)
DEBUG:decode payload=b'\xb6\xcdp\x9d\x8e}\x0b\xcc\xaaE\x99\xe8\x14!]\x9b\x93\xfa.X%\x99H\xa9\x95\xe2\x07\xa35\x7f\xd6\xd6R\xf7\xd7L\xd0\xb0|\xa7GgSAD+\xf1\xdd\xa0l\xaa\xd5U{\x90\xc3/\x9b\xf5\x9e\x9d\xc4cd\x00\xd5\xad,Lz\xd8\xe8\xedU\x98k\xad)\xe8\xc1T\xf8\x08\xa4\xfc\x00\xe5\xd5\x80\xa8\xf4\xbd\x95\x95\xf5\xd6|\x93=r~\xf14z \x95\x11\xf5X\xd8\xb2d*j\xe6\x87\xabi5\xa2\xa0\x04\xd7\x84\x16Hr7'
DEBUG:decrypting=b'\xb6\xcdp\x9d\x8e}\x0b\xcc\xaaE\x99\xe8\x14!]\x9b\x93\xfa.X%\x99H\xa9\x95\xe2\x07\xa35\x7f\xd6\xd6R\xf7\xd7L\xd0\xb0|\xa7GgSAD+\xf1\xdd\xa0l\xaa\xd5U{\x90\xc3/\x9b\xf5\x9e\x9d\xc4cd\x00\xd5\xad,Lz\xd8\xe8\xedU\x98k\xad)\xe8\xc1T\xf8\x08\xa4\xfc\x00\xe5\xd5\x80\xa8\xf4\xbd\x95\x95\xf5\xd6|\x93=r~\xf14z \x95\x11\xf5X\xd8\xb2d*j\xe6\x87\xabi5\xa2\xa0\x04\xd7\x84\x16Hr7'
DEBUG:decrypted 3.x payload='{"dps":{"1":false,"9":0,"17":43,"18":0,"19":0,"20":1271,"21":1,"22":625,"23":31468,"24":18126,"25":1148,"26":0}}'
DEBUG:payload type = <class 'str'>
DEBUG:decoded results='{"dps":{"1":false,"9":0,"17":43,"18":0,"19":0,"20":1271,"21":1,"22":625,"23":31468,"24":18126,"25":1148,"26":0}}'
Smart Plug WiFi   Product ID = keydnqmh87c8ajv4  [Valid Broadcast]:
    Address = 192.168.1.206   Device ID = eb099f68fc98defbd6vqcs (len:22)  Local Key = dfd4cb0ca6a36d8a  Version = 3.3  Type = default, MAC = d8:1f:12:d2:57:71
    Status: {'1': False, '9': 0, '17': 43, '18': 0, '19': 0, '20': 1271, '21': 1, '22': 625, '23': 31468, '24': 18126, '25': 1148, '26': 0}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.201', 'gwId': 'eb06b9ad96cc645217ruup', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keym9qkuywghyrvs', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.200', 'gwId': 'eb629cf13d51f2d0d5gv7t', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': '5xierbs16mkdnkpk', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.207', 'gwId': 'eb597c0e524d178a80caat', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keydnqmh87c8ajv4', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.203', 'gwId': 'eb3dcc68131b35ae344alc', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keytg5kq8gvkv9dh', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"eb68e355da1be4ae69ok5o","devId":"eb68e355da1be4ae69ok5o","uid":"eb68e355da1be4ae69ok5o","t":"1673812678"}'
DEBUG:final payload: b'{"gwId":"eb68e355da1be4ae69ok5o","devId":"eb68e355da1be4ae69ok5o","uid":"eb68e355da1be4ae69ok5o","t":"1673812678"}'
DEBUG:payload encrypted=b'00006699000000000001000000100000008e303132333435363738396162b10ee238fc0804d9bd022d3c390177abf7ad1b69c6f3a587b2160bf06b9c0e4218307660aa6fe8d35f60e015f6c492115d9b0f2cc5b182381300b3a1486208a91136b29c547881e5580989971ddeb6497d6f2fd4b9787d021457829a1cd78f64e69f26a78dd8d56575da7aa2e8ecbd965eea6d2c40018c5512a3a551087af867486c00009966'
DEBUG:Received valid UDP packet: {'ip': '192.168.1.204', 'gwId': 'ebd1b02d382049733dnq0u', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keytg5kq8gvkv9dh', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.205', 'gwId': 'eb68e355da1be4ae69ok5o', 'uuid': '8b05ecd80b3d2553', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.206', 'gwId': 'eb099f68fc98defbd6vqcs', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keydnqmh87c8ajv4', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.201', 'gwId': 'eb06b9ad96cc645217ruup', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keym9qkuywghyrvs', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.200', 'gwId': 'eb629cf13d51f2d0d5gv7t', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': '5xierbs16mkdnkpk', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"eb68e355da1be4ae69ok5o","devId":"eb68e355da1be4ae69ok5o","uid":"eb68e355da1be4ae69ok5o","t":"1673812681"}'
DEBUG:final payload: b'{"gwId":"eb68e355da1be4ae69ok5o","devId":"eb68e355da1be4ae69ok5o","uid":"eb68e355da1be4ae69ok5o","t":"1673812681"}'
DEBUG:payload encrypted=b'00006699000000000001000000100000008e303132333435363738396162b10ee238fc0804d9bd022d3c390177abf7ad1b69c6f3a587b2160bf06b9c0e4218307660aa6fe8d35f60e015f6c492115d9b0f2cc5b182381300b3a1486208a91136b29c547881e5580989971ddeb6497d6f2fd4b9787d021457829a1cd78f64e69f26a78dd8d56575da7aa2e8ecb29f5eea5f6c968decbaf0ec5c6293b1dcc4c61200009966'
DEBUG:Received valid UDP packet: {'ip': '192.168.1.207', 'gwId': 'eb597c0e524d178a80caat', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keydnqmh87c8ajv4', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.203', 'gwId': 'eb3dcc68131b35ae344alc', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keytg5kq8gvkv9dh', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.204', 'gwId': 'ebd1b02d382049733dnq0u', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keytg5kq8gvkv9dh', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.205', 'gwId': 'eb68e355da1be4ae69ok5o', 'uuid': '8b05ecd80b3d2553', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.206', 'gwId': 'eb099f68fc98defbd6vqcs', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keydnqmh87c8ajv4', 'version': '3.3'}
EWS 410   Product ID = key8u54q9dtru5jw  [Valid Broadcast]:
    Address = 192.168.1.205   Device ID = eb68e355da1be4ae69ok5o (len:22)  Local Key = 6434389541e96704  Version = 3.5  Type = default, MAC = 38:1f:8d:4f:66:f6
    Polling 192.168.1.205 Failed: No response
DEBUG:Received valid UDP packet: {'ip': '192.168.1.201', 'gwId': 'eb06b9ad96cc645217ruup', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keym9qkuywghyrvs', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.200', 'gwId': 'eb629cf13d51f2d0d5gv7t', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': '5xierbs16mkdnkpk', 'version': '3.3'}
DEBUG:Received valid UDP packet: {'ip': '192.168.1.207', 'gwId': 'eb597c0e524d178a80caat', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'keydnqmh87c8ajv4', 'version': '3.3'}
Scan completed in 18.0054 seconds

Scan Complete!  Found 7 devices.
Broadcasted: 7
Versions: 3.3: 6, 3.5: 1

>> Saving device snapshot data to snapshot.json

DEBUG:Scan complete with 7 devices found
Xilef11 commented 1 year ago

I still get "Polling failed: no response" on the protocol 3.5 device (192.168.2.46) when scanning with the latest commit. Here's the debug run:

>>> import tinytuya
>>> tinytuya.set_debug(True)
DEBUG:TinyTuya [1.10.0]

>>> tinytuya.scan()
DEBUG:loaded=devices.json [3 devices]

TinyTuya (Tuya device scanner) [1.10.0]

[Loaded devices.json - 3 devices]

Scanning on UDP ports 6666 and 6667 and 7000 for devices for 18 seconds...

DEBUG:Listening for Tuya devices on UDP 6666 and 6667 and 7000
DEBUG:Received valid UDP packet: {'ip': '192.168.2.46', 'gwId': 'ebf310edb88d15f0edyr5i', 'uuid': '60b308e46e1b5871', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
DEBUG:building command 10 payload=b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673811660"}'
DEBUG:final payload: b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673811660"}'
DEBUG:payload encrypted=b'00006699000000000001000000100000008e3031323334353637383961624bbfc4bee23dc36abc9ac192e73685d396eb71c393c815c4971fe121a5e68508404a17c76598d7455ca2f8ee9c837c48b766d518885df7e3b8e593c482a0a403ff8446cb7e1a95bd51255b2fc615ad084fbd3fb53c3cc0613b0bd3aeb4637640ab8e831b1a50791f5107612922c3cd7d91d381495f73c054b75d6bd846e139843ea600009966'
DEBUG:Received valid UDP packet: {'ip': '192.168.2.51', 'gwId': 'eb834c7e4b36a9bab54at3', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"eb834c7e4b36a9bab54at3","devId":"eb834c7e4b36a9bab54at3","uid":"eb834c7e4b36a9bab54at3","t":"1673811661"}'
DEBUG:payload encrypted=b'000055aa000000010000000a000000881a5d57874bd85ccacd3db8dccd99cf5f3c8382aa1ff3146edf3256d327e8ca6fcf79a5374702faa2d2263882759c5760d190c2645d100e904c9689a20f03a905b2d6db8c2370636de2e977ec2cff05463c8382aa1ff3146edf3256d327e8ca6f03dce4e8f6a1e7ee22b09efcdbf5d7aff3346495a6fc5e64e6a586faffbe35bd5e1202ea0000aa55'
DEBUG:PollDevice: raw unpacked message = TuyaMessage(seqno=1, cmd=10, retcode=0, payload=b'\x8dV\xae\xfe`?\xd90\xa0\x1f\xde~\x01\xe3\x12\xe85\xd1\x0c\xf4\x9bHN\x9f\xca\\\xa3\xe7*abc^\xebK\xdd$\x82\xe4 \x1e\xfa\xe8!\x0ccG\xa6\xa8!\x87\x17\xb0\x93#qD>5x\x94\x13\n\xde\xe9O\xbd=\xf6#$dr\'\xd6)\xdc`\x95\xb8\xee\xd1Iit] \xefw\xa5\xeb^\x8b\xb0|1\x1c)\xc5\xa2O\xd32\xdf\x03\xaa\x08\x9c\x08\xc5W\xd6\xff\xde\x0e\xb0\x9f\x96\x7f"w\x92\xfbA}S\xd0\xff', crc=2177728455, crc_good=True, prefix=21930, iv=None)
DEBUG:decode payload=b'\x8dV\xae\xfe`?\xd90\xa0\x1f\xde~\x01\xe3\x12\xe85\xd1\x0c\xf4\x9bHN\x9f\xca\\\xa3\xe7*abc^\xebK\xdd$\x82\xe4 \x1e\xfa\xe8!\x0ccG\xa6\xa8!\x87\x17\xb0\x93#qD>5x\x94\x13\n\xde\xe9O\xbd=\xf6#$dr\'\xd6)\xdc`\x95\xb8\xee\xd1Iit] \xefw\xa5\xeb^\x8b\xb0|1\x1c)\xc5\xa2O\xd32\xdf\x03\xaa\x08\x9c\x08\xc5W\xd6\xff\xde\x0e\xb0\x9f\x96\x7f"w\x92\xfbA}S\xd0\xff'
DEBUG:decrypting=b'\x8dV\xae\xfe`?\xd90\xa0\x1f\xde~\x01\xe3\x12\xe85\xd1\x0c\xf4\x9bHN\x9f\xca\\\xa3\xe7*abc^\xebK\xdd$\x82\xe4 \x1e\xfa\xe8!\x0ccG\xa6\xa8!\x87\x17\xb0\x93#qD>5x\x94\x13\n\xde\xe9O\xbd=\xf6#$dr\'\xd6)\xdc`\x95\xb8\xee\xd1Iit] \xefw\xa5\xeb^\x8b\xb0|1\x1c)\xc5\xa2O\xd32\xdf\x03\xaa\x08\x9c\x08\xc5W\xd6\xff\xde\x0e\xb0\x9f\x96\x7f"w\x92\xfbA}S\xd0\xff'
DEBUG:decrypted 3.x payload='{"dps":{"20":true,"21":"white","22":901,"23":733,"24":"000003e803e8","25":"000e0d0000000000000000c80000","26":0,"34":false}}'
DEBUG:payload type = <class 'str'>
DEBUG:decoded results='{"dps":{"20":true,"21":"white","22":901,"23":733,"24":"000003e803e8","25":"000e0d0000000000000000c80000","26":0,"34":false}}'
36819 4   Product ID = key8u54q9dtru5jw  [Valid Broadcast]:
    Address = 192.168.2.51   Device ID = eb834c7e4b36a9bab54at3 (len:22)  Local Key = 7db01ec2416277f3  Version = 3.3  Type = default, MAC = 38:1f:8d:42:0e:14
    Status: {'20': True, '21': 'white', '22': 901, '23': 733, '24': '000003e803e8', '25': '000e0d0000000000000000c80000', '26': 0, '34': False}
DEBUG:building command 10 payload=b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673811664"}'
DEBUG:final payload: b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673811664"}'
DEBUG:payload encrypted=b'00006699000000000001000000100000008e3031323334353637383961624bbfc4bee23dc36abc9ac192e73685d396eb71c393c815c4971fe121a5e68508404a17c76598d7455ca2f8ee9c837c48b766d518885df7e3b8e593c482a0a403ff8446cb7e1a95bd51255b2fc615ad084fbd3fb53c3cc0613b0bd3aeb4637640ab8e831b1a50791f5107612922c3cd7991d3d393049671fe775c3045d6eed54a6d8900009966'
DEBUG:Received valid UDP packet: {'ip': '192.168.2.46', 'gwId': 'ebf310edb88d15f0edyr5i', 'uuid': '60b308e46e1b5871', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
DEBUG:Received valid UDP packet: {'ip': '192.168.2.51', 'gwId': 'eb834c7e4b36a9bab54at3', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.3'}
DEBUG:building command 10 payload=b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673811667"}'
DEBUG:final payload: b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673811667"}'
DEBUG:payload encrypted=b'00006699000000000001000000100000008e3031323334353637383961624bbfc4bee23dc36abc9ac192e73685d396eb71c393c815c4971fe121a5e68508404a17c76598d7455ca2f8ee9c837c48b766d518885df7e3b8e593c482a0a403ff8446cb7e1a95bd51255b2fc615ad084fbd3fb53c3cc0613b0bd3aeb4637640ab8e831b1a50791f5107612922c3cd7a91d39ec8bf9dc541a75ccb6c7aead81ed0d500009966'
DEBUG:Received valid UDP packet: {'ip': '192.168.2.46', 'gwId': 'ebf310edb88d15f0edyr5i', 'uuid': '60b308e46e1b5871', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
36819   Product ID = key8u54q9dtru5jw  [Valid Broadcast]:
    Address = 192.168.2.46   Device ID = ebf310edb88d15f0edyr5i (len:22)  Local Key = 71ad785601d640cc  Version = 3.5  Type = default, MAC = 38:1f:8d:36:d2:03
    Polling 192.168.2.46 Failed: No response
DEBUG:Received valid UDP packet: {'ip': '192.168.2.51', 'gwId': 'eb834c7e4b36a9bab54at3', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.3'}
Scan completed in 18.0338 seconds

Scan Complete!  Found 2 devices.
Broadcasted: 2
Versions: 3.3: 1, 3.5: 1

>> Saving device snapshot data to snapshot.json

DEBUG:Scan complete with 2 devices found
jasonacox commented 1 year ago

Thank you @Xilef11 and @Oglaf ! Sadly, looks like we are not there yet or these 3.5 devices don't respond to status requests.

I'll let @uzlonewolf chime in on next steps if there is anything. In the meantime, if you are willing, see if you get any data from the devices using a monitoring loop (replacing DEVICEID etc., with your device details). Run this and then change things on the device (power on/off etc) to see if you get any updates:

import tinytuya

# start without debug to make it easier to see any responses 
# tinytuya.set_debug(True)

d = tinytuya.OutletDevice('DEVICEID', 'DEVICEIP', 'DEVICEKEY')
d.set_version(3.5)
d.set_socketPersistent(True)

print(" > Send Request for Status < ")
payload = d.generate_payload(tinytuya.DP_QUERY)
d.send(payload)

print(" > Begin Monitor Loop <")
while(True):
    # See if any data is available
    data = d.receive()
    print('Received Payload: %r' % data)

    # Send keyalive heartbeat
    print(" > Send Heartbeat Ping < ")
    payload = d.generate_payload(tinytuya.HEART_BEAT)
    d.send(payload)

    # Option - Some plugs require an UPDATEDPS command to update their power data points

    # print(" > Send Request for Status < ")
    # payload = d.generate_payload(tinytuya.DP_QUERY)
    # d.send(payload)
Xilef11 commented 1 year ago

I get an "Unexpected Payload from device". Turning on debug mode outputs the following:

DEBUG:TinyTuya [1.10.0]

 > Send Request for Status <
DEBUG:building command 10 payload=b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673820487"}'
DEBUG:sending payload quick
DEBUG:final payload: b'0123456789abcdef'
DEBUG:payload encrypted=b'00006699000000000001000000030000002c30313233343536373839616200ac91fa9f6cd767a6c6c296b763d0d00580760429af017e88da70bf31e5093300009966'
DEBUG:received data=b'0000669900000000f86e0000000400000050313ae6fdf1c511adc9234adf091ed711f71642eef808fbd24375249a402e63a98ded882f8cb310e523f6a2bc1ee81edb42f62d8147e3c0a0d871c77e836290949515133dc63504a833f57439a98bf38d00009966'
DEBUG:decrypted session key negotiation step 2 payload=b'\x00\x00\x00\x00703a47c9b5df4183\xe0\x8d\x81/`\xeck\xd7v\xb56\xe5\xaf\xfa{\xf3\x81\x1aZ\xa3\\\x18\xe9\xd1\n_\x08\xd3\x89\xd3/!'
DEBUG:payload type = <class 'bytes'> len = 52
DEBUG:session key negotiation step 2 failed HMAC check! wanted=b'e08d812f60ec6bd776b536e5affa7bf3811a5aa35c18e9d10a5f08d389d32f21' but got=b'34313833e08d812f60ec6bd776b536e5affa7bf3811a5aa35c18e9d10a5f08d3'
DEBUG:session local nonce: b'0123456789abcdef' remote nonce: b'\x00\x00\x00\x00703a47c9b5df'
DEBUG:sending payload quick
DEBUG:final payload: b'\x8a\xf6\x7f2~7\x80K\xb8\x94\x92&\xeb\xa78jy\xb2\xb3[\x1d{q\x92\xbc\xce\x061w9\x10t'
DEBUG:payload encrypted=b'00006699000000000002000000050000003c303132333435363738396162ba6bdcfbd56e611b266b31d23fa08ddc8b3bfaa0ea8251301bb48369a0eafc5edcc152a1c488e05e4db7c405c1e2386c00009966'
DEBUG:Session nonce XOR'd: b'0123\x03\x05\x05V\x0c\x0e\x02[\x01Q\x01\x00'
DEBUG:Session key negotiate success! session key: b'9/\xe5"\xc3#t\xd9\xc01\x9a\xb0 \x11A\xfc'
DEBUG:sending payload
DEBUG:final payload: b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673820487"}'
DEBUG:payload encrypted=b'00006699000000000003000000100000008e3031323334353637383961625d758a4c45cfefaca7aca640a233d923d5200b8d973ee5f1c4f0b99b5d64b24a8cde66896e29e5957f0a9e4892497f692eb7b9d6027dace009b9741cc3659920962623fadb44b4b5c2fdb225a31ec8123849a6457d81bb8625b2cfad71f35744eeccf698ab3cca65a492f074e99049fc67f60e0f1bcda1306dd800731afec57bb18200009966'
 > Begin Monitor Loop <
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 0/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 1/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 2/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 3/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 4/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 5/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:ERROR Unexpected Payload from Device - 904 - payload: null
Received Payload: {'Error': 'Unexpected Payload from Device', 'Err': '904', 'Payload': None}
 > Send Heartbeat Ping <
DEBUG:building command 9 payload=b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i"}'
DEBUG:sending payload quick
DEBUG:final payload: b'0123456789abcdef'
DEBUG:payload encrypted=b'00006699000000000004000000030000002c30313233343536373839616200ac91fa9f6cd767a6c6c296b763d0d0558c61f9ee4ba982a2604a946fc20ba100009966'
DEBUG:received data=b'0000669900000000935c00000004000000508dea5a0fe11da602f7e2b5b3260b2412c5a59b984cb2d7142b3d24ce2d32e68fe42d341d4afd39f2cf86086d5f1ecc92c444f76099f97414365dd6cd04f3d29fe5b5d81397cac4a19d7db3175ad699b400009966'
DEBUG:decrypted session key negotiation step 2 payload=b'\x00\x00\x00\x00f3f17880123dcc8b\xe0\x8d\x81/`\xeck\xd7v\xb56\xe5\xaf\xfa{\xf3\x81\x1aZ\xa3\\\x18\xe9\xd1\n_\x08\xd3\x89\xd3/!'
DEBUG:payload type = <class 'bytes'> len = 52
DEBUG:session key negotiation step 2 failed HMAC check! wanted=b'e08d812f60ec6bd776b536e5affa7bf3811a5aa35c18e9d10a5f08d389d32f21' but got=b'63633862e08d812f60ec6bd776b536e5affa7bf3811a5aa35c18e9d10a5f08d3'
DEBUG:session local nonce: b'0123456789abcdef' remote nonce: b'\x00\x00\x00\x00f3f17880123d'
DEBUG:sending payload quick
DEBUG:final payload: b"\x0e<\x98ja\xad\xaa5d\x00\x86\xfaN|'\xf8\xb9\x82\xda\xbd\x8c\xa9\xf7G\xcaj`8\xcf\xd3GP"
DEBUG:payload encrypted=b'00006699000000000005000000050000003c3031323334353637383961623ea13ba3caf44b65faff250e9a7b924e4b0b93467b50d7e56d10e5601800ab7a769c53a3618afc9a665dfbaf271c9fd200009966'
DEBUG:Session nonce XOR'd: b'0123R\x06P\x06\x0f\x01YRRVV\x02'
DEBUG:Session key negotiate success! session key: b'\x16:\x16!\xf1\x90\xad\xaft\x8b\xb6vHYA\xa8'
DEBUG:sending payload
DEBUG:final payload: b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i"}'
DEBUG:payload encrypted=b'00006699000000000006000000090000005e303132333435363738396162f07a65effa1ae0c70a4f9482b5373e0bda55063d8f3d505945cf9176847e540e5ea4f3fd5a1455aa0bcc5aa9ac9006d552929fa609b378ac421d9286f6d669f9a34fba69bc75af1c703c8691b8d2e26a227500009966'
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 0/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 1/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 2/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 3/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 4/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:_recv_all(): no data? b''
DEBUG:_recv_all(): no data? b''
DEBUG:Error decoding received data - read retry 5/5
Traceback (most recent call last):
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 952, in _send_receive
    rmsg = self._receive()
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 842, in _receive
    data = self._recv_all( min_len )
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\core.py", line 823, in _recv_all
    raise DecodeError('No data received - connection closed?')
tinytuya.core.DecodeError: No data received - connection closed?
DEBUG:ERROR Unexpected Payload from Device - 904 - payload: null
Received Payload: {'Error': 'Unexpected Payload from Device', 'Err': '904', 'Payload': None}
 > Send Heartbeat Ping <
DEBUG:building command 9 payload=b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i"}'
DEBUG:sending payload quick
DEBUG:final payload: b'0123456789abcdef'
DEBUG:payload encrypted=b'00006699000000000007000000030000002c30313233343536373839616200ac91fa9f6cd767a6c6c296b763d0d065886cad5317ce294409a372a5df0a2f00009966'
DEBUG:received data=b'00006699000000000a91000000040000005034c14109ec45874ab93ff8f67d7481cac6b395b8a7cf6f4079eb8f8ecb32481619738fd29886ee5ebe3696dfa6ac9ff4829eecee9fe173e4a5e0b3c843cc78930d1be2bcca28687ee4b2cb6770a2a58e00009966'
DEBUG:decrypted session key negotiation step 2 payload=b'\x00\x00\x00\x004a150aa181de62dd\xe0\x8d\x81/`\xeck\xd7v\xb56\xe5\xaf\xfa{\xf3\x81\x1aZ\xa3\\\x18\xe9\xd1\n_\x08\xd3\x89\xd3/!'
DEBUG:payload type = <class 'bytes'> len = 52
DEBUG:session key negotiation step 2 failed HMAC check! wanted=b'e08d812f60ec6bd776b536e5affa7bf3811a5aa35c18e9d10a5f08d389d32f21' but got=b'36326464e08d812f60ec6bd776b536e5affa7bf3811a5aa35c18e9d10a5f08d3'
DEBUG:session local nonce: b'0123456789abcdef' remote nonce: b'\x00\x00\x00\x004a150aa181de'
DEBUG:sending payload quick
DEBUG:final payload: b'\x89\xef\x8c\xda\xa8!f\xbd\x0fF\xea\xae\xb9\xc0\xdcM\r~X|\xf2>R\xc6\x18\\<w\x8a\x98R\xff'
DEBUG:payload encrypted=b'00006699000000000008000000050000003c303132333435363738396162b9722f13037887ed91b9495a6dc769fbfff7118705c77264bf26b92f5d4bbed54b20aa5764ab0bb6974bbef9c34184af00009966'
DEBUG:Session nonce XOR'd: b'0123\x00T\x07\x02\x08X\x00S[U\x01\x03'
DEBUG:Session key negotiate success! session key: b'ME\xb3\xf9\xf2\x86\xa3\x8f\x9f\xf6\x0e"\x1a\x8f\xea\xe8'
DEBUG:sending payload
DEBUG:final payload: b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i"}'
DEBUG:payload encrypted=b'00006699000000000009000000090000005e303132333435363738396162156a4cfe5d20613cae5832bee0087d2a6f2951348f0ed19197d458101fa483a33a019db2d45e0a5c3e4451401c8c6fed6dcaed7e31bf6fae721ddc502d942a5257709bfe85625a07b5265145560210f1498500009966'
uzlonewolf commented 1 year ago

While the ZB gateway I have does not respond to v3.5 requests, it can sent them to v3.5 devices to support scene linkage. So, I wrote a script that pretends to be a v3.5 device to capture some traffic. Turns out my final session key generation is wrong; I'm trying to figure it out now.

uzlonewolf commented 1 year ago

Ok, that took way too long to figure out. Didn't help that I got distracted with the lan key exchange protocol on port 6682... Anyway, please git checkout https://github.com/uzlonewolf/tinytuya/tree/pv35 then git pull and try it again. You may need to reboot the device since they tend to get mad on too many connection/handshake failures.

jasonacox commented 1 year ago

Thanks @uzlonewolf ! You're amazing! The related PR has also been merged into the main repo (https://github.com/jasonacox/tinytuya.git).

@Xilef11 and @Oglaf - Let us know your test results. 🤞 🙏

Xilef11 commented 1 year ago

well, that's interesting. python -m tinytuya scan still returns a "Polling failed: No response", but the monitor loop does get a response, but only on the initial query and once after settings are changed in the app. Somehow these "setting change" responses have a "protocol: 4" in them.

 > Send Request for Status <
 > Begin Monitor Loop <
Received Payload: {'dps': {'20': True, '21': 'colour', '22': 291, '23': 400, '24': '000003e803e8', '25': '000e0d0000000000000000c80000', '26': 0, '34': False}}
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: {'protocol': 4, 't': 1673883553, 'data': {'dps': {'24': '007803e803e8'}}, 'dps': {'24': '007803e803e8'}}
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
Received Payload: {'protocol': 4, 't': 1673883561, 'data': {'dps': {'24': '002103e803e8'}}, 'dps': {'24': '002103e803e8'}}
 > Send Heartbeat Ping <
Received Payload: None
 > Send Heartbeat Ping <
jasonacox commented 1 year ago

Progress! Thanks @Xilef11 !

When you ran the scan, did you have a current devices.json file in the same directory with the key you are using for the monitor script? I any case, it seems that the status call is working based on the monitor. Would you mind running a few checks for us?

d = tinytuya.OutletDevice('DEVICEID', 'DEVICEIP', 'DEVICEKEY') d.set_version(3.5) d.set_socketPersistent(True) print(d.status())


* Run the scan again with debug mode:
```python
import tinytuya

tinytuya.set_debug(True)
tinytuya.scan()
Xilef11 commented 1 year ago

Status check:

{'dps': {'20': True, '21': 'colour', '22': 291, '23': 400, '24': '002103e803e8', '25': '000e0d0000000000000000c80000', '26': 0, '34': False}}

debug scan (with a current devices.json and only the 3.5 device online)

DEBUG:loaded=devices.json [3 devices]

TinyTuya (Tuya device scanner) [1.10.0]

[Loaded devices.json - 3 devices]

Scanning on UDP ports 6666 and 6667 and 7000 for devices for 18 seconds...

DEBUG:Listening for Tuya devices on UDP 6666 and 6667 and 7000
DEBUG:Received valid UDP packet: {'ip': '192.168.2.46', 'gwId': 'ebf310edb88d15f0edyr5i', 'uuid': '60b308e46e1b5871', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
DEBUG:building command 10 payload=b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673888134"}'
DEBUG:final payload: b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673888134"}'
DEBUG:payload encrypted=b'00006699000000000001000000100000008e3031323334353637383961624bbfc4bee23dc36abc9ac192e73685d396eb71c393c815c4971fe121a5e68508404a17c76598d7455ca2f8ee9c837c48b766d518885df7e3b8e593c482a0a403ff8446cb7e1a95bd51255b2fc615ad084fbd3fb53c3cc0613b0bd3aeb4637640ab8e831b1a50791f510761202bc4c87991d3cc80126c42b24ebd4837a6c4659b7bbe00009966'
DEBUG:building command 10 payload=b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673888138"}'
DEBUG:final payload: b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673888138"}'
DEBUG:payload encrypted=b'00006699000000000001000000100000008e3031323334353637383961624bbfc4bee23dc36abc9ac192e73685d396eb71c393c815c4971fe121a5e68508404a17c76598d7455ca2f8ee9c837c48b766d518885df7e3b8e593c482a0a403ff8446cb7e1a95bd51255b2fc615ad084fbd3fb53c3cc0613b0bd3aeb4637640ab8e831b1a50791f510761202bc4c87591d33beefe42904d0ebea49116d450c98ecf00009966'
DEBUG:Received valid UDP packet: {'ip': '192.168.2.46', 'gwId': 'ebf310edb88d15f0edyr5i', 'uuid': '60b308e46e1b5871', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
DEBUG:building command 10 payload=b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673888142"}'
DEBUG:final payload: b'{"gwId":"ebf310edb88d15f0edyr5i","devId":"ebf310edb88d15f0edyr5i","uid":"ebf310edb88d15f0edyr5i","t":"1673888142"}'
DEBUG:payload encrypted=b'00006699000000000001000000100000008e3031323334353637383961624bbfc4bee23dc36abc9ac192e73685d396eb71c393c815c4971fe121a5e68508404a17c76598d7455ca2f8ee9c837c48b766d518885df7e3b8e593c482a0a403ff8446cb7e1a95bd51255b2fc615ad084fbd3fb53c3cc0613b0bd3aeb4637640ab8e831b1a50791f510761202bc4cf7f91d373d78a7e3eddef1c0a58f52de5dc721400009966'
DEBUG:Received valid UDP packet: {'ip': '192.168.2.46', 'gwId': 'ebf310edb88d15f0edyr5i', 'uuid': '60b308e46e1b5871', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
36819   Product ID = key8u54q9dtru5jw  [Valid Broadcast]:
    Address = 192.168.2.46   Device ID = ebf310edb88d15f0edyr5i (len:22)  Local Key = 71ad785601d640cc  Version = 3.5  Type = default, MAC = 38:1f:8d:36:d2:03
    Polling 192.168.2.46 Failed: No response
DEBUG:Received valid UDP packet: {'ip': '192.168.2.46', 'gwId': 'ebf310edb88d15f0edyr5i', 'uuid': '60b308e46e1b5871', 'active': 2, 'ablilty': 0, 'encrypt': True, 'productKey': 'key8u54q9dtru5jw', 'version': '3.5', 'token': True, 'wf_cfg': True, 'clientLink': 3}
Scan completed in 18.0406 seconds

Scan Complete!  Found 1 devices.
Broadcasted: 1
Versions: 3.5: 1

>> Saving device snapshot data to snapshot.json

DEBUG:Scan complete with 1 devices found
jasonacox commented 1 year ago

Thank you @Xilef11 ! Good news on the status() results! That means there is still a bug in scanner.py. Can you also try this?

python3 -m tinytuya scan
python3 -m tinytuya snapshot

I'm more interested in the snapshot output to see if it reads the 3.5 device there.

Xilef11 commented 1 year ago

scan:

TinyTuya (Tuya device scanner) [1.10.0]

[Loaded devices.json - 3 devices]

Scanning on UDP ports 6666 and 6667 and 7000 for devices for 18 seconds...

36819   Product ID = key8u54q9dtru5jw  [Valid Broadcast]:
    Address = 192.168.2.46   Device ID = ebf310edb88d15f0edyr5i (len:22)  Local Key = 0afcd6c2451d2f3e  Version = 3.5  Type = default, MAC = 38:1f:8d:36:d2:03
    Polling 192.168.2.46 Failed: No response
Scan completed in 18.0373 seconds

Scan Complete!  Found 1 devices.
Broadcasted: 1
Versions: 3.5: 1

>> Saving device snapshot data to snapshot.json

snapshot:

TinyTuya (Tuya device scanner) [1.10.0]

Loaded snapshot.json - 1 devices:

Name                      ID                       IP                 Key               Version

36819                     ebf310edb88d15f0edyr5i   192.168.2.46       0afcd6c2451d2f3e  3.5

Poll local devices? (Y/n):

Polling 1 local devices from last snapshot...
Traceback (most recent call last):
  File "d:\users\felix\appdata\local\miniconda3\lib\runpy.py", line 193, in _run_module_as_main
    "__main__", mod_spec)
  File "d:\users\felix\appdata\local\miniconda3\lib\runpy.py", line 85, in _run_code
    exec(code, run_globals)
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\__main__.py", line 86, in <module>
    scanner.snapshot(color=color)
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\scanner.py", line 1687, in snapshot
    result = devices(verbose=False, scantime=0, color=color, poll=True, byID=True, discover=False, snapshot=by_ip)
  File "D:\Users\Felix\Desktop\tuya\tinytuya\tinytuya\scanner.py", line 1295, in devices
    rd, _, _ = select.select( read_socks, [], [], 0 )
OSError: [WinError 10022] Un argument non valide a été fourni

"invalid argument" from Windows when polling from the snapshot.

uzlonewolf commented 1 year ago

@jasonacox Looks like there are 3 places in the scanner with == 3.4 that need to be changed to >= 3.4