#!/usr/bin/python3

import hmac
import json
import os
import pprint
import random
import socket
import subprocess
import time

import requests


# Use a whitelist since there are a lot of uninteresting file system
# types on modern linux systems
interesting_fstypes = {"ext4", "tmpfs", "vfat"}

# It's a bit weird that this works.
hostname = socket.gethostbyaddr(socket.gethostname())[0]


now = time.time()

report = []
with open("/proc/mounts") as mfh:
    for ln in mfh:
        (dev, mountpoint, fstype, options, _, _) = ln.split()
        if fstype not in interesting_fstypes:
            continue

        try:
            with open(mountpoint + "/.writable", "w") as fh:
                fh.write("w")
            writable = 1
        except PermissionError as e:
            # Pilot error
            writable = 0
        except OSError as e:
            # Check for e.errno == 30?
            # Nope, any error means that we can't write.
            writable = 0

        report.append(
            {
                "description": {
                    "hostname": hostname,
                    "mountpoint": mountpoint,
                    "measure": "writable",
                    "unit": "bool",
                },
                "data": [
                    [now, writable]
                ]
            }
        )

for dir in (".", os.environ["HOME"] + "/.config/ltsdb", "/etc/ltsdb"):
    try:
        with open(dir + "/config.json") as fh:
            client_config = json.load(fh)
        baseurl = client_config["server"]
        break
    except FileNotFoundError:
        pass
while True:
    for r in report:
        node = hostname
        timestamp = time.time()
        msg = (node + " " + str(timestamp)).encode("UTF-8")
        digest = hmac.new(client_config["key"].encode("UTF-8"), msg, "SHA256").hexdigest()
        r["auth"] = {
            "node": node,
            "timestamp": timestamp,
            "hmac": digest,
        }
    #pprint.pp(report)
    r = requests.post(baseurl + "report", json=report)
    print(r)
    if r.status_code == 200:
        exit(0)
    elif r.status_code == 409:
        time.sleep(0.5 + random.random())
        continue
    else:
        exit(1)