"""Scribe Uploader for Pytorch Benchmark Data

Currently supports data in pytest-benchmark format but can be extended.

New fields can be added just by modifying the schema in this file, schema
checking is only here to encourage reusing existing fields and avoiding typos.
"""

import argparse
import json
import os
import subprocess
import time
from collections import defaultdict

import requests


class ScribeUploader:
    def __init__(self, category):
        self.category = category

    def format_message(self, field_dict):
        assert "time" in field_dict, "Missing required Scribe field 'time'"
        message = defaultdict(dict)
        for field, value in field_dict.items():
            if field in self.schema["normal"]:
                message["normal"][field] = str(value)
            elif field in self.schema["int"]:
                message["int"][field] = int(value)
            elif field in self.schema["float"]:
                message["float"][field] = float(value)
            else:
                raise ValueError(
                    f"Field {field} is not currently used, be intentional about adding new fields"
                )
        return message

    def _upload_intern(self, messages):
        for m in messages:
            json_str = json.dumps(m)
            cmd = ["scribe_cat", self.category, json_str]
            subprocess.run(cmd)

    def upload(self, messages):
        if os.environ.get("SCRIBE_INTERN"):
            return self._upload_intern(messages)
        access_token = os.environ.get("SCRIBE_GRAPHQL_ACCESS_TOKEN")
        if not access_token:
            raise ValueError("Can't find access token from environment variable")
        url = "https://graph.facebook.com/scribe_logs"
        r = requests.post(
            url,
            data={
                "access_token": access_token,
                "logs": json.dumps(
                    [
                        {
                            "category": self.category,
                            "message": json.dumps(message),
                            "line_escape": False,
                        }
                        for message in messages
                    ]
                ),
            },
        )
        print(r.text)
        r.raise_for_status()


class PytorchBenchmarkUploader(ScribeUploader):
    def __init__(self):
        super().__init__("perfpipe_pytorch_benchmarks")
        self.schema = {
            "int": [
                "time",
                "rounds",
            ],
            "normal": [
                "benchmark_group",
                "benchmark_name",
                "benchmark_executor",
                "benchmark_fuser",
                "benchmark_class",
                "benchmark_time",
                "pytorch_commit_id",
                "pytorch_branch",
                "pytorch_commit_time",
                "pytorch_version",
                "pytorch_git_dirty",
                "machine_kernel",
                "machine_processor",
                "machine_hostname",
                "circle_build_num",
                "circle_project_reponame",
            ],
            "float": [
                "stddev",
                "min",
                "median",
                "max",
                "mean",
            ],
        }

    def post_pytest_benchmarks(self, pytest_json):
        machine_info = pytest_json["machine_info"]
        commit_info = pytest_json["commit_info"]
        upload_time = int(time.time())
        messages = []
        for b in pytest_json["benchmarks"]:
            test = b["name"].split("[")[0]
            net_name = b["params"]["net_name"]
            benchmark_name = f"{test}[{net_name}]"
            executor = b["params"]["executor"]
            fuser = b["params"]["fuser"]
            m = self.format_message(
                {
                    "time": upload_time,
                    "benchmark_group": b["group"],
                    "benchmark_name": benchmark_name,
                    "benchmark_executor": executor,
                    "benchmark_fuser": fuser,
                    "benchmark_class": b["fullname"],
                    "benchmark_time": pytest_json["datetime"],
                    "pytorch_commit_id": commit_info["id"],
                    "pytorch_branch": commit_info["branch"],
                    "pytorch_commit_time": commit_info["time"],
                    "pytorch_version": None,
                    "pytorch_git_dirty": commit_info["dirty"],
                    "machine_kernel": machine_info["release"],
                    "machine_processor": machine_info["processor"],
                    "machine_hostname": machine_info["node"],
                    "circle_build_num": os.environ.get("CIRCLE_BUILD_NUM"),
                    "circle_project_reponame": os.environ.get(
                        "CIRCLE_PROJECT_REPONAME"
                    ),
                    "stddev": b["stats"]["stddev"],
                    "rounds": b["stats"]["rounds"],
                    "min": b["stats"]["min"],
                    "median": b["stats"]["median"],
                    "max": b["stats"]["max"],
                    "mean": b["stats"]["mean"],
                }
            )
            messages.append(m)
        self.upload(messages)


if __name__ == "__main__":
    parser = argparse.ArgumentParser(description=__doc__)
    parser.add_argument(
        "--pytest-bench-json",
        "--pytest_bench_json",
        type=argparse.FileType("r"),
        help="Upload json data formatted by pytest-benchmark module",
    )
    args = parser.parse_args()
    if args.pytest_bench_json:
        benchmark_uploader = PytorchBenchmarkUploader()
        json_data = json.load(args.pytest_bench_json)
        benchmark_uploader.post_pytest_benchmarks(json_data)
