janvda / miband4 Goto Github PK
View Code? Open in Web Editor NEWThis project forked from satcar77/miband4
Access Xiaomi MiBand 4 from Linux using Bluetooth LE
This project forked from satcar77/miband4
Access Xiaomi MiBand 4 from Linux using Bluetooth LE
The idea is that it automatically connects to the miband once the miband is in reach.
If the miband goes out of reach - it should properly disconnects.
When connecting / disconnecting an MQTT message must be published.
It would be amazing if it works with Redmi Smart Band 2? Mostly I am interested in music controls...
Actually I want to send signals from my Redmi Smart Band 2 to my Linux computer and do certain simple tasks based on the signal. I don't know if there is any way other than music controls to send a custom message/signal from a smart band.
Is there any documentation for how to start investigating?
I couldn't get the bluetooth log from my Android 8 to investigate it. I am not sure but I think it is because of my phone is not rooted.
After succesful connection navigating to music screen on my miband4 resulted in below error:
2021-11-16 17:20:20,745 miband_api (ERROR) > 'miband' object has no attribute 'artist'
Traceback (most recent call last):
File "/miband4/miband_api.py", line 113, in post_wait_for_notifications
notification_received = band.waitForNotifications(0.5)
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 560, in waitForNotifications
resp = self._getResp(['ntfy','ind'], timeout)
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 416, in _getResp
self.delegate.handleNotification(hnd, data)
File "/miband4/miband.py", line 111, in handleNotification
self.device.setMusic()
File "/miband4/miband.py", line 666, in setMusic
if self.artist is not None:
AttributeError: 'miband' object has no attribute 'artist'
FYI the full log:
root@pi3two:/miband4# python miband_api.py
2021-11-16 17:19:03,940 miband_api (INFO) > Connecting to MQTT broker (nuc1:1883 alive=60, bind_address=)...
2021-11-16 17:19:03,981 miband_api (INFO) > ... connected to MQTT Broker!
2021-11-16 17:19:04,110 uvicorn.error (INFO) > Started server process [1923]
2021-11-16 17:19:04,111 uvicorn.error (INFO) > Waiting for application startup.
2021-11-16 17:19:04,113 uvicorn.error (INFO) > Application startup complete.
2021-11-16 17:19:04,115 uvicorn.error (INFO) > Uvicorn running on http://0.0.0.0:8001 (Press CTRL+C to quit)
2021-11-16 17:19:12,021 uvicorn.access (INFO) > 192.168.2.40:50097 - "GET /docs HTTP/1.1" 200
2021-11-16 17:19:12,396 uvicorn.access (INFO) > 192.168.2.40:50097 - "GET /openapi.json HTTP/1.1" 200
2021-11-16 17:19:38,988 miband (INFO) > Connecting to D1:C5:15:51:03:89
2021-11-16 17:19:40,190 miband (INFO) > Connected
2021-11-16 17:19:46,099 miband (INFO) > Enabling Auth Service notifications status...
2021-11-16 17:19:46,225 miband (INFO) > Requesting random number...
2021-11-16 17:19:46,246 miband (INFO) > Sending encrypted random number
2021-11-16 17:19:46,375 miband (INFO) > Initialized
2021-11-16 17:19:46,376 miband (INFO) > Disabling Auth Service notifications status...
2021-11-16 17:19:46,412 uvicorn.access (INFO) > 192.168.2.40:50098 - "POST /connect?mac_address=D1%3AC5%3A15%3A51%3A03%3A89&authentication_key=1cf7c5612b4791be375f1b02b7f3ac7b HTTP/1.1" 200
2021-11-16 17:20:13,964 miband_api (INFO) > Waiting for notifications - infinite loop - never returning !
2021-11-16 17:20:20,745 miband_api (ERROR) > 'miband' object has no attribute 'artist'
Traceback (most recent call last):
File "/miband4/miband_api.py", line 113, in post_wait_for_notifications
notification_received = band.waitForNotifications(0.5)
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 560, in waitForNotifications
resp = self._getResp(['ntfy','ind'], timeout)
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 416, in _getResp
self.delegate.handleNotification(hnd, data)
File "/miband4/miband.py", line 111, in handleNotification
self.device.setMusic()
File "/miband4/miband.py", line 666, in setMusic
if self.artist is not None:
AttributeError: 'miband' object has no attribute 'artist'
2021-11-16 17:20:25,861 miband_api (INFO) > music focus out
When retrieving activity log getting below error:
2021-11-27 22:50:16,508 miband_api (DEBUG) > retrieve_activity(): acquiring lock ...
2021-11-27 22:50:16,509 miband_api (INFO) > Calling retrieve_activity() ...
2021-11-27 22:50:16,510 miband_api (INFO) > retrieving activity between 2021-11-27 20:50:00 and 2021-11-27 22:45:00
2021-11-27 22:50:16,510 miband (DEBUG) > start_get_previews_data(2021-11-27 20:50:00)...
2021-11-27 22:50:16,512 miband_api (DEBUG) > retrieve_activity():...lock released
2021-11-27 22:50:16,514 uvicorn.access (INFO) > 172.25.0.2:42394 - "POST /retrieve_activity?start_time_ms=1638042600000&end_time_ms=1638049500000 HTTP/1.1" 500
2021-11-27 22:50:16,515 uvicorn.error (ERROR) > Exception in ASGI application
Traceback (most recent call last):
File "/usr/local/lib/python3.9/site-packages/uvicorn/protocols/http/httptools_impl.py", line 375, in run_asgi
result = await app(self.scope, self.receive, self.send)
File "/usr/local/lib/python3.9/site-packages/uvicorn/middleware/proxy_headers.py", line 75, in __call__
return await self.app(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/fastapi/applications.py", line 208, in __call__
await super().__call__(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/starlette/applications.py", line 112, in __call__
await self.middleware_stack(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/starlette/middleware/errors.py", line 181, in __call__
raise exc
File "/usr/local/lib/python3.9/site-packages/starlette/middleware/errors.py", line 159, in __call__
await self.app(scope, receive, _send)
File "/usr/local/lib/python3.9/site-packages/starlette/exceptions.py", line 82, in __call__
raise exc
File "/usr/local/lib/python3.9/site-packages/starlette/exceptions.py", line 71, in __call__
await self.app(scope, receive, sender)
File "/usr/local/lib/python3.9/site-packages/starlette/routing.py", line 656, in __call__
await route.handle(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/starlette/routing.py", line 259, in handle
await self.app(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/starlette/routing.py", line 61, in app
response = await func(request)
File "/usr/local/lib/python3.9/site-packages/fastapi/routing.py", line 226, in app
raw_response = await run_endpoint_function(
File "/usr/local/lib/python3.9/site-packages/fastapi/routing.py", line 161, in run_endpoint_function
return await run_in_threadpool(dependant.call, **values)
File "/usr/local/lib/python3.9/site-packages/starlette/concurrency.py", line 39, in run_in_threadpool
return await anyio.to_thread.run_sync(func, *args)
File "/usr/local/lib/python3.9/site-packages/anyio/to_thread.py", line 28, in run_sync
return await get_asynclib().run_sync_in_worker_thread(func, *args, cancellable=cancellable,
File "/usr/local/lib/python3.9/site-packages/anyio/_backends/_asyncio.py", line 805, in run_sync_in_worker_thread
return await future
File "/usr/local/lib/python3.9/site-packages/anyio/_backends/_asyncio.py", line 743, in run
result = func(*args)
File "/miband4/miband_api.py", line 32, in wrapper
return func(*args, **kwargs)
File "/miband4/miband_api.py", line 46, in wrapper
rc=func(*args, **kwargs)
File "/miband4/miband_api.py", line 255, in retrieve_activity
return band.get_activity_betwn_intervals(start_time,end_time,cb_activity_log)
File "/miband4/miband.py", line 569, in get_activity_betwn_intervals
self.start_get_previews_data(start_timestamp)
File "/miband4/miband.py", line 562, in start_get_previews_data
utc_offset = char.read()[9:11]
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 197, in read
return self.peripheral.readCharacteristic(self.valHandle)
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 530, in readCharacteristic
resp = self._getResp('rd')
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 407, in _getResp
resp = self._waitResp(wantType + ['ntfy', 'ind'], timeout)
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 375, in _waitResp
raise BTLEInternalError("Unexpected response (%s)" % respType, resp)
bluepy.btle.BTLEInternalError: Unexpected response (wr)
2021-11-27 22:55:16,498 miband_api (DEBUG) > retrieve_activity(): acquiring lock ...
Here below the exception raised when device gets disconnect (due to bluetooth out of range):
2021-11-17 10:26:14,386 uvicorn.access (INFO) > 192.168.2.40:58613 - "POST /wait_for_notifications HTTP/1.1" 500
2021-11-17 10:26:14,387 uvicorn.error (ERROR) > Exception in ASGI application
Traceback (most recent call last):
File "/usr/local/lib/python3.9/site-packages/uvicorn/protocols/http/httptools_impl.py", line 375, in run_asgi
result = await app(self.scope, self.receive, self.send)
File "/usr/local/lib/python3.9/site-packages/uvicorn/middleware/proxy_headers.py", line 75, in __call__
return await self.app(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/fastapi/applications.py", line 208, in __call__
await super().__call__(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/starlette/applications.py", line 112, in __call__
await self.middleware_stack(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/starlette/middleware/errors.py", line 181, in __call__
raise exc
File "/usr/local/lib/python3.9/site-packages/starlette/middleware/errors.py", line 159, in __call__
await self.app(scope, receive, _send)
File "/usr/local/lib/python3.9/site-packages/starlette/exceptions.py", line 82, in __call__
raise exc
File "/usr/local/lib/python3.9/site-packages/starlette/exceptions.py", line 71, in __call__
await self.app(scope, receive, sender)
File "/usr/local/lib/python3.9/site-packages/starlette/routing.py", line 656, in __call__
await route.handle(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/starlette/routing.py", line 259, in handle
await self.app(scope, receive, send)
File "/usr/local/lib/python3.9/site-packages/starlette/routing.py", line 61, in app
response = await func(request)
File "/usr/local/lib/python3.9/site-packages/fastapi/routing.py", line 226, in app
raw_response = await run_endpoint_function(
File "/usr/local/lib/python3.9/site-packages/fastapi/routing.py", line 161, in run_endpoint_function
return await run_in_threadpool(dependant.call, **values)
File "/usr/local/lib/python3.9/site-packages/starlette/concurrency.py", line 39, in run_in_threadpool
return await anyio.to_thread.run_sync(func, *args)
File "/usr/local/lib/python3.9/site-packages/anyio/to_thread.py", line 28, in run_sync
return await get_asynclib().run_sync_in_worker_thread(func, *args, cancellable=cancellable,
File "/usr/local/lib/python3.9/site-packages/anyio/_backends/_asyncio.py", line 805, in run_sync_in_worker_thread
return await future
File "/usr/local/lib/python3.9/site-packages/anyio/_backends/_asyncio.py", line 743, in run
result = func(*args)
File "/miband4/miband_api.py", line 20, in wrapper
return func(*args, **kwargs)
File "/miband4/miband_api.py", line 130, in post_wait_for_notifications
notification_received = band.waitForNotifications(0.5)
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 560, in waitForNotifications
resp = self._getResp(['ntfy','ind'], timeout)
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 407, in _getResp
resp = self._waitResp(wantType + ['ntfy', 'ind'], timeout)
File "/usr/local/lib/python3.9/site-packages/bluepy/btle.py", line 362, in _waitResp
raise BTLEDisconnectError("Device disconnected", resp)
bluepy.btle.BTLEDisconnectError: Device disconnected
Hi! Thanks to your fork, I've been able to use the band with my Pinephone!
I'd like to not use to my dusty android phone to set trivial things in the band, like for example my watchface.
No matter which one I load however, it always ends up failing.
I've done some simple analysis and the band fails on b'\x00'
payload = b'\x01\x08'+struct.pack("<I",fileSize)[:-1]+b'\x00'+struct.pack("<I",crc)
char.write(payload,withResponse=True)
self.waitForNotifications(2)
char.write(b'\x03\x01',withResponse=True)
with open(fileName,"rb") as f:
while True:
c = f.read(20) #takes 20 bytes
if not c:
self._log.info ("Bytes written successfully. Wait till sync finishes")
break
char_write.write(c)
# # after update is done send these values
char.write(b'\x00', withResponse=True) # <- It always fails here
self.waitForNotifications(2)
char.write(b'\x04', withResponse=True)
self.waitForNotifications(2)
Here's the related code in GadgetBridge [UpdateFirmwareOperation*], but I can't make sense of it
I would like to help to debug this issue further, if only I could figure how to reliably snoop logs from the android phone.
Make reference to:
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.