from collections.abc import Awaitable, Callable, Sequence
from typing import Any, ClassVar

from temporalio import activity, workflow

from csirtmu.beta_temporal.config import AppConfig
from csirtmu.beta_temporal.constants import WorkflowReference
from csirtmu.beta_temporal.external_services.rt import structs
from csirtmu.beta_temporal.external_services.rt.client import RTClient
from csirtmu.beta_temporal.workflows.logging import LoggedActivities, LoggedWorkflow


class SetCustomFieldsOnCreateActivities(LoggedActivities):
    HEADERS: ClassVar = [
        "From",
        "Reply-To",
        "X-Muni-Envelope-From",
        "X-Muni-O365-Test",
        "X-Muni-Envelope-To",
        "To",
        "X-Get-Message-Sender-Via",
        "X-Authenticated-Sender",
        "Disposition-Notification-To",
        "X-RT-Original-Requestor",
    ]

    def __init__(self, rt_client: RTClient) -> None:
        self.rt_client = rt_client

    def get_activities(self) -> Sequence[Callable[..., Any]]:
        return [self.set_custom_fields]

    @activity.defn
    async def set_custom_fields(self, transaction: structs.TransactionStruct) -> None:
        self.log_activity()
        if transaction.ticket_obj is None:
            return
        if (ticket_data := self.rt_client.get_ticket_data(transaction)) is None:
            return
        custom_fields = {}
        for header in self.HEADERS:
            if header in ticket_data.headers:
                custom_fields[header] = ticket_data.headers[header]
        self.rt_client.edit_ticket(transaction.ticket_obj.id, CustomFields=custom_fields)


class SetCustomFieldsOnCreate(LoggedWorkflow, workflow_name=WorkflowReference.SET_CUSTOM_FIELDS_ON_CREATE):
    @classmethod
    def get_activities(cls) -> Sequence[Callable[..., Awaitable[Any]]]:
        config = AppConfig.get()
        return SetCustomFieldsOnCreateActivities(RTClient(config.rt)).get_activities()

    @workflow.run
    async def run(self, transaction: structs.TransactionStruct) -> None:
        self.log_workflow()
        config = AppConfig.get()
        await workflow.execute_activity(
            SetCustomFieldsOnCreateActivities.set_custom_fields,
            args=(transaction,),
            retry_policy=config.temporal.retry_policy,
            start_to_close_timeout=config.temporal.activity_timeout,
        )
