# Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
from __future__ import annotations

__all__ = ["get_queue_parameter_definitions"]

import yaml

from .. import api
from ._list_apis import _call_paginated_deadline_list_api
from ._session import get_boto3_client
from ..exceptions import DeadlineOperationError
from ..job_bundle.parameters import (
    JobParameter,
    get_ui_control_for_parameter_definition,
    parameter_definition_difference,
    validate_job_parameter,
)
from ..ui._utils import tr


@api.record_function_latency_telemetry_event()
def get_queue_parameter_definitions(
    *, farmId: str, queueId: str, config=None
) -> list[JobParameter]:
    """
    This gets all the queue parameter definitions for the specified [Deadline Cloud queue].

    It does so by getting all the full templates for [queue environments], and then combining
    them equivalently to the Deadline Cloud service logic.

    [Deadline Cloud queue]: https://docs.aws.amazon.com/deadline-cloud/latest/userguide/queues.html
    [queue environments]: https://docs.aws.amazon.com/deadline-cloud/latest/userguide/create-queue-environment.html
    """
    deadline = get_boto3_client("deadline", config=config)
    response = _call_paginated_deadline_list_api(
        deadline.list_queue_environments,
        "environments",
        farmId=farmId,
        queueId=queueId,
    )
    queue_environments = sorted(
        (
            deadline.get_queue_environment(
                farmId=farmId,
                queueId=queueId,
                queueEnvironmentId=queue_env["queueEnvironmentId"],
            )
            for queue_env in response["environments"]
        ),
        key=lambda queue_env: queue_env["priority"],
    )
    queue_environment_templates = [
        yaml.safe_load(queue_env["template"]) for queue_env in queue_environments
    ]

    queue_parameters_definitions: dict[str, JobParameter] = {}
    for template in queue_environment_templates:
        for parameter in template.get("parameterDefinitions", []):
            parameter = validate_job_parameter(parameter, type_required=True, default_required=True)

            # If there is no group label, set it to the name of the Queue Environment
            if not parameter.get("userInterface", {}).get("groupLabel"):
                if "userInterface" not in parameter:
                    parameter["userInterface"] = {
                        "control": get_ui_control_for_parameter_definition(parameter)
                    }
                parameter["userInterface"]["groupLabel"] = tr("Queue Environment: {name}").format(
                    name=template["environment"]["name"]
                )
            existing_parameter = queue_parameters_definitions.get(parameter["name"])
            if existing_parameter:
                differences = parameter_definition_difference(existing_parameter, parameter)
                if differences:
                    raise DeadlineOperationError(
                        f"Job template parameter {parameter['name']} is duplicated across queue environments with mismatched fields:\n"
                        + " ".join(differences)
                    )
            else:
                queue_parameters_definitions[parameter["name"]] = parameter

    return list(queue_parameters_definitions.values())
