hbldh / bleak

A cross platform Bluetooth Low Energy Client for Python using asyncio
MIT License
1.82k stars 300 forks source link

[Amazfit] "Operation not permitted" when enabling notifications #558

Closed iarspider closed 3 years ago

iarspider commented 3 years ago

Description

I'm trying to read heartbeat data from my Amazfit watch. I have configured it to be discoverable and to expose the HR data, but I get org.bluez.Error.NotPermitted error.

What I Did

  1. Using discover.py example, I got the mac address of my watch
  2. Using service_explorer.py example, I got the UUID of the service:
    ...
    [Service] 0000180d-0000-1000-8000-00805f9b34fb (Handle: 39): Heart Rate
        [Characteristic] 00002a39-0000-1000-8000-00805f9b34fb (Handle: 43): Heart Rate Control Point (read,write), Value: org.bluez.Error.NotPermitted
        [Characteristic] 00002a37-0000-1000-8000-00805f9b34fb (Handle: 40): Heart Rate Measurement (notify), Value: None
                [Descriptor] 00002902-0000-1000-8000-00805f9b34fb (Handle: 42): Client Characteristic Configuration) | Value: org.bluez.Error.NotPermitted
    ...
  3. Using enable_notifications.py example, I tried getting information, but got org.bluez.Error.NotPermitted error. Adding await client.pair(protection_level=3) before client.start_notify does not change anything.
$ python3 notify.py
Executing <Handle MessageBus._message_reader() created at /usr/local/opt/python-3.8.0/lib/python3.8/asyncio/selector_events.py:252> took 0.113 seconds
Executing <Handle MessageBus._message_reader() created at /usr/local/opt/python-3.8.0/lib/python3.8/asyncio/selector_events.py:252> took 0.112 seconds
Traceback (most recent call last):
  File "notify.py", line 61, in <module>
    loop.run_until_complete(run(address, True))
  File "/usr/local/opt/python-3.8.0/lib/python3.8/asyncio/base_events.py", line 608, in run_until_complete
    return future.result()
  File "notify.py", line 45, in run
    await client.start_notify(CHARACTERISTIC_UUID, notification_handler)
  File "/usr/local/opt/python-3.8.0/lib/python3.8/site-packages/bleak/backends/bluezdbus/client.py", line 927, in start_notify
    assert_reply(reply)
  File "/usr/local/opt/python-3.8.0/lib/python3.8/site-packages/bleak/backends/bluezdbus/utils.py", line 23, in assert_reply
    raise BleakDBusError(reply.error_name)
bleak.exc.BleakDBusError: org.bluez.Error.NotPermitted
iarspider commented 3 years ago

I think (although I have no proofs) that I need to bond with the watch using pre-shared key, however I found no way to input it in bleak. This key is not pin / passkey, but a long hex string, see here for details.

iarspider commented 3 years ago

Nevermind. The auth is done not on bluez level, but by responding to a certain notification: https://github.com/satcar77/miband4/blob/master/miband.py#L30 (yes, this is for Mi Band, but works with my Amazfit just fine)