colmi_r02_client: reading a cheap smart ring over Bluetooth, offline
A python client + documentation for the Colmi R02 smart ring
At a glance
- What is it?
- colmi_r02_client is a Python client for the Colmi R02 family of smart rings, reverse engineered over BLE and kept deliberately offline, with a command line tool for scanning, live heart rate and syncing to SQLite. The protocol notes are in the repository, down to the 16 byte packet layout, the GATT service UUID and the checksum rule.
- Who is it for?
- colmi_r02_client is worth using if you own one of these rings and want your data out of the vendor app, because the client is 100 percent open source and 100 percent offline, so nothing about your heart rate has to leave your machine, and the author has documented the protocol well enough that the work does not have to be redone.
- Can I use it commercially?
- Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
- Is it still maintained?
- Yes. The repository last received commits 105 days ago.
- What is it written in?
- Mainly Python, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on October 23, 2026, and from our analysis. They are not legal advice.
Editorial analysis
A twenty dollar ring with an accelerometer and a heart rate sensor
colmi_r02_client is described as an open source Python client to read your data from the Colmi R02 family of smart rings, and the claim in the README is 100 percent open source and 100 percent offline.
The hardware is described as a cheap smart ring, about twenty dollars, and the sensors listed are an accelerometer for step tracking, sleep tracking and gestures, with the gestures marked as maybe, a heart rate sensor, and blood oxygen, or SPO2.
The origin story is worth a line, because it explains the project's shape. The author found out about the ring from atc1441 and his work on the ATC_RF03, and from the Hackaday coverage of a hackable smart ring. So this is a client built on top of somebody else's reverse engineering of a similar device, extended to a different model, and the project treats the protocol as something to be documented rather than hidden.
Three rings are listed as fully compatible, the Colmi R02, R06 and R10, and the rule of thumb is neat enough to remember: if the listing suggests you use the QRing app, the ring is compatible with this client. That is a practical shortcut, since the app in the listing is the only thing a buyer has to look at.
The MIT licence, the Python primary language, the main branch and a last push on 2026-07-10 with no GitHub releases make this a small, single-author project with a real body of work in it.
The reverse engineering status list is the honest part
The README keeps a checklist of what has been worked out, and it is worth reading because it is more informative than a feature list would be.
Done are real time heart rate and SPO2, step logs, with the author's own note that he still does not quite understand how the day is split up, heart rate logs also called periodic measurement, setting the ring time, and setting the HR log frequency. Not done are SPO2 logs, sleep tracking, and stress measurement.
That gap is the interesting part, because it shows which of the sensors are actually usable. A ring at twenty dollars with an accelerometer and a photodiode can plausibly do heart rate and blood oxygen, and a stress score would be a derived figure from heart rate variability, so its absence is not a hardware limitation. Sleep tracking, on the other hand, is a signal processing job over the accelerometer, and it is listed as not done, which tells you the author has not got that far rather than that the ring cannot do it.
The planned features are more CLI functionality, pretty printing of heart rate and steps, and a simple web interface. So the direction of travel is a nicer command line experience first and a web interface later, which is the order that makes sense for a client that already has a working sync.
The repository also carries a MYSTERIES.md file at the root, which by name alone suggests a running list of the parts of the protocol that are not yet understood, and a check.sh script. The author's own lab notes live on a separate site as a stream of consciousness, starting with a post on smart ring hacking from July 2024, and the README points there as the best source for the raw material.
Install with pipx, then scan for the ring
The getting started section starts with a recommendation that says a lot about the author's priorities. If you do not know Python well, install pipx, because it is purpose built for managing Python packages intended to be used as standalone programs and it will keep your computer safe from the pitfalls of Python packaging.
pipx install git+https://github.com/tahnok/colmi_r02_clientThen you find the ring. The scan command lists nearby devices:
colmi_r02_util scanand the output is a table with a name and a Bluetooth address:
Found device(s)
Name | Address
--------------------------------------------
R02_341C | 70:CB:0D:D0:34:1CWith the address in hand you can read live heart rate:
colmi_r02_client --address=70:CB:0D:D0:34:1C get-real-time heart-ratewhich returns a list of samples:
Starting reading, please wait.
[81, 81, 79, 79, 79, 79]The sync command is the one that matters for keeping history, and it writes to SQLite:
colmi_r02_client --address=3A:08:6A:6F:EB:EC syncThe output shows where the database is written and the window it synced:
Writing to /home/wes/src/colmi_r02_client/ring_data.sqlite
Syncing from 2024-12-01 01:43:04.723232+00:00 to 2024-12-01 02:03:20.150315+00:00
DoneThe database schema is published in the repository at tests/database_schema.sql, which is the kind of thing that saves an afternoon when you want to query the data yourself.
The command surface is small, and the help output is the reference
The CLI is a Click application with a fixed set of commands, and the full help output is printed in the README, which makes it the actual reference for what the tool can do.
Usage: colmi_r02_client [OPTIONS] COMMAND [ARGS]...
Options:
--debug / --no-debug
--record / --no-record Write all received packets to a file
--address TEXT Bluetooth address
--name TEXT Bluetooth name of the device, slower but will work
on macOS
--help Show this message and exit.Two of those options are worth explaining. The name option is the macOS escape hatch, because the README notes that looking a device up by name is slower but will work on macOS, which implies that the address path does not work there, a familiar Bluetooth stack difference. The record option writes all received packets to a file, which is the debugging tool that makes the reverse engineering possible at all, and it pairs with the raw command that sends an arbitrary command to the ring.
The command list covers the implemented features. There is get-heart-rate-log for a given date, get-heart-rate-log-settings, get-real-time-heart-rate, get-steps, info for device info and battery level, raw, reboot, set-heart-rate-log-settings, set-time, and sync. The help text for set-time notes that the time must be set, required if the ring has never been set, which is the kind of detail that saves a confusing first run.
The project also exposes itself as a library, since the colmi_r02_client.client class can be used to write your own code in Python, with docstrings that the author says are visible on the docs site. The docs are generated with pdoc, and the repository holds a docs/ directory along with the package source, tests, a poetry.lock and a pyproject.toml.
A GATT service, 16 byte packets and a checksum that sums the other 15 bytes
The communication protocol details are the part of the project that makes it reusable by someone else, and the README explains them at a level that does not require reading the source.
The ring has a BLE GATT service with the UUID 6E40FFF0-B5A3-F393-E0A9-E50E24DCCA9E, and it has two important characteristics. The RX characteristic is 6E400002-B5A3-F393-E0A9-E50E24DCCA9E, which you write to. The TX characteristic is 6E400003-B5A3-F393-E0A9-E50E24DCCA9E, which you can subscribe to and which is where the ring responds to the packets you have sent. The README notes that this closely resembles the Nordic UART Service and UART and serial communications in general, which is the single most useful fact for anyone modifying the client, because it means the framing is a known pattern rather than a bespoke one.
The packet structure is 16 bytes in both directions. The first byte is always a command, tag or type, so the packet asking for the battery level starts with 0x03 and the response to it also starts with 0x03. The last byte is always a checksum or CRC, and the value is calculated by summing the other fifteen bytes in the packet and taking the result modulo 255, with the implementation in colmi_r02_client.packet.checksum.
The middle fourteen bytes are the subdata or payload. Some requests, like the one in colmi_r02_client.set_time.set_time_packet, include additional data, and almost all responses use the subdata to return what was asked for.
One complication is called out explicitly. Some requests result in multiple responses that have to be considered together to get the data, and the example given is the SportDetailParser in colmi_r02_client.steps. That is a common pattern in firmware protocols and it is where a naive client usually falls over.
The README closes the section by saying that if you want the actual packet structure for a given feature, look at the source code for that feature, and that the author has tried to make it easy to follow even if you do not know Python well, with tests giving validated request and response pairs and human readable interpretations of the data.
There is also a security note, and it is a candid one. There is no binding or security keys required to get started, which the author acknowledges is kind of bad, and then explains the mitigating factor, which is that the range on the ring is really tiny and he is not too worried about someone getting his steps or heart rate information, leaving the judgement to the reader.
Editorial conclusion
colmi_r02_client is worth using if you own one of these rings and want your data out of the vendor app, because the client is 100 percent open source and 100 percent offline, so nothing about your heart rate has to leave your machine, and the author has documented the protocol well enough that the work does not have to be redone. It is the wrong tool if you want the features the client has not reverse engineered yet, since sleep tracking, SPO2 logs and stress measurement are all still unchecked on the status list, and it is the wrong tool if you need continuous background sync, because the client talks to the ring when you ask it to. Before you rely on it, verify three things yourself: that your ring is one of the compatible models, with the QRing app on the listing being the rule of thumb, that your Python is between 3.11 and 3.14, and that the command you want actually exists, since the CLI surface is a fixed list of commands rather than a general interface.
Frequently asked questions
Which Colmi smart rings does colmi_r02_client support?
The Colmi R02, R06 and R10 are listed as fully compatible. The rule of thumb given is that if the listing suggests you use the QRing app, the ring is compatible with the client.
How do I install and use the Colmi R02 client?
The README recommends pipx for people who do not know Python well, with pipx install git+https://github.com/tahnok/colmi_r02_client. Then colmi_r02_util scan finds nearby rings, and colmi_r02_client with an --address gives you live heart rate or a sync to SQLite.
What data has not been reverse engineered yet?
The status list has SPO2 logs, sleep tracking and stress measurement still unchecked, while real time heart rate and SPO2, step logs, heart rate logs, setting the ring time and setting the HR log frequency are done. The author also notes he does not quite understand how the step data splits up the day.
How does the Colmi R02 protocol work?
The ring exposes a BLE GATT service with UUID 6E40FFF0-B5A3-F393-E0A9-E50E24DCCA9E, an RX characteristic to write to and a TX characteristic to subscribe to, closely resembling the Nordic UART Service. Packets are 16 bytes, the first byte is a command or type, the last is a checksum computed by summing the other fifteen bytes modulo 255, and the middle fourteen carry the payload.
Does the Colmi R02 client send my data anywhere?
No. The project describes itself as 100 percent open source and 100 percent offline, and the data is synced to a local SQLite database whose schema is published in the repository. The protocol notes do mention that no binding or security keys are required, which the author frames as a mitigated risk given the ring's very short range.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/tahnok-colmi-r02-client)Was this useful?