"""
DSP系统MCP工具 - 提供与DSP业务系统交互的MCP工具
"""
from typing import Dict, Any, Optional, List
from loguru import logger

from mcp_framework.mcp_tools import mcp
from mcp_framework.business.market import accounts as accounts_api
from mcp_framework.business.plans import plans as plans_api
from mcp_framework.business.flow import flow as flow_api
from mcp_framework.business.project import config as project_api


# @mcp.tool()
# async def get_marketing_plans(
#     account_id: Optional[str] = None, 
#     page: int = 1, 
#     page_size: int = 10,
#     status: Optional[str] = None
# ) -> Dict[str, Any]:
#     """获取营销计划列表
    
#     Args:
#         account_id: 账户ID（可选，不提供则获取所有账户的计划）
#         page: 页码，默认1
#         page_size: 每页记录数，默认10
#         status: 计划状态（可选，如"active"、"paused"等）
        
#     Returns:
#         计划列表数据
#     """
#     filter_params = {}
#     if status:
#         filter_params["status"] = status
        
#     result = await plans_api.get_plan_list(account_id, page, page_size, filter_params)
#     return result

@mcp.tool()
async def get_plan_detail(plan_id: str) -> Dict[str, Any]:
    """计划元数据信息 - 获取营销计划详细配置信息
    
    Args:
        plan_id: 计划ID
        
    Returns:
        计划详细配置数据，包含以下字段：
        
        基本信息：
        - id: 计划ID
        - masterId: 投放账户ID
        - campaignId: 活动ID
        - planName: 计划名称
        - planMode: 计划类型，1表示普通计划
        - planStatus: 计划状态，2表示开启，3表示关闭，5表示待审核，6表示审核拒绝
        - planStatusDesc: 计划状态的中文描述
        - isDel: 是否删除，0表示未删除，1表示已删除
        - isPlanPut: 计划是否投放，0表示未投放，1表示已投放
        
        投放设置：
        - putCycle: 投放周期类型
        - startDate: 指定周期开始日期（若有）
        - endDate: 指定周期结束日期（若有）
        - hours: 周期小时数据，空表示不限
        - budgetType: 计划目标类型，1表示花费，2表示曝光，3表示点击
        - budgetDay: 预算日预算
        - budgetDaily: 日预算
        - budgetHour: 固定预算小时预算
        - nextBudgetType: 下一预算类型
        - nextBudgetDay: 下一日预算
        - consumeRate: 投放速率，1表示匀速投放，2表示优先跑量
        
        出价信息：
        - bidType: 出价方式，1表示CPM，2表示CPC，3表示OCPM
        - bidPrice: 出价
        - deepBidStatus: 深度出价类型，0表示关闭，1表示开启
        - deepBidAction: 深度出价优化目标
        - deepBidType: 深度出价类型
        - deepBidPrice: 深度出价价格
        - bidAlgoType: 竞价分布算法出价类型，1表示稳定成本，2表示最优成本，3表示均衡模式
        - hourBidPrice: 小时出价
        - isDynamicCpcPrice: 是否开启pid动态调价
        
        定向设置：
        - osType: 操作系统，1表示Android，2表示iOS，3表示所有
        - osTypeDesc: 操作系统的中文描述
        - slotType: 广告形式，数值对应不同的广告形式
        - slotTypeDesc: 广告形式的中文描述
        - slotTypes: 计划广告形式多选
        - areaCountry: 指定国家
        - crowdLabel: 指定人群包
        - industryId: 行业ID
        - industryName: 行业名称
        - adxId: ADX ID
        - epId: EP ID
        - media: 媒体定向
        - slot: 广告位定向
        - packageName: 包名定向
        - rtaStrategy: RTA策略
        - flowType: 流量类型
        - deviceBrand: 设备品牌定向
        - devicePrice: 设备价格定向
        - deviceReleaseDate: 设备发布日期
        - ssp: SSP定向
        
        监测设置：
        - monitorId: 监测站点ID
        - monitorName: 监测站点名称
        - monitorViewUrl1: 第三方曝光监测1
        - monitorViewUrl2: 第三方曝光监测2
        - monitorClickUrl1: 第三方点击监测1
        - monitorClickUrl2: 第三方点击监测2
        - landingUrl: 落地页URL
        - deeplink: Deeplink链接
        - autoLinkRate: DeepLink自动吊起比例（0-100）
        - isDeeplink: 是否支持deeplink
        - trackingGroup: Tracking组定向
        
        频次控制：
        - frequencyNumView: 曝光频次限制
        - frequencyCycleView: 曝光频次限制周期
        - frequencyNumClick: 点击频次限制
        - frequencyCycleClick: 点击频次限制周期
        
        优化设置：
        - optimizeTargetId: 优化目标ID
        - optimizeTargetName: 优化目标名称
        - isOptimizeMediaBudget: 媒体预算优化，0表示关闭，1表示开启
        - flowDetectionState: 流量探测开关，0表示关闭，1表示开启
        - learningState: 学习期状态
        - learningLength: 学习期时长（天）
        - budgetLearningRate: 学习期预算比例
        - monitorIndex: 过滤转化用户
        - antiFraud: 反作弊策略
        
        Deal设置：
        - dealType: Deal类型
        - dealId: Deal ID
        - returnRatio: 返量比例
        
        创意设置：
        - templateId: JS模板ID
        - behaviorAppId: 行为应用ID
        - behaviorAppName: 行为应用名称
        - dpaState: 是否支持DPA，0表示不支持，1表示支持
        
        实验设置：
        - isAbPlan: 是否AB实验计划，0表示否，1表示是
        - shadowPlanId: 影子计划ID
        
        注：具体字段的可用性取决于后端API返回的数据结构，部分字段可能不存在
    """
    result = await plans_api.get_plan_info(plan_id)
    
    # 处理返回结果，确保能正确呈现
    if result.get("success") and result.get("data"):
        # 如果需要，此处可以添加字段格式化或说明
        plan_data = result["data"]
        
        # 添加计划状态说明
        status_map = {
            1: "待投放",
            2: "投放中",
            3: "暂停", 
            4: "投放结束"
        }
        
        if "planStatus" in plan_data and plan_data["planStatus"] in status_map:
            plan_data["planStatusDesc"] = status_map[plan_data["planStatus"]]
            
        # 添加广告形式说明
        slot_type_map = {
            100: "横幅",
            200: "开屏",
            300: "信息流",
            400: "视频",
            500: "ICON",
            600: "Push",
            700: "插屏"
        }
        
        if "slotType" in plan_data and plan_data["slotType"] in slot_type_map:
            plan_data["slotTypeDesc"] = slot_type_map[plan_data["slotType"]]
            
        # 添加操作系统说明
        os_type_map = {
            0: "所有",
            1: "iOS",
            2: "Android", 
        }
        
        if "osType" in plan_data and plan_data["osType"] in os_type_map:
            plan_data["osTypeDesc"] = os_type_map[plan_data["osType"]]
    
    return result

@mcp.tool()
async def get_plan_project_map(plan_id: int) -> Dict[str, Any]:
    """项目元数据信息 - 获取计划对应的项目ID和名称
    
    该接口用于查询广告计划所属的项目信息，在DSP系统中，项目是一个重要的业务概念，
    它定义了一组相关计划的共同配置和业务规则，包括自定义指标、优化目标和数据分析维度。
    
    在实际应用中，该接口的主要用途包括：
    1. 确定计划所属的业务项目，进行分类管理
    2. 获取项目ID后，进一步查询项目的特定配置（如自定义指标）
    3. 在多项目环境中，识别计划的业务归属
    4. 辅助多维分析，按项目维度统计数据
    
    典型的使用场景是与get_project_custom_index配合使用，先获取计划所属项目ID，
    再查询该项目的自定义指标配置，用于后续的数据分析和报表生成。
    
    Args:
        plan_id: 计划ID
        
    Returns:
        计划与项目的映射关系数据，包含以下字段：
        
        - id: 计划ID，标识查询的计划
        - masterId: 广告主ID，该计划所属的广告主
        - planName: 计划名称，方便用户识别
        - projectId: 项目ID，该计划所属的项目标识
        - projectName: 项目名称，如"lazada-rta"，表示项目业务含义
        - identify: 项目标识，用于区分不同的项目，主要用于各个数据接口的参数
        - timeZone: 项目的投放时区信息，对于一些报表接口，该参数十分重要

    """
    result = await project_api.get_plan_project_map(plan_id)
    return result


# @mcp.tool()
# async def get_project_custom_index(project_id: int) -> Dict[str, Any]:
#     """项目元数据信息 - 获取项目设置的计算指标数据
    
#     该接口用于获取项目中配置的所有自定义指标，包括基础指标、计算指标和行为指标。
#     这些指标配置是项目级别的，可用于多维分析报表、数据过滤和自定义统计。
    
#     在实际应用中，这些指标可用于：
#     1. 构建自定义分析报表，展示特定的业务KPI
#     2. 在计划优化时，评估各种转化行为的表现
#     3. 计算ROI、ROAS等复合指标
#     4. 数据可视化展示，让用户更好地理解广告效果
    
#     通常与get_plan_project_map配合使用，先获取计划所属项目，再查询该项目的指标配置。
    
#     Args:
#         project_id: 项目ID
        
#     Returns:
#         项目自定义指标配置数据，包含以下字段：
        
#         - actionDIndex: 延迟行为序号，如12，用于标识延迟转化行为
#         - actionIndex: 行为序号，如50，用于标识即时转化行为
#         - id: 项目ID
        
#         - actionFields: 行为字段列表，每项包含：
#           * key: 字段标识，如"bid"、"win"、"view"等
#           * title: 字段名称，如"竞价量"、"竞得量"、"曝光量"等
#           这些字段用于在报表中展示各种行为指标
        
#         - baseFields: 基础字段列表，每项包含：
#           * key: 字段标识，如"p4pRevenue"、"affi"等
#           * title: 字段名称
#           * action: 对应动作，如"p4pRevenue"表示P4P收入
#           * rAction: 映射的行为字段，如"action"表示激活行为
#           * indexCategory: 指标分类，如"总数类"
#           * isCommon: 是否常用，1表示是
#           * isShow: 是否显示，1表示是
#           这些字段是系统预定义的基础指标，用于常规数据分析
        
#         - computedFields: 计算字段列表，每项包含：
#           * key: 字段标识，如"computed_1737126400853"
#           * title: 字段名称，如"p4p佣金"
#           * field1: 计算字段1，如"p4pRevenue"
#           * field2: 计算字段2，如"rate_1737126396226"
#           * computedType: 计算类型，如"/"表示除法
#           * actionIndex: 对应行为索引，如"actionD11"
#           * indexCategory: 指标分类，如"总数类"
#           * isShow: 是否显示，1表示是
#           * roundVal: 保留小数位数，如2
#           这些字段是用户自定义的复合计算指标，通常用于计算ROI、ROAS等
        
#         - rateFields: 比率字段列表，每项包含：
#           * key: 字段标识，如"rate_1737126396226"
#           * title: 字段值，如"1000000"
#           这些字段用于计算比率指标，例如CPM换算等
#     """
#     result = await project_api.get_project_custom_index(project_id)
#     return result