Skip to main content

Python client library and CLI for the LED-Ticker BLE device

Project description

led_ticker — Python library & CLI for the LED Ticker

led_ticker speaks the same BLE service as the iOS app, so you can drive the device — or build your own tools — from any machine with Bluetooth. The device advertises as LED-Ticker-XXXX.

Install

pip install led-ticker      # or: uv add led-ticker

This installs the importable led_ticker package and the led command. From a checkout you can also run the CLI with no install via uv:

uv run tools/led.py <cmd>   # uses ./src directly

Library

from led_ticker import LedTicker, scan

# Scan for available devices (returns DeviceInfo with name, address, rssi):
for d in scan():
    print(d.name, d.address, d.rssi)

# Reuse one connection for several operations:
with LedTicker(pin="482913") as d:
    d.set_tickers(["AAPL", "MSFT"])
    d.set_status("BUSY", minutes=30)
    print(d.get_version())          # -> "0.3.0"
    s = d.get_status()              # -> Status(text="BUSY", seconds=1800)

# Or a one-shot for a single call (opens and closes its own connection):
import led_ticker
led_ticker.set_mode(["stocks", "weather"])

LedTicker(select=None, address=None, name_prefix="LED-Ticker", scan_timeout=4.0, timeout=15.0, pin=None). By default the first LED-Ticker-* in range is used; if several are in range it raises AmbiguousDeviceError (whose .candidates is a list of DeviceInfo). Pass select= — a name suffix (the XXXX in LED-Ticker-XXXX), full name, or address — to choose one, or address= to target a known address directly (skips the scan). Methods raise ValidationError, AuthError, DeviceNotFoundError, AmbiguousDeviceError, or ProtocolError (all subclasses of LedTickerError).

Selecting a device

With more than one LED-Ticker in range, list them and target one explicitly:

uv run tools/led.py devices                 # list units: name, address, signal
uv run tools/led.py --device A1B2 status "BUSY" 30   # target by name suffix

--device matches a unit by its name suffix (the XXXX in LED-Ticker-XXXX), its full name, or its Bluetooth address. If you run a command with several units in range and no --device, an interactive terminal prompts you to choose; in a script (no TTY) it lists the candidates and exits non-zero so you can re-run with --device.

CLI

# Sign mode
uv run tools/led.py status "BUSY" 30      # show for 30 min, then auto-clear
uv run tools/led.py status "ON AIR"       # indefinite
uv run tools/led.py status clear

# Timer mode (countdown sign — random animation at zero, then resumes ambient)
uv run tools/led.py timer 10              # 10-minute countdown
uv run tools/led.py timer cancel

# Ambient mode (subset of stocks/weather/clock, 'all', or 'none' for sign-only)
uv run tools/led.py mode stocks weather
uv run tools/led.py mode clock
uv run tools/led.py mode all
uv run tools/led.py mode none

# Power (volatile — power cycle returns to on)
uv run tools/led.py power on
uv run tools/led.py power off

# Display settings (persisted on the device)
uv run tools/led.py display                  # show current brightness + scroll speed
uv run tools/led.py display brightness 8     # brightness 0-15
uv run tools/led.py display speed 50         # scroll ms/step 20-500 (lower = faster)
uv run tools/led.py display 8 50             # both at once

# Timezone (persisted; POSIX TZ string — the iOS app has a friendly picker)
uv run tools/led.py timezone                              # show current
uv run tools/led.py timezone "EST5EDT,M3.2.0,M11.1.0"     # US Eastern

# Data
uv run tools/led.py tickers AAPL TSLA NVDA SPY
uv run tools/led.py locations "47.61,-122.33,Seattle"   # lat,lon,label (look up coords online)
uv run tools/led.py apikey your-finnhub-key
uv run tools/led.py wifi My Network Name password

# Inspect
uv run tools/led.py get version           # firmware version on the device
uv run tools/led.py get wifi|apikey|tickers|status|locations|mode|power|display|timezone|version  # read other settings

# Auth
uv run tools/led.py pin 482913            # save the device's PIN locally (~/.config/led-ticker/pin)
uv run tools/led.py pin clear             # forget the saved PIN
uv run tools/led.py pin-enforce on        # device: require PIN for writes (default after a fresh flash)
uv run tools/led.py pin-enforce off       # device: stop requiring PIN (escape hatch)

# Maintenance
uv run tools/led.py reload                # force stock refresh
uv run tools/led.py reset                 # wipe NVS, rotate PIN, revert to config.h defaults

Stale-PIN safety: every write probes the device after sending the PIN and exits with a clear error if the PIN was rotated by a factory reset — a write never fails silently because of an out-of-date local PIN.

License

Apache-2.0 © 2026 Sunil Sayala — free to use, including commercially, with attribution. (The firmware in the parent repo is also Apache-2.0; the hardware design files are CC BY 4.0 — see the repo root.)

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

led_ticker-0.3.0.tar.gz (21.5 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

led_ticker-0.3.0-py3-none-any.whl (19.3 kB view details)

Uploaded Python 3

File details

Details for the file led_ticker-0.3.0.tar.gz.

File metadata

  • Download URL: led_ticker-0.3.0.tar.gz
  • Upload date:
  • Size: 21.5 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for led_ticker-0.3.0.tar.gz
Algorithm Hash digest
SHA256 b58578d144a415943a13830feb8ecad60b7f944ace77811f7f8b6595ed2c6549
MD5 0a953e08042724cd377ad945ee7e7119
BLAKE2b-256 60c1d2d41461739f2fe5d3f563a02dfe95b281e842bc62b63f55a01aa164b986

See more details on using hashes here.

Provenance

The following attestation bundles were made for led_ticker-0.3.0.tar.gz:

Publisher: publish.yml on ssayala/esp32-led-simple

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file led_ticker-0.3.0-py3-none-any.whl.

File metadata

  • Download URL: led_ticker-0.3.0-py3-none-any.whl
  • Upload date:
  • Size: 19.3 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for led_ticker-0.3.0-py3-none-any.whl
Algorithm Hash digest
SHA256 8051ea16edb2f7db5cafcd86b9307bfba0338a6ec5d466fe75139ab3803516b5
MD5 52a5a000a9a434169ee7afe49c1a5f50
BLAKE2b-256 caf3bab6ce2b7081c4fa78e7fb01966d4eb5b463d1bf461767eeb28d30678655

See more details on using hashes here.

Provenance

The following attestation bundles were made for led_ticker-0.3.0-py3-none-any.whl:

Publisher: publish.yml on ssayala/esp32-led-simple

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page