diff --git a/.gitignore b/.gitignore index 4c5ca30..68eff0a 100644 --- a/.gitignore +++ b/.gitignore @@ -1,4 +1,8 @@ *.pyc *.swp .vscode -__pycache__ \ No newline at end of file +__pycache__ +*.ini + +mijia/* +miflora/* diff --git a/README.md b/README.md index 4842580..bfe4a31 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,17 @@ -Mi Flower Care & Temp-Humidity sensor +# Mi Flower Care & Temp-Humidity sensor +## Config file +save it as `my.ini` + + [dynamodb] + region_name = ap-southeast-1 + table = iot-logger + +## AWS Credentials + +You have to save credentials in ~/.aws/credentials + + [default] + aws_secret_access_key = ... + aws_access_key_id = ... diff --git a/dynamo.py b/dynamo.py new file mode 100644 index 0000000..1173646 --- /dev/null +++ b/dynamo.py @@ -0,0 +1,95 @@ +import sys +import boto3 +import arrow +import json +import decimal +import configparser + +from mijia.mijia.mijia_poller import MijiaPoller, \ + MI_HUMIDITY, MI_TEMPERATURE, MI_BATTERY +from miflora.miflora.miflora_poller import MiFloraPoller, \ + MI_CONDUCTIVITY, MI_MOISTURE, MI_LIGHT + +config = configparser.ConfigParser() +try: + config.read('my.ini') + region_name = config['dynamodb']['region_name'] + table = config['dynamodb']['table'] +except: + print('Config file read failed') + sys.exit(1) + +dynamodb = boto3.resource('dynamodb', region_name=region_name) +table = dynamodb.Table(table) + + +def flowercare(mac_addr, poller): + temperature = poller.parameter_value(MI_TEMPERATURE) + battery = poller.parameter_value(MI_BATTERY) + light = poller.parameter_value(MI_LIGHT) + moisture = poller.parameter_value(MI_MOISTURE) + conductivity = poller.parameter_value(MI_CONDUCTIVITY) + firmware = poller.firmware_version() + + print('Flower care {}'.format(mac_addr)) + print("Temperature: {}°C".format(temperature)) + print("Moisture: {}%".format(moisture)) + print("Light: {} lux".format(light)) + print("Fertility: {} uS/cm".format(conductivity)) + print("Battery: {}%".format(battery)) + + response = table.put_item( + Item={ + 'device': mac_addr, + 'timestamp': arrow.get().naive.isoformat(), + 'data': { + 'temperature': decimal.Decimal('{}'.format(temperature)), + 'battery': decimal.Decimal('{}'.format(battery)), + 'light': decimal.Decimal('{}'.format(light)), + 'moisture': decimal.Decimal('{}'.format(moisture)), + 'conductivity': decimal.Decimal('{}'.format(conductivity)), + }, + 'info': { + 'sensor': 'Xiaomi Mi Flora', + 'firmware': '{}'.format(poller.firmware_version()), + }, + } + ) + return response + + +def mijia(mac_addr, poller): + temperature = poller.parameter_value(MI_TEMPERATURE) + battery = poller.parameter_value(MI_BATTERY) + humidity = poller.parameter_value(MI_HUMIDITY) + firmware = poller.firmware_version() + + print('Mijia {}'.format(mac_addr)) + print("Temperature: {}°C".format(temperature)) + print("Humidity: {}%".format(humidity)) + print("Battery: {}%".format(battery)) + + response = table.put_item( + Item={ + 'device': mac_addr, + 'timestamp': arrow.get().naive.isoformat(), + 'data': { + 'temperature': decimal.Decimal('{}'.format(temperature)), + 'battery': decimal.Decimal('{}'.format(battery)), + 'humidity': decimal.Decimal('{}'.format(humidity)), + }, + 'info': { + 'sensor': 'Mijia', + 'firmware': '{}'.format(firmware), + }, + } + ) + return response + +def save_data(mac_addr, device, poller): + if device == 'flora': + return flowercare(mac_addr, poller) + elif device == 'mijia': + return mijia(mac_addr, poller) + else: + return False diff --git a/read.py b/read.py index 1e6dbcf..79e47af 100644 --- a/read.py +++ b/read.py @@ -1,19 +1,38 @@ -from .mijia.mijia.mijia_poller import MijiaPoller, \ -MI_HUMIDITY, MI_TEMPERATURE, MI_BATTERY -from .miflora.miflora.miflora_poller import MiFloraPoller, \ - MI_CONDUCTIVITY, MI_MOISTURE, MI_LIGHT +from os import sys, path -poller = MiFloraPoller("C4:7C:8D:66:2B:80") +USAGE = ''' +python3 read.py [device] -print("Mi Flora: " + address) -print("Firmware: {}".format(poller.firmware_version())) -print("Name: {}".format(poller.name())) +DEVICE: + flora Mi Flower Care + mijia Mijia Temperature & Humidity sensor +''' +def UsageAndExit(msg): + if msg: + print(msg) + print(USAGE) + sys.exit(0) -poller = MijiaPoller("4C:65:A8:D5:66:D4") +if __name__ == '__main__' and __package__ is None: + sys.path.append(path.dirname(path.dirname(path.abspath(__file__)))) + from dynamo import save_data + argv = sys.argv[1:] + if len(argv) != 2: + UsageAndExit() -print("Mijia: " + address) -print("Firmware: {}".format(poller.firmware_version())) -print("Name: {}".format(poller.name())) + supported_devices = ['flora', 'mijia'] + if argv[0] not in supported_devices: + UsageAndExit("Unsupported devices") + + device, mac_addr = argv + if device == 'flora': + from miflora.miflora.miflora_poller import MiFloraPoller + poller = MiFloraPoller(mac_addr) + elif device == 'mijia': + from mijia.mijia.mijia_poller import MijiaPoller + poller = MijiaPoller(mac_addr) + + save_data(device, poller) diff --git a/requirements.txt b/requirements.txt index 8cfbeb0..79cd9b6 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1 +1,3 @@ bluepy +boto3 +arrow