# Copyright 2020 The ChromiumOS Authors
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

"""Objects for describing template code to be generated from structured.xml."""

import hashlib
import os
import re
import struct


class Util:
    """Helpers for generating C++."""

    @staticmethod
    def sanitize_name(name):
        return re.sub("[^0-9a-zA-Z_]", "_", name)

    @staticmethod
    def camel_to_snake(name):
        pat = "((?<=[a-z0-9])[A-Z]|(?!^)[A-Z](?=[a-z]))"
        return re.sub(pat, r"_\1", name).lower()

    @staticmethod
    def hash_name(name):
        # This must match the hash function in chromium's
        # //metrics/uploader/metric_hashes.cc. >Q means 8 bytes, big endian.
        name = name.encode("utf-8")
        md5 = hashlib.md5(name)
        return struct.unpack(">Q", md5.digest()[:8])[0]

    @staticmethod
    def event_name_hash(project_name, event_name):
        """Make the name hash for an event.

        This gets uploaded in the StructuredEventProto.event_name_hash field. It
        is the sole means of recording which event from structured.xml a
        StructuredEventProto instance represents.

        To avoid naming collisions, it must contain three pieces of information:
         - the name of the event itself
         - the name of the event's project, to avoid collisions with events of
           the same name in other projects
         - an identifier that this comes from chromeos, to avoid collisions with
           events and projects of the same name defined in chromiumos's
           structured.xml

        This must use sanitized names for the project and event.
        """
        event_name = Util.sanitize_name(event_name)
        project_name = Util.sanitize_name(project_name)
        return Util.hash_name(f"cros::{project_name}::{event_name}")


class FileInfo:
    """Codegen-related info about a file."""

    def __init__(self, dirname, basename):
        self.dirname = dirname
        self.basename = basename
        self.filepath = os.path.join(dirname, basename)

        # This takes the last three components of the filepath for use in the
        # header guard, ie. METRICS_STRUCTURED_STRUCTURED_EVENTS_H_
        relative_path = os.sep.join(self.filepath.split(os.sep)[-3:])
        self.guard_path = Util.sanitize_name(relative_path).upper()


class ProjectInfo:
    """Codegen-related info about a project."""

    def __init__(self, project):
        self.raw_name = project.name
        self.name = Util.sanitize_name(project.name)
        self.namespace = Util.camel_to_snake(self.name)
        self.name_hash = Util.hash_name(self.name)
        self.is_event_sequence = project.is_event_sequence_project

        # Set ID Type.
        if project.id == "uma":
            self.id_type = "kUmaId"
        elif project.id == "per-project":
            self.id_type = "kProjectId"
        elif project.id == "none":
            self.id_type = "kUnidentified"

        # Set the event type.
        if self.is_event_sequence:
            self.event_type = "SEQUENCE"
        else:
            # Set event type. This is inferred by checking all metrics within
            # the project. If any of a project's metrics is a raw string, then
            # it's events are considered raw string events, even if they also
            # contain non-strings.
            self.event_type = "REGULAR"
            for event in project.events:
                for metric in event.metrics:
                    if metric.type == "raw-string":
                        self.event_type = "RAW_STRING"
                        break


class EventInfo:
    """Codegen-related info about an event."""

    def __init__(self, event, project_info):
        self.raw_name = event.name
        self.name = Util.sanitize_name(event.name)
        self.name_hash = Util.event_name_hash(project_info.name, self.name)


class MetricInfo:
    """Codegen-related info about a metric."""

    def __init__(self, metric):
        self.raw_name = metric.name
        self.name = Util.sanitize_name(metric.name)
        self.hash = Util.hash_name(metric.name)
        self.type_name = metric.type

        if metric.type == "hmac-string":
            self.setter_type = "std::string&"
            self.setter = "AddHmacMetric"
            self.getter_type = "std::string"
            self.getter = "GetHmacMetricForTest"
            self.arg_parser = "ParseStringStructuredMetricsArg"
        elif metric.type == "int":
            self.setter_type = "int64_t"
            self.setter = "AddIntMetric"
            self.getter_type = "int64_t"
            self.getter = "GetIntMetricForTest"
            self.arg_parser = "ParseIntStructuredMetricsArg"
        elif metric.type == "raw-string":
            self.setter_type = "std::string&"
            self.setter = "AddRawStringMetric"
            self.getter_type = "std::string"
            self.getter = "GetRawStringMetricForTest"
            self.arg_parser = "ParseStringStructuredMetricsArg"
        elif metric.type == "double":
            self.setter_type = "double"
            self.setter = "AddDoubleMetric"
            self.getter_type = "double"
            self.getter = "GetDoubleMetricForTest"
            self.arg_parser = "ParseDoubleStructuredMetricsArg"
        elif metric.type == "int-array":
            self.setter_type = "std::vector<int64_t>&"
            self.max_size = metric.max_size
            self.setter = "AddIntArrayMetric"
            self.getter_type = "std::vector<int64_t>"
            self.getter = "GetIntArrayMetricForTest"
            self.arg_parser = "ParseIntArrayStructuredMetricsArg"
        else:
            raise ValueError("Invalid metric type.")


class Template:
    """Template for producing code from structured.xml."""

    def __init__(
        self,
        model,
        dirname,
        basename,
        file_template,
        project_template,
        event_template,
        pre_metric_template,
        metric_template,
        array_template,
        is_header,
    ):
        self.model = model
        self.dirname = dirname
        self.basename = basename
        self.file_template = file_template
        self.project_template = project_template
        self.event_template = event_template
        self.pre_metric_template = pre_metric_template
        self.metric_template = metric_template
        self.array_template = array_template
        self.is_header = is_header

    def write_file(self):
        file_info = FileInfo(self.dirname, self.basename)
        with open(file_info.filepath, "w", encoding="utf-8") as f:
            f.write(self._stamp_file(file_info))

    def _stamp_file(self, file_info):
        project_code = "".join(
            self._stamp_project(file_info, p) for p in self.model.projects
        )

        project_names = sorted([p.name for p in self.model.projects])
        project_hashes_list = [
            f"UINT64_C({Util.hash_name(n)})" for n in project_names
        ]
        project_hashes_literal = "{" + ", ".join(project_hashes_list) + "}"

        return self.file_template.format(
            file=file_info,
            project_code=project_code,
            project_hashes=project_hashes_literal,
        )

    def _stamp_project(self, file_info, project):
        project_info = ProjectInfo(project)
        event_code = "".join(
            self._stamp_event(file_info, project_info, event)
            for event in project.events
        )
        return self.project_template.format(
            file=file_info, project=project_info, event_code=event_code
        )

    def _stamp_event(self, file_info, project_info, event):
        event_info = EventInfo(event, project_info)
        if self.is_header:
            metric_code = "".join(
                self._stamp_metric(file_info, event_info, metric)
                for metric in event.metrics
            )
            metric_code += "".join(
                self._stamp_array_metric(file_info, event_info, metric)
                for metric in event.metrics
                if metric.is_array()
            )
        else:
            metric_code = "".join(
                self._stamp_metric(file_info, event_info, metric)
                for metric in event.metrics
                if not metric.is_array()
            )
            metric_code += "".join(
                self._stamp_array_metric(file_info, event_info, metric)
                for metric in event.metrics
                if metric.is_array()
            )

        pre_metric_code = "".join(
            self._stamp_pre_metric(file_info, event_info, metric)
            for metric in event.metrics
        )

        return self.event_template.format(
            file=file_info,
            project=project_info,
            event=event_info,
            pre_metric_code=pre_metric_code,
            metric_code=metric_code,
        )

    def _stamp_pre_metric(self, file_info, event_info, metric):
        return self.pre_metric_template.format(
            file=file_info, event=event_info, metric=MetricInfo(metric)
        )

    def _stamp_metric(self, file_info, event_info, metric):
        return self.metric_template.format(
            file=file_info, event=event_info, metric=MetricInfo(metric)
        )

    def _stamp_array_metric(self, file_info, event_info, metric):
        return self.array_template.format(
            file=file_info, event=event_info, metric=MetricInfo(metric)
        )
