Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Antela Smart Bulbs cause tuyapi and upstream apps to crash #676

Open
iainmc83 opened this issue Nov 15, 2024 · 18 comments
Open

Antela Smart Bulbs cause tuyapi and upstream apps to crash #676

iainmc83 opened this issue Nov 15, 2024 · 18 comments

Comments

@iainmc83
Copy link

I think I have the same issue as some of the commenters on #325.

I'm using https://flows.nodered.org/node/node-red-contrib-tuya-smart-device in v4.0.5 of node-red on a raspberry pi 4.
Since adding some Antela bulbs to the Tuya app, node red crashes with the below error...

15 Nov 10:09:41 - [red] Uncaught Exception:
15 Nov 10:09:41 - [error] TypeError: Cannot read properties of undefined (reading 'payload')
    at Socket.<anonymous> (/home/iain/.node-red/node_modules/tuyapi/index.js:985:30)
    at Socket.emit (node:events:517:28)
    at Socket.emit (node:domain:489:12)
    at UDP.onMessage [as onmessage] (node:dgram:942:8)

I think some minification might be happening, as I have traced the error to this line: https://github.com/codetheweb/tuyapi/blob/master/index.js#L1013
(which is 985 on my local version. not 1013.)

Payload is indeed undefined. If I hack a console.log(error) into the try/catch on line 1003 I get:

TypeError: Prefix does not match: 0000669900000000000000000013000000ef18e50e3166d903b212dcf474d350b9a60368c20de852a60f097eb08cd2cebfc4be6b061d7fc95d05354ad9b981024152cdce6119eb5df16718edc92aab320bf14af2c184d11c7d1ec1b54de7e21c34830a65e71af2332474f5c280bc4e7962288228df3bc8f71aba9c24739310477bee094becd986db3eb01a5cfc33b25150c8a2e3928443591e5a678aa04021bc8c3a89a2e2868a65c6c81bb28c24e41900f21dff928125dbf50c0a1a3e2ca21c87825d45e13c9911905dae6b039b3d147e228fd660d78829fa481ac5efba580b557653080d8fad6bd094499092f13c8296f3341d333141006fc4d77c611a12306400009966
    at MessageParser.parsePacket (/home/iain/.node-red/node_modules/tuyapi/lib/message-parser.js:113:13)
    at MessageParser.parseRecursive (/home/iain/.node-red/node_modules/tuyapi/lib/message-parser.js:238:25)
    at MessageParser.parse (/home/iain/.node-red/node_modules/tuyapi/lib/message-parser.js:259:17)
    at Socket.<anonymous> (/home/iain/.node-red/node_modules/tuyapi/index.js:976:26)
    at Socket.emit (node:events:517:28)
    at Socket.emit (node:domain:489:12)
    at UDP.onMessage [as onmessage] (node:dgram:942:8)

UPDATE:

Suspecting the node-red plugin was using an older version of the API, I have since checked out the latest version of this repo and tested it with my problem bulbs. I see the prefix error above has now been fixed, but I get a further error when I put the problem device details into the Asynchronous example in the readme. Ultimately resulting in the same undefined payload. It looks like this second error needs to be resolved before 'node-red-contrib-tuya-smart-device' updates their dependencies.

// $DEBUG=* node test.js

  TuyAPI Received UDP message. +1s
  TuyAPI RangeError [ERR_OUT_OF_RANGE]: The value of "offset" is out of range. It must be >= 0 and <= 257. Received 261
  TuyAPI     at boundsError (node:internal/buffer:88:9)
  TuyAPI     at Uint8Array.readInt32BE (node:internal/buffer:484:5)
  TuyAPI     at MessageParser.parsePacket (/Users/Iain/tuyatest/node_modules/tuyapi/lib/message-parser.js:216:36)
  TuyAPI     at MessageParser.parseRecursive (/Users/Iain/tuyatest/node_modules/tuyapi/lib/message-parser.js:280:25)
  TuyAPI     at MessageParser.parse (/Users/Iain/tuyatest/node_modules/tuyapi/lib/message-parser.js:301:17)
  TuyAPI     at Socket.<anonymous> (/Users/Iain/tuyatest/node_modules/tuyapi/index.js:1005:26)
  TuyAPI     at Socket.emit (node:events:519:28)
  TuyAPI     at UDP.onMessage [as onmessage] (node:dgram:943:8) +1ms
  TuyAPI UDP data: +1ms
  TuyAPI undefined +0ms
/Users/Iain/tuyatest/node_modules/tuyapi/index.js:1014
      const thisID = dataRes.payload.gwId;
                             ^

TypeError: Cannot read properties of undefined (reading 'payload')
    at Socket.<anonymous> (/Users/Iain/tuyatest/node_modules/tuyapi/index.js:1014:30)
    at Socket.emit (node:events:519:28)
    at UDP.onMessage [as onmessage] (node:dgram:943:8)

I have run out of talent at this point. https://github.com/codetheweb/tuyapi/blob/master/lib/message-parser.js#L216 😆

I'm happy to assist in debugging this. If I can't control these lamps using the Tuya API, I would at least like them to not crash the api and in turn, crash node-red. I need to have the bulbs in the Tuya app to control them. I have tried removing them from the linked App account in the Tuya dashboard, but they continue to appear in the list of devices and crash the API.

Thanks.

@ddpurdie
Copy link

I'm seeing the same issue using [email protected].
I have two light bulbs that report version 3.5 protocol. If these are not present, then I don't see any problems.
Version 7.7.0 does not appear to be finding devices ( device.find() ) that utilize the version 3.5 protocol.

@Apollon77
Copy link
Collaborator

Please post the esception with 7.7.0 because I assume line number must be different. Ten I can have a look.

Ideally with enhanced debug by using

DEBUG=TuyAPI* node ....

@ddpurdie
Copy link

I've extended the 'Received UDP message' debug statement to display the message.

  TuyAPI Received UDP message. <Buffer 00 00 66 99 00 00 00 00 00 00 00 00 00 13 00 00 00 f0 d6 5d d4 4e 23 9b b7 0d e0 f3 99 ce 42 1c d4 71 ad 41 35 13 48 af e3 23 27 5f fc 58 e2 ef c2 87 ... 212 more bytes> +729ms
  TuyAPI RangeError [ERR_OUT_OF_RANGE]: The value of "offset" is out of range. It must be >= 0 and <= 258. Received 262
  TuyAPI     at boundsError (node:internal/buffer:88:9)
  TuyAPI     at Uint8Array.readInt32BE (node:internal/buffer:484:5)
  TuyAPI     at MessageParser.parsePacket (/home/data/work/tuya/javascript/node_modules/tuyapi/lib/message-parser.js:216:36)
  TuyAPI     at MessageParser.parseRecursive (/home/data/work/tuya/javascript/node_modules/tuyapi/lib/message-parser.js:280:25)
  TuyAPI     at MessageParser.parse (/home/data/work/tuya/javascript/node_modules/tuyapi/lib/message-parser.js:301:17)
  TuyAPI     at Socket.<anonymous> (/home/data/work/tuya/javascript/node_modules/tuyapi/index.js:1016:26)
  TuyAPI     at Socket.emit (node:events:518:28)
  TuyAPI     at UDP.onMessage [as onmessage] (node:dgram:942:8) +2ms
  TuyAPI UDP data: +1ms
  TuyAPI undefined +1ms
/home/data/work/tuya/javascript/node_modules/tuyapi/index.js:1025
      const thisID = dataRes.payload.gwId;
                             ^

TypeError: Cannot read properties of undefined (reading 'payload')
    at Socket.<anonymous> (/home/data/work/tuya/javascript/node_modules/tuyapi/index.js:1025:30)
    at Socket.emit (node:events:518:28)
    at UDP.onMessage [as onmessage] (node:dgram:942:8)

Node.js v22.11.0

@Apollon77
Copy link
Collaborator

Apollon77 commented Jan 27, 2025

Ok, in the code there seems to be a return missing when such a parsing error happens.

Other then that ... which version is set for this device from your side? Because seems not to be 3.5

@ddpurdie
Copy link

Interesting question. I've not set a 'version'. I'm expecting the 'find' to handle that.
The code example:

const device = new TuyAPI({
  id: 'xxxxxxxxxxxxxxxxxxxx',
  key: 'xxxxxxxxxxxxxxxx'})

Does not include a version.
I've since added
version: 3.5, to the creation of the device object. The results vary.
I've also modified to test code to follow another example.

const TuyAPI = require('tuyapi');

const device = new TuyAPI({
    version: '3.5',
    id: 'bfcd8c1a8cee583a86bsw5',
    key: 'G1yDGXt$B!RPRc$-' ,
    issueRefreshOnConnect: true});

// Find device on network
device.find().then(() => {
    // Connect to device
    device.connect();
});

// Add event listeners
device.on('connected', () => {
    console.log('Connected to device!');
});

device.on('disconnected', () => {
    console.log('Disconnected from device.');
});

device.on('error', error => {
    console.log('Error!', error);
});

device.on('dp-refresh', data => {
    console.log('DP_REFRESH data from device: ', data);
});

device.on('data', data => {
    console.log('DATA from device: ', data);

});

// Disconnect after 10 seconds
setTimeout(() => { device.disconnect(); }, 1000);

If a non version 3.5 device is processed first then I get

TuyAPI Finding missing IP undefined or ID bfcd8c1a8cee583a86bsw5 +0ms
TuyAPI Received UDP message. <Buffer 00 00 55 aa 00 00 00 00 00 00 00 23 00 00 00 bc 00 00 00 00 f4 ac 6f d3 f5 e5 16 01 43 0e e9 7c fe 73 6a 90 b2 bf ec d0 b7 34 71 54 ad 1c 77 34 75 da ... 154 more bytes> +2s
TuyAPI UDP data: +7ms
TuyAPI {
TuyAPI   payload: '\x00\x00\x00\x00\x00\x00\x00#\x00\x00\x00�\x00\x00\x00\x00��o���\x16\x01C\x0E�|�sj����з4qT�\x1Cw4uڒ+ȿTV�N\b�w#�l\x024`,\x0E��@���\x1A1C\x04,h�{�rV���\x0B�ɔol���HS.\r����1r���8�W��>J�C�&=�i\x04�|O(\x1C3\\ʜ�C�3\x07��+\x12�o�4o��>��Ş�\x07z7\x13��4��\\Ɯj\x0E\x151`�{�\n' +
TuyAPI     '̛�\x10��\x02u�W\x04�Gi',
TuyAPI   leftover: false,
TuyAPI   commandByte: 2293760,
TuyAPI   sequenceN: 0
TuyAPI } +0ms
TuyAPI Connecting to undefined... +8ms
TuyAPI Error event from socket. undefined AggregateError [ECONNREFUSED]: 
  at internalConnectMultiple (node:net:1121:18)
  at afterConnectMultiple (node:net:1688:7) {
code: 'ECONNREFUSED',
[errors]: [
  Error: connect ECONNREFUSED ::1:6668
      at createConnectionError (node:net:1651:14)
      at afterConnectMultiple (node:net:1681:16) {
    errno: -111,
    code: 'ECONNREFUSED',
    syscall: 'connect',
    address: '::1',
    port: 6668
  },
  Error: connect ECONNREFUSED 127.0.0.1:6668
      at createConnectionError (node:net:1651:14)
      at afterConnectMultiple (node:net:1681:16) {
    errno: -111,
    code: 'ECONNREFUSED',
    syscall: 'connect',
    address: '127.0.0.1',
    port: 6668
  }
]
} +13ms
node:events:496
    throw er; // Unhandled 'error' event
    ^

Error: Error from socket: 
  at Socket.<anonymous> (/home/data/work/tuya/javascript/node_modules/tuyapi/index.js:686:26)
  at Socket.emit (node:events:518:28)
  at emitErrorNT (node:internal/streams/destroy:170:8)
  at emitErrorCloseNT (node:internal/streams/destroy:129:3)
  at process.processTicksAndRejections (node:internal/process/task_queues:90:21)
Emitted 'error' event on TuyaDevice instance at:
  at Socket.<anonymous> (/home/data/work/tuya/javascript/node_modules/tuyapi/index.js:686:12)
  at Socket.emit (node:events:518:28)
  [... lines matching original stack trace ...]
  at process.processTicksAndRejections (node:internal/process/task_queues:90:21)

If, by chance, a version 3.5 device is processed first then I get:


  TuyAPI Finding missing IP undefined or ID bfcd8c1a8cee583a86bsw5 +0ms
  TuyAPI Received UDP message. <Buffer 00 00 66 99 00 00 00 00 00 00 00 00 00 13 00 00 00 f0 0a 82 85 0e 96 3e 3c 2b 47 58 ef bf 79 b1 2c ca 02 41 9c a2 62 75 bc 5b 21 0a 0b aa 36 a9 42 7e ... 212 more bytes> +837ms
  TuyAPI UDP data: +7ms
  TuyAPI {
  TuyAPI   payload: {
  TuyAPI     ip: '192.168.86.20',
  TuyAPI     gwId: 'bfcd8c1a8cee583a86bsw5',
  TuyAPI     uuid: 'ab1127bdfbef9b0d',
  TuyAPI     active: 2,
  TuyAPI     ablilty: 0,
  TuyAPI     encrypt: true,
  TuyAPI     productKey: 'key8u54q9dtru5jw',
  TuyAPI     version: '3.5',
  TuyAPI     token: true,
  TuyAPI     wf_cfg: true,
  TuyAPI     clientLink: 3
  TuyAPI   },
  TuyAPI   leftover: false,
  TuyAPI   commandByte: 19,
  TuyAPI   sequenceN: 0
  TuyAPI } +0ms
  TuyAPI Connecting to 192.168.86.20... +8ms
  TuyAPI Socket connected. +156ms
  TuyAPI Protocol 3.4, 3.5: Negotiate Session Key - Send Msg 0x03 +4ms
  TuyAPI Socket closed: 192.168.86.20 +30s

It looks like the connect times out.
If I set the IP address as well as the other parameters, then I get:

  TuyAPI IP and ID are already both resolved. +0ms
  TuyAPI Connecting to 192.168.86.20... +4ms
  TuyAPI Socket connected. +206ms
  TuyAPI Protocol 3.4, 3.5: Negotiate Session Key - Send Msg 0x03 +6ms
  TuyAPI Socket closed: 192.168.86.20 +30s

Again, this looks like a timeout - after 30 seconds

@Apollon77
Copy link
Collaborator

I try to optimize the version detection ... if you like install from this branch here #690 and see if it is better when you do not provide a version

@ddpurdie
Copy link

Partial success.
If I specify id, key and ip, then i get a non crashing result.
If I specify just the id and the key, then it does crash

TuyAPI Finding missing IP undefined or ID bfcd8c1a8cee583a86bsw5 +0ms
 TuyAPI Received UDP message. +2s
 TuyAPI UDP data: +3ms
 TuyAPI {
 TuyAPI   payload: {
 TuyAPI     ip: '192.168.86.36',
 TuyAPI     gwId: 'bf81baecffdd933ca4zpaa',
 TuyAPI     active: 2,
 TuyAPI     ablilty: 0,
 TuyAPI     encrypt: true,
 TuyAPI     productKey: 'keyjup78v54myhan',
 TuyAPI     version: '3.4',
 TuyAPI     token: true,
 TuyAPI     wf_cfg: true
 TuyAPI   },
 TuyAPI   leftover: false,
 TuyAPI   commandByte: 35,
 TuyAPI   sequenceN: 0,
 TuyAPI   version: '3.1'
 TuyAPI } +1ms
 TuyAPI Received UDP message. +162ms
 TuyAPI UDP data: +1ms
 TuyAPI {
 TuyAPI   payload: {
 TuyAPI     ip: '192.168.86.28',
 TuyAPI     gwId: 'bfd3ed4a52741fc369ilwc',
 TuyAPI     active: 2,
 TuyAPI     ablilty: 0,
 TuyAPI     encrypt: true,
 TuyAPI     productKey: 'agjbamgmrbcbazp7',
 TuyAPI     version: '3.3'
 TuyAPI   },
 TuyAPI   leftover: false,
 TuyAPI   commandByte: 19,
 TuyAPI   sequenceN: 0,
 TuyAPI   version: '3.1'
 TuyAPI } +0ms
 TuyAPI Received UDP message. +131ms
 TuyAPI UDP data: +1ms
 TuyAPI {
 TuyAPI   payload: {
 TuyAPI     ip: '192.168.86.39',
 TuyAPI     gwId: 'bfcfd16ce0c5949776lx97',
 TuyAPI     active: 2,
 TuyAPI     ablilty: 0,
 TuyAPI     encrypt: true,
 TuyAPI     productKey: 'keyjup78v54myhan',
 TuyAPI     version: '3.4',
 TuyAPI     token: true,
 TuyAPI     wf_cfg: true
 TuyAPI   },
 TuyAPI   leftover: false,
 TuyAPI   commandByte: 35,
 TuyAPI   sequenceN: 0,
 TuyAPI   version: '3.1'
 TuyAPI } +1ms
 TuyAPI Received UDP message. +1s
 TuyAPI UDP data: +1ms
 TuyAPI {
 TuyAPI   payload: '\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00�@��y��P�&v�X�\\�3Wkr"�\x11�_ٺj] 8\x07ߞʥ�\x1D\x11s��r�:�\x0BW�9J"C�Q�5��2?���jt��\x04\x1D�Ҹ�Iڜ�\x10�����\x13���P�ot6�8���1\x1E�\b��Z\x0E>\x01{\x02.�M��S_i��䇓\x1A2\x06%�-��W��usZ/\x1C�\x1D\x18�U\x02u�.��Į\r8G��\x02"\x02n���3\x1C�\x15&\x0BW��v\x18>�O\x03�M\x1F� �\x1E�G�v8)�&OD�\x12\x1B\x03\x14�\x1B�\x16�Y�\x16�܄�,�Cۭ�j�̣�jk��\x02�`\x00\x12,�?��vA',
 TuyAPI   leftover: false,
 TuyAPI   commandByte: 19,
 TuyAPI   sequenceN: 0,
 TuyAPI   version: '3.5'
 TuyAPI } +1ms
 TuyAPI Connecting to undefined... +5ms
 TuyAPI Error event from socket. undefined AggregateError [ECONNREFUSED]: 
   at internalConnectMultiple (node:net:1121:18)
   at afterConnectMultiple (node:net:1688:7) {
 code: 'ECONNREFUSED',
 [errors]: [
   Error: connect ECONNREFUSED ::1:6668
       at createConnectionError (node:net:1651:14)
       at afterConnectMultiple (node:net:1681:16) {
     errno: -111,
     code: 'ECONNREFUSED',
     syscall: 'connect',
     address: '::1',
     port: 6668
   },
   Error: connect ECONNREFUSED 127.0.0.1:6668
       at createConnectionError (node:net:1651:14)
       at afterConnectMultiple (node:net:1681:16) {
     errno: -111,
     code: 'ECONNREFUSED',
     syscall: 'connect',
     address: '127.0.0.1',
     port: 6668
   }
 ]
} +17ms
Error! Error: Error from socket: 
   at Socket.<anonymous> (/home/data/work/tuya/javascript/node_modules/tuyapi/index.js:688:26)
   at Socket.emit (node:events:518:28)
   at emitErrorNT (node:internal/streams/destroy:170:8)
   at emitErrorCloseNT (node:internal/streams/destroy:129:3)
   at process.processTicksAndRejections (node:internal/process/task_queues:90:21)
node:internal/process/promises:394
   triggerUncaughtException(err, true /* fromPromise */);
   ^

AggregateError [ECONNREFUSED]: 
   at internalConnectMultiple (node:net:1121:18)
   at afterConnectMultiple (node:net:1688:7) {
 code: 'ECONNREFUSED',
 [errors]: [
   Error: connect ECONNREFUSED ::1:6668
       at createConnectionError (node:net:1651:14)
       at afterConnectMultiple (node:net:1681:16) {
     errno: -111,
     code: 'ECONNREFUSED',
     syscall: 'connect',
     address: '::1',
     port: 6668
   },
   Error: connect ECONNREFUSED 127.0.0.1:6668
       at createConnectionError (node:net:1651:14)
       at afterConnectMultiple (node:net:1681:16) {
     errno: -111,
     code: 'ECONNREFUSED',
     syscall: 'connect',
     address: '127.0.0.1',
     port: 6668
   }
 ]
}

Node.js v22.11.0

I must go. I though I would pass on the partial good news as soon as I could.
I need to look into the good result - I think the dps is funny

 TuyAPI IP and ID are already both resolved. +0ms
  TuyAPI Connecting to 192.168.86.20... +5ms
  TuyAPI Socket connected. +211ms
Connected to device!
  TuyAPI GET Payload (refresh): +5ms
  TuyAPI {
  TuyAPI   gwId: 'bfcd8c1a8cee583a86bsw5',
  TuyAPI   devId: 'bfcd8c1a8cee583a86bsw5',
  TuyAPI   t: '1738043575',
  TuyAPI   dpId: [ 4, 5, 6, 18, 19, 20 ],
  TuyAPI   uid: 'bfcd8c1a8cee583a86bsw5'
  TuyAPI } +0ms
  TuyAPI GET Payload: +10ms
  TuyAPI {
  TuyAPI   gwId: 'bfcd8c1a8cee583a86bsw5',
  TuyAPI   devId: 'bfcd8c1a8cee583a86bsw5',
  TuyAPI   t: '1738043575',
  TuyAPI   dps: {},
  TuyAPI   uid: 'bfcd8c1a8cee583a86bsw5'
  TuyAPI } +0ms
  TuyAPI Disconnect +773ms
Disconnected from device.
  TuyAPI Socket closed: 192.168.86.20 +3ms

No time today.

@Apollon77
Copy link
Collaborator

Ok, please have a look again when you find time. I updated the branch ...

@ddpurdie
Copy link

Hi Ingo,
I've had a little bit of time to play.

In the device constructor I need to specify either 'ip' or the 'version' for joy.
If neither is specified then the device is found, but the payload is not decoded and the ip or id are not available in the device object for use by the connect().

My reading is that the 'find' operation should find the required device if either the ip or the id are not present and fill in the missing fields.

I have devices of version 3.3, 3.4 and 3.5 in my system.
If I 'find' the version 3.3 device specifying only id and key, then I see (what I think ) is expected behavior: ie: payload decoded and a connection made, although the version is a little bit confused.

    id: 'bfd3ed4a52741fc369ilwc',
    key: 'G1yDGXt$B!RPRc$-' ,
    issueRefreshOnConnect: true
});
  TuyAPI {
  TuyAPI   payload: {
  TuyAPI     ip: '192.168.86.28',
  TuyAPI     gwId: 'bfd3ed4a52741fc369ilwc',
  TuyAPI     active: 2,
  TuyAPI     ablilty: 0,
  TuyAPI     encrypt: true,
  TuyAPI     productKey: 'agjbamgmrbcbazp7',
  TuyAPI     version: '3.3'
  TuyAPI   },
  TuyAPI   leftover: false,
  TuyAPI   commandByte: 19,
  TuyAPI   sequenceN: 0,
  TuyAPI   version: '3.1'
  TuyAPI } +0ms
  TuyAPI Connecting to 192.168.86.28... +5ms
  TuyAPI Socket connected. +148ms
Connected to device!

On a version 3.4 or 3.5 device I get:

TuyAPI Received UDP message. +21ms
  TuyAPI UDP data: +2ms
  TuyAPI {
  TuyAPI   payload: '\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00�:\x00���\x1B\x07�T�K�\x1A�ؒ�47��x�\x01�+��<�#�譛\x16\x12Q��\x07�-���d�\r\x03U\tXS0\x17�\x1A��c0�zf����\t��=h�MZ��5\x1A�"�\x02\n' +
  TuyAPI     '��!���9�cͦ�,e�\x1E��=Ny�\x00\x0E�\x1Am�U��|��#��v�+1ms^�"#���\x1C7�&�*��2�9unq����Do�\x11�\x14=�G����z���� ��\x11��X�\x03\r6�2\x07\x7F/9�հ���\x07��f���\n' +
  TuyAPI     '�\x1C�;����\x7FZ\x1B\x0E��\x01D\x1D&e\x0Ed\x7F�\x04\x16ߪ\x02AֻU�@�',
  TuyAPI   leftover: false,
  TuyAPI   commandByte: 19,
  TuyAPI   sequenceN: 0,
  TuyAPI   version: '3.5'
  TuyAPI }
  TuyAPI Connecting to undefined... +5ms

I'll continue digging as time permits

@Apollon77
Copy link
Collaborator

Please try the branch I mentioned above ... The "connect toi undefined" should not happen with that anymore at all!

For 3.4 and 3.5 the content is encrypted and I think that the real key needs to be used to decrypt ... if that assumption is right then .... Do you wanne try something just for the 3.4/3.5 case !?

change

tuyapi/index.js

Line 1014 in a8212a8

const parser = new MessageParser({key: UDP_KEY, version: this.device.version});

to be

  const parser = new MessageParser({key: this.device.key, version: this.device.version});

Does it then correctly decode the payload?

If yes I can add handling to try the device key as fallback if the normal key is not working

@ddpurdie
Copy link

The connection to 'undefined' does not occur any more.

I changed line 1014 as suggested. The v3.4/v3.5 payload is still not decoded.

In its original form, the v3.3 and 3.4 payloads are decoded. The v3.5 payloads are not decoded.
The complete output for all devices is:

2025-01-29T10:09:52.609Z TuyAPI Finding missing IP undefined or ID xxxxxxxxxxxxxxxxxxxxxx
2025-01-29T10:09:52.731Z TuyAPI Received UDP message.
2025-01-29T10:09:52.734Z TuyAPI UDP data:
2025-01-29T10:09:52.737Z TuyAPI {
  payload: {
    ip: '192.168.86.36',
    gwId: 'bf81baecffdd933ca4zpaa',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:09:52.973Z TuyAPI Received UDP message.
2025-01-29T10:09:52.974Z TuyAPI UDP data:
2025-01-29T10:09:52.976Z TuyAPI {
  payload: '\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00��k����c.2��M��KJ�0\tg�������dzn�A���`]|�E�Ux)�\x05 \x0Ed\x0Bi��\x05�r�\x01\t���1��\x1D���_q\x14��� %��\x1D3\x15\x1E�\t�K��\x13m���y�s��A\x1F�2\x02���=4\x1A#� ʘ�{MN�41��\x00Pe������g�\x05\x1Bu\r�4�sf���9#t\\v*�\x14z݃\n' +
    "v�BPZ�Ѧ�d�H?����W��(\x15�x���#8c\x00�\x1F\x17���\x02�eA�>�E-#`߯�¶���+�'C����\fn2\x14���3g�[�AI�",
  leftover: false,
  commandByte: 19,
  sequenceN: 0,
  version: '3.5'
}
2025-01-29T10:09:52.976Z TuyAPI Received string payload. Ignoring.
2025-01-29T10:09:53.610Z TuyAPI Received UDP message.
2025-01-29T10:09:53.611Z TuyAPI UDP data:
2025-01-29T10:09:53.612Z TuyAPI {
  payload: {
    ip: '192.168.86.38',
    gwId: 'bff9627d4cfc0f9e12hhbc',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:09:54.483Z TuyAPI Received UDP message.
2025-01-29T10:09:54.484Z TuyAPI UDP data:
2025-01-29T10:09:54.484Z TuyAPI {
  payload: '\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00�\x1E}����\x7F\r=��A�5*9i)C\x06đ�u\x17�Ŷb\x03\b^n)\n' +
    '������^ٰ\x07��x\x15��`\x01�\x05�Z��.��a�q���q�(\x04�3�̢إg>oBm\b\x07�K���&�B]�6b���y��\x1E��\x14]E�㼲Q�%���Z9��k�t�W���\'��\x1F\x01�z��\x1A\x10��Q%��\rty�{\x02n!��\x07� >sW�@\x7F��_�T�LbS�\x04B�݇��+E�GG���EZ��`�\x1Aĝ�J����3A�\x1D�Ϳِ�z�\b\x19"i���\x0Bxi\x0Ej��',
  leftover: false,
  commandByte: 19,
  sequenceN: 0,
  version: '3.5'
}
2025-01-29T10:09:54.484Z TuyAPI Received string payload. Ignoring.
2025-01-29T10:09:54.846Z TuyAPI Received UDP message.
2025-01-29T10:09:54.846Z TuyAPI UDP data:
2025-01-29T10:09:54.847Z TuyAPI {
  payload: {
    ip: '192.168.86.32',
    gwId: 'bf401cdb231a5e08f3q675',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:09:54.969Z TuyAPI Received UDP message.
2025-01-29T10:09:54.969Z TuyAPI UDP data:
2025-01-29T10:09:54.970Z TuyAPI {
  payload: {
    ip: '192.168.86.45',
    gwId: 'bf59457bce4b1064b4p01n',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:09:55.102Z TuyAPI Received UDP message.
2025-01-29T10:09:55.103Z TuyAPI UDP data:
2025-01-29T10:09:55.103Z TuyAPI {
  payload: {
    ip: '192.168.86.39',
    gwId: 'bfcfd16ce0c5949776lx97',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:09:57.405Z TuyAPI Received UDP message.
2025-01-29T10:09:57.406Z TuyAPI UDP data:
2025-01-29T10:09:57.406Z TuyAPI {
  payload: {
    ip: '192.168.86.28',
    gwId: 'bfd3ed4a52741fc369ilwc',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'agjbamgmrbcbazp7',
    version: '3.3'
  },
  leftover: false,
  commandByte: 19,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:09:57.736Z TuyAPI Received UDP message.
2025-01-29T10:09:57.737Z TuyAPI UDP data:
2025-01-29T10:09:57.737Z TuyAPI {
  payload: {
    ip: '192.168.86.36',
    gwId: 'bf81baecffdd933ca4zpaa',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:09:57.950Z TuyAPI Received UDP message.
2025-01-29T10:09:57.951Z TuyAPI UDP data:
2025-01-29T10:09:57.951Z TuyAPI {
  payload: '\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00�8�8��\x05��X�\x0ER���w�+d��\x18�Ln"\x10j|O��nS\x13��51��R���Ѿ\x1F�:友��k���\x1A��B�Yu\b�@�N,�/����\r�.>�}\b|�9���\r�\x12�7_Ng��<���\x0E�Pv�\x06Av�$}>\x07v#c\x7F\x1Ai-�c���R7\x0E��Kw&���\x7F3E��b`=��!`D\x1Ca<i��\x1D\f�\x1A\x7FG*�[=>\'\r�l6|\\�^���]D����\x02��&�{�\x03H��_X#��\x16B��r\x11�b�J#�\x12)��ij\x1At�0�S-��>X',
  leftover: false,
  commandByte: 19,
  sequenceN: 0,
  version: '3.5'
}
2025-01-29T10:09:57.951Z TuyAPI Received string payload. Ignoring.
2025-01-29T10:09:58.615Z TuyAPI Received UDP message.
2025-01-29T10:09:58.615Z TuyAPI UDP data:
2025-01-29T10:09:58.615Z TuyAPI {
  payload: {
    ip: '192.168.86.38',
    gwId: 'bff9627d4cfc0f9e12hhbc',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:09:59.504Z TuyAPI Received UDP message.
2025-01-29T10:09:59.505Z TuyAPI UDP data:
2025-01-29T10:09:59.505Z TuyAPI {
  payload: `\x00\x00\x00\x00\x00\x00\x00\x00\x00\x13\x00\x00\x00�4\f�'yV\x10��t���"k�\x02M\x1C\x10\x1Fxlz�%�����\x17��=zTj"\x1C��V\x0E�G�Wi!����\x07\x1A"��\x0B�9m�q��u\x14fM�kr�\x18-��<����E��Q�0���ӵ\x0F\b{.�K��z��&�o�|\x18(���\x1B"��6nXi0��\x15b[\x1F�4\x14\x07�B�&\x0B'}X�C!5����������0�A�u0�*�]�\x13���\x00�\x15�Ǔ��}�7I�9\x10n\x1E��<#n@����M�@�e~1\x03���\x10��/�oQE�vP��\x00g��\x16�`,
  leftover: false,
  commandByte: 19,
  sequenceN: 0,
  version: '3.5'
}
2025-01-29T10:09:59.505Z TuyAPI Received string payload. Ignoring.
2025-01-29T10:09:59.859Z TuyAPI Received UDP message.
2025-01-29T10:09:59.860Z TuyAPI UDP data:
2025-01-29T10:09:59.860Z TuyAPI {
  payload: {
    ip: '192.168.86.32',
    gwId: 'bf401cdb231a5e08f3q675',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:09:59.966Z TuyAPI Received UDP message.
2025-01-29T10:09:59.966Z TuyAPI UDP data:
2025-01-29T10:09:59.966Z TuyAPI {
  payload: {
    ip: '192.168.86.45',
    gwId: 'bf59457bce4b1064b4p01n',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:10:00.068Z TuyAPI Received UDP message.
2025-01-29T10:10:00.069Z TuyAPI UDP data:
2025-01-29T10:10:00.069Z TuyAPI {
  payload: {
    ip: '192.168.86.39',
    gwId: 'bfcfd16ce0c5949776lx97',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'keyjup78v54myhan',
    version: '3.4',
    token: true,
    wf_cfg: true
  },
  leftover: false,
  commandByte: 35,
  sequenceN: 0,
  version: '3.1'
}
2025-01-29T10:10:02.411Z TuyAPI Received UDP message.
2025-01-29T10:10:02.412Z TuyAPI UDP data:
2025-01-29T10:10:02.412Z TuyAPI {
  payload: {
    ip: '192.168.86.28',
    gwId: 'bfd3ed4a52741fc369ilwc',
    active: 2,
    ablilty: 0,
    encrypt: true,
    productKey: 'agjbamgmrbcbazp7',
    version: '3.3'
  },
  leftover: false,
  commandByte: 19,
  sequenceN: 0,
  version: '3.1'
}
/home/data/work/tuya/javascript/node_modules/tuyapi/index.js:1111
      throw new Error('find() timed out. Is the device powered on and the ID or IP correct?');
            ^

Error: find() timed out. Is the device powered on and the ID or IP correct?
    at /home/data/work/tuya/javascript/node_modules/tuyapi/index.js:1111:13
    at Timeout._onTimeout (/home/data/work/tuya/javascript/node_modules/p-timeout/index.js:25:13)
    at listOnTimeout (node:internal/timers:594:17)
    at process.processTimers (node:internal/timers:529:7)

Node.js v22.11.0

@Apollon77
Copy link
Collaborator

Hm ... but there is a 3.4 decoded as you can see ... could it be you tried with the 3.4 key? Can you try with the 3.5 device key?

@Apollon77
Copy link
Collaborator

Ahh wait, I found another place where the version was not updated to the "detected" one. Please update again, so that one manual change again please and test again. if that works with 3.4 the I think i have an idea how to fix it for all

@ddpurdie
Copy link

Jackpot. Works for 3.3, 3.4 and 3.5 devices

@ddpurdie
Copy link

My one observation is that the UPD data.payload.version does not always match the UDP data.version
It does for 3.5, but not for 3.4 or 3.3.
ie:

TuyAPI UDP data: +0ms
  TuyAPI {
  TuyAPI   payload: {
  TuyAPI     ip: '192.168.86.32',
  TuyAPI     gwId: 'bf401cdb231a5e08f3q675',
  TuyAPI     active: 2,
  TuyAPI     ablilty: 0,
  TuyAPI     encrypt: true,
  TuyAPI     productKey: 'keyjup78v54myhan',
  TuyAPI     version: '3.4',                                                            <-------
  TuyAPI     token: true,
  TuyAPI     wf_cfg: true
  TuyAPI   },
  TuyAPI   leftover: false,
  TuyAPI   commandByte: 35,
  TuyAPI   sequenceN: 0,
  TuyAPI   version: '3.1'                                                             <-------

@iainmc83
Copy link
Author

Thanks for picking this up chaps. You've both gone way above my understanding! Can you confirm we're both running this the same way @ddpurdie and I'll check it with my bulbs.

I last ran it by doing:

git checkout optimizations2701
npm ci
DEBUG=* node dev.js

...using the example code you posted above. I was only specifying id and key and I was also seeing the find() timeout. How did you determine which version of the protocol your bulbs were using without an output from the api?

I haven't tried the latest branch yet, I'll do that when I'm home tomorrow and once I know I'm running correctly.

@ddpurdie
Copy link

I used the tinytuya module for python to determine other information - version ...

@Apollon77
Copy link
Collaborator

@ddpurdie That the version is different when this is the log of the "find" then in fact the "payload" version is the one returned via discovery and the other is the "assumed" version which always defaults to 3.1 ... some lines later this gets then fixed ... so it is this log only.

I will cleanup and release a new version soon

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants