mihai-dinculescu / tapo

Unofficial Tapo API Client. Works with TP-Link Tapo smart devices. Tested with light bulbs (L510, L520, L530, L610, L630), light strips (L900, L920, L930), plugs (P100, P105, P110, P115, P300), hubs (H100), switches (S200B) and sensors (KE100, T100, T110, T300, T310, T315).
MIT License
339 stars 35 forks source link

Panic in p110.get_device_info() #140

Closed gsaviane closed 8 months ago

gsaviane commented 8 months ago

I'm using this tapo API to fetch the status of some P110 plugs with Python. I got this rust panic while fetching the status:

Dec 02 05:56:09 raspberrypi python3[2031047]: thread 'tokio-runtime-worker' panicked at tapo/src/api/protocol/klap_cipher.rs:61:26: Dec 02 05:56:09 raspberrypi python3[2031047]: range start index 32 out of range for slice of length 0 Dec 02 05:56:09 raspberrypi python3[2031047]: note: run with RUST_BACKTRACE=1 environment variable to display a backtrace Dec 02 05:56:09 raspberrypi python3[2031047]: Traceback (most recent call last): ... Dec 02 05:56:09 raspberrypi python3[2031047]: File "/usr/local/bin/tapo-standby-killer.py", line 38, in readDeviceOn Dec 02 05:56:09 raspberrypi python3[2031047]: device_info = await p110.get_device_info() Dec 02 05:56:09 raspberrypi python3[2031047]: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Dec 02 05:56:09 raspberrypi python3[2031047]: pyo3_asyncio.RustPanic: rust future panicked

It's likely the device became unreachable after a successful connection with p110 = await client.p110(ip). I was also wondering if, instead of just panicking, there is a better way to pass up an exception to the Python layer that it is easier to catch.

mihai-dinculescu commented 8 months ago

That is not a great user experience. This error is currently unhandled in the Rust code, so it bubbles up to Python as a panic.

An unreachable device will throw a proper timeout exception, so it's not that.

This panic occurs when the API of the device returns an empty response. It might be that the response status code is not properly validated. I'll investigate.

gsaviane commented 7 months ago

Hi, the library is still panicking. I tracked the full stack, maybe can help for further investigations

2024-01-07T06:35:41.578057+01:00 raspberrypi python3[1072361]: thread 'tokio-runtime-worker' panicked at tapo/src/api/protocol/klap_cipher.rs:61:26: 2024-01-07T06:35:41.613919+01:00 raspberrypi python3[1072361]: range start index 32 out of range for slice of length 0 2024-01-07T06:35:41.619313+01:00 raspberrypi python3[1072361]: stack backtrace: 2024-01-07T06:35:41.930871+01:00 raspberrypi python3[1072361]: 0: rust_begin_unwind 2024-01-07T06:35:41.932535+01:00 raspberrypi python3[1072361]: at ./rustc/cc66ad468955717ab92600c770da8c1601a4ff33/library/std/src/panicking.rs:595:5 2024-01-07T06:35:41.934638+01:00 raspberrypi python3[1072361]: 1: core::panicking::panic_fmt 2024-01-07T06:35:41.935300+01:00 raspberrypi python3[1072361]: at ./rustc/cc66ad468955717ab92600c770da8c1601a4ff33/library/core/src/panicking.rs:67:14 2024-01-07T06:35:41.935957+01:00 raspberrypi python3[1072361]: 2: core::slice::index::slice_start_index_len_fail_rt 2024-01-07T06:35:41.936342+01:00 raspberrypi python3[1072361]: at ./rustc/cc66ad468955717ab92600c770da8c1601a4ff33/library/core/src/slice/index.rs:52:5 2024-01-07T06:35:41.936777+01:00 raspberrypi python3[1072361]: 3: core::slice::index::slice_start_index_len_fail 2024-01-07T06:35:41.937139+01:00 raspberrypi python3[1072361]: at ./rustc/cc66ad468955717ab92600c770da8c1601a4ff33/library/core/src/slice/index.rs:40:9 2024-01-07T06:35:41.949087+01:00 raspberrypi python3[1072361]: 4: tapo::api::protocol::klap_cipher::KlapCipher::decrypt 2024-01-07T06:35:41.956973+01:00 raspberrypi python3[1072361]: 5: <tapo::api::protocol::klap_protocol::KlapProtocol as tapo::api::protocol::tapo_protocol::TapoPro tocolExt>::execute_request::{{closure}} 2024-01-07T06:35:41.962650+01:00 raspberrypi python3[1072361]: 6: <tapo::api::protocol::tapo_protocol::TapoProtocol as tapo::api::protocol::tapo_protocol::TapoPro tocolExt>::execute_request::{{closure}} 2024-01-07T06:35:41.972875+01:00 raspberrypi python3[1072361]: 7: tapo::api::api_client::ApiClient::get_device_info::{{closure}} 2024-01-07T06:35:41.980510+01:00 raspberrypi python3[1072361]: 8: <pyo3_asyncio::generic::Cancellable as core::future::future::Future>::poll 2024-01-07T06:35:41.983036+01:00 raspberrypi python3[1072361]: 9: <tokio::task::task_local::TaskLocalFuture<T,F> as core::future::future::Future>::poll 2024-01-07T06:35:41.988233+01:00 raspberrypi python3[1072361]: 10: ::spawn::{{closure}} 2024-01-07T06:35:41.995734+01:00 raspberrypi python3[1072361]: 11: tokio::runtime::task::core::Core<T,S>::poll 2024-01-07T06:35:41.996563+01:00 raspberrypi python3[1072361]: 12: tokio::runtime::task::harness::Harness<T,S>::poll 2024-01-07T06:35:41.997293+01:00 raspberrypi python3[1072361]: 13: tokio::runtime::scheduler::multi_thread::worker::Context::run_task 2024-01-07T06:35:42.004578+01:00 raspberrypi python3[1072361]: 14: tokio::runtime::scheduler::multi_thread::worker::Context::run 2024-01-07T06:35:42.012060+01:00 raspberrypi python3[1072361]: 15: tokio::runtime::context::scoped::Scoped::set 2024-01-07T06:35:42.015976+01:00 raspberrypi python3[1072361]: 16: tokio::runtime::context::runtime::enter_runtime 2024-01-07T06:35:42.016336+01:00 raspberrypi python3[1072361]: 17: tokio::runtime::scheduler::multi_thread::worker::run 2024-01-07T06:35:42.016705+01:00 raspberrypi python3[1072361]: 18: tokio::runtime::task::core::Core<T,S>::poll 2024-01-07T06:35:42.023126+01:00 raspberrypi python3[1072361]: 19: tokio::runt

mihai-dinculescu commented 7 months ago

I suspect this is because the above change has not been released yet. There is one more fix I want to get in before I cut a new version. Sorry, it dragged on.

mihai-dinculescu commented 7 months ago

The fix has been released in Tapo Rust v0.7.7 and Tapo Python v0.1.4.

gsaviane commented 7 months ago

Excellent! Sorry, I didn't mean to hurry, just wanted to help.