Simple data logging client for InfluxDB/MQTT target
Project description
klimalogger
A Python client for logging environmental sensor data to MQTT brokers. Supports both server deployments (Linux/Unix with systemd) and embedded CircuitPython microcontrollers (ESP32, RP2040, etc.).
Features
- Automatic sensor detection via I2C bus scanning
- Multiple deployment targets: Server (systemd) and CircuitPython microcontrollers
- MQTT-based data transport with configurable QoS
- Flexible configuration: File-based (server) or environment variable-based (CircuitPython)
- Periodic measurements with configurable intervals
- Built-in calculations: Sea-level pressure adjustment, temperature compensation
Supported Sensors
All sensors use I2C communication and are automatically detected:
| Sensor Type | Measurement | I2C Address (Hex) |
|---|---|---|
| BME680 | Temperature, Humidity, Pressure, Air Quality (VOC) | 0x77 |
| BMP3xx | Temperature, Pressure | Various |
| DPS310 | Temperature, Pressure | Various |
| SHT4x | Temperature, Relative Humidity | 0x44 |
| SGP30 | Air Quality (eCO2, TVOC) | Various |
| SGP40 | Air Quality (VOC raw) | 0x59 |
| SCD4x | CO2 Concentration | 0x62 |
| PM25 | Particulate Matter (PM1.0, PM2.5, PM10) | 0x12 |
| BH1750 | Light Intensity | 0x23 |
| VEML7700 | Ambient Light | 0x10 |
| TSL2591 | Light (Visible + IR) | 0x29 |
| MMC56x3 | Magnetic Field (3-axis) | 0x30 |
Installation
Server Deployment (Linux/Unix)
1. Install via pip
It is recommended to use a virtual environment:
# Create virtual environment
virtualenv /opt/klimalogger
# Activate virtual environment
. /opt/klimalogger/bin/activate
# Install klimalogger
pip install klimalogger
2. Configure
Create a configuration file at /etc/klimalogger.conf:
[queue]
host=mqtt.example.com
port=1883
queue_prefix=sensors
queue_qos=1
# Optional authentication
username=mqtt_user
password=mqtt_password
[client]
# Optional: Explicitly specify sensor I2C addresses (hex, comma-separated)
# If not specified, sensors are auto-detected
# sensors=0x44,0x62,0x77
# Optional: Override default device mapping
# device_map=0x44=SHT4x,0x62=SCD4x
# Optional: Elevation in meters for pressure calculations
elevation=100
Alternate config locations (checked in order):
./klimalogger.conf/etc/klimalogger/klimalogger.conf/etc/klimalogger.conf
3. Test
Validate sensor detection and readout:
/opt/klimalogger/bin/klimalogger --check
This outputs JSON-formatted measurement data.
For debugging with verbose output:
/opt/klimalogger/bin/klimalogger --service --debug
4. Setup systemd Service
Create /etc/systemd/system/klimalogger.service:
[Unit]
Description=Klimalogger Service
After=multi-user.target
[Service]
Type=simple
Restart=always
ExecStart=/opt/klimalogger/bin/klimalogger --service
[Install]
WantedBy=multi-user.target
Enable and start the service:
sudo systemctl daemon-reload
sudo systemctl enable klimalogger
sudo systemctl start klimalogger
# Check status
sudo systemctl status klimalogger
# View logs
sudo journalctl -u klimalogger -f
CircuitPython Deployment (ESP32, RP2040, etc.)
1. Hardware Setup
Connect your CircuitPython device via USB. The device should mount as /Volumes/CIRCUITPY (macOS) or similar on Linux/Windows.
Verified boards include:
- Adafruit QT Py ESP32-S2
- Adafruit QT Py ESP32-S3
Any CircuitPython-compatible board with I2C support should be supported with some minor modifications.
2. Install CircuitPython (if needed)
To update to the latest CircuitPython firmware:
- Enter bootloader mode (press BOOT + RESET, then release RESET)
- Flash firmware using esptool:
esptool write-flash -e 0 ~/Downloads/adafruit-circuitpython-*.bin
Download firmware from circuitpython.org/downloads
3. Install Dependencies
Wait for the hardware to reboot. You should have the mount /Volumes/CIRCUITPY visible.
Install required CircuitPython libraries using circup:
# Install circup if needed
pip install circup
# Install dependencies
circup install -U -r requirements_cpy.txt
4. Configure Environment
Create a settings.toml file in the root of your CircuitPython device:
# WiFi Configuration
WIFI_SSID = "your-wifi-ssid"
WIFI_PASSWORD = "your-wifi-password"
# MQTT Configuration
MQTT_HOST = "mqtt.example.com"
MQTT_PORT = "1883"
MQTT_PREFIX = "sensors"
MQTT_USERNAME = "mqtt_user" # Optional
MQTT_PASSWORD = "mqtt_password" # Optional
# Optional: Elevation in meters
ELEVATION = "100"
# Optional: Device mapping (address=SensorName)
DEVICE_MAP = "119=BMP3xx"
# Local NTP server
NTP_SERVER = "192.168.2.119"
5. Deploy Software
Run the installation script to copy source files to your device:
./install.py
This copies the klimalogger package and main_cpy.py to your CircuitPython device.
6. Run
The device will automatically run main_cpy.py on boot. To restart:
- Press CTRL+D in the REPL, or
- Reset the device
Monitor output via the serial console:
# macOS/Linux
screen /dev/tty.usbmodem* 115200
# Or use Mu Editor's serial console
Development
Requirements
- Python 3.10 or later
- Poetry for dependency management
Setup Development Environment
# Clone the repository
git clone https://github.com/wuan/klimalogger.git
cd klimalogger
# Install dependencies with Poetry
poetry install
# Activate virtual environment
poetry shell
Running Tests
# Run all tests
pytest
# Run with coverage report
pytest --cov=klimalogger
# Run specific test file
pytest tests/sensor/test_bme680.py
Code Quality
This project uses pre-commit hooks for code quality:
# Install pre-commit hooks
pip install pre-commit
pre-commit install
# Run all hooks manually
pre-commit run --all-files
Configured tools:
- black and isort: Code formatting
- ruff: Linting with auto-fixes
- mypy: Static type checking
Building and Publishing
poetry publish --build
Project Structure
klimalogger/
├── klimalogger/ # Main package
│ ├── sensor/ # Individual sensor drivers
│ ├── calc/ # Calculation utilities (pressure, temperature)
│ ├── cpy/ # CircuitPython-specific code
│ ├── script/ # CLI entry points
│ ├── config.py # Configuration management
│ ├── transport.py # MQTT transport layer
│ ├── measurement.py # Data structures
│ └── sensors.py # Sensor management and auto-detection
├── tests/ # Test suite
├── main_cpy.py # CircuitPython entry point
├── install.py # CircuitPython deployment script
└── pyproject.toml # Poetry configuration
Usage Examples
Check Sensor Data
klimalogger --check
Output:
{
"sensor": "SHT4x",
"measurement": "temperature",
"value": 23.5,
"unit": "°C"
}
Run as Service
# With default log level (warnings only)
klimalogger --service
# With verbose output
klimalogger --service --verbose
# With debug output
klimalogger --service --debug
Check Version
klimalogger --version
Contributing
Contributions are welcome! Please:
- Fork the repository
- Create a feature branch
- Make your changes with tests
- Run pre-commit hooks
- Submit a pull request
License
Apache License 2.0 - See LICENSE file for details.
Links
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file klimalogger-0.8.10.tar.gz.
File metadata
- Download URL: klimalogger-0.8.10.tar.gz
- Upload date:
- Size: 21.9 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: poetry/2.2.1 CPython/3.14.1 Darwin/25.2.0
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
e69db50f01c3fbdf9288918d6b682790a72039127eba8e6882a800996560ddc3
|
|
| MD5 |
e21cf0a27048ca71c04c13bba87ef16c
|
|
| BLAKE2b-256 |
bd63a30cd35f10434c2f6774e8bbd65bcc8f023cb386bad51c45aeb6007896bf
|
File details
Details for the file klimalogger-0.8.10-py3-none-any.whl.
File metadata
- Download URL: klimalogger-0.8.10-py3-none-any.whl
- Upload date:
- Size: 29.0 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: poetry/2.2.1 CPython/3.14.1 Darwin/25.2.0
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
89df86553306b21626422691ce5dca87a9b82828725bb9d19e5982019cec4f79
|
|
| MD5 |
61804438dcc838f1c9af0d9efe02bdab
|
|
| BLAKE2b-256 |
8e900d6c8d9cdf2d1466b1daf1f9539967104d9a2653b10b2e4fd0c5b66e4106
|