import argparse
import os
import yt.yson as yson
from flask import Flask, request, Response


app = Flask(__name__)


def load_all_rides(path):
    "Load all rides information from easyview files"
    features = {}
    track_points = {}

    for name in os.listdir(path):
        features[name] = {}
        track_points[name] = {}

        with open(os.path.join(path, name), "rb") as f:
            for line in f:
                point = yson.loads(line)
                if "mark_bad" not in point:
                    track_points[name][str(point["feature_id"])] = {
                        "accuracy": float(point["accuracy"]) if point["accuracy"] != "not given" else None,
                        "timestamp": int(point["timestamp"]),
                        "lon": float(point["lon"]),
                        "lat": float(point["lat"]),
                    }
                else:
                    features[name][str(point["feature_id"])] = {
                        "timestamp": float(point["timestamp"]),
                        "bad": False,
                    }

    return features, track_points


@app.route('/mark_bad')
def mark_bad():
    global features
    args = request.args

    source_id = args['source_id']
    date = args['date']

    key = source_id + "_" + date
    feature_id = args['feature_id']
    features[key][feature_id]["bad"] = True

    return Response("updated\n", status=200, headers={"Access-Control-Allow-Origin": "*"})


@app.route('/mark_bad_multiple')
def mark_bad_by_time():
    global features
    args = request.args

    key = args["key"]
    start = int(args["start"])
    end = int(args["end"])
    print(start, end)

    for feature_id in features[key].keys():
        timestamp = features[key][feature_id]["timestamp"]
        if start <= timestamp <= end:
            features[key][feature_id]["bad"] = True

    return Response("updated\n", status=200, headers={"Access-Control-Allow-Origin": "*"})


@app.route('/save_ride')
def save_ride():
    global features, track_points, annotations_path
    args = request.args
    name = args["name"]

    with open(os.path.join(annotations_path, "{name}_features.csv".format(name=name)), "w") as f:
        f.write("id,timestamp,bad\n")
        for i, point in features[name].items():
            f.write("{i},{timestamp},{bad}\n".format(i=i, **point))

    with open(os.path.join(annotations_path, "{name}_track-points.csv".format(name=name)), "w") as f:
        f.write("id,timestamp,lon,lat,accuracy\n")
        for i, point in track_points[name].items():
            f.write("{i},{timestamp},{lon},{lat},{accuracy}\n".format(i=i, **point))

    return Response("saved\n", status=200, headers={"Access-Control-Allow-Origin": "*"})


def main():
    global features, track_points, annotations_path
    parser = argparse.ArgumentParser(description='Run server for feature position annotation')
    parser.add_argument("--easyview_path", help="Path to easyview files", required=True)
    parser.add_argument("--annotations_path", help="Path to folder with annotations", required=True)
    args = parser.parse_args()
    annotations_path = args.annotations_path

    features, track_points = load_all_rides(args.easyview_path)
    print("Loaded all rides")
    app.run(host="::", port=1234)


if __name__ == "__main__":
    main()
