"""
仓位计算模块

核心公式：
仓位(保证金) = 风险金额 ÷ (止损距离 × 杠杆)
名义持仓 = 保证金 × 杠杆
"""

from ..config import settings as S
from ..config.coins import get_coin


def calc_effective_equity(balance: float, month_start_balance: float) -> float:
    """
    有效权益 = min(实际余额, 月初余额 × 3)
    防暴涨后重仓回吐
    """
    return min(balance, month_start_balance * S.EFFECTIVE_EQUITY_MULTIPLIER)


def calc_position(
    equity: float,
    sl_distance: float,
    coin: str,
    signal_type: str,
    leverage: int,
    position_mult: float = 1.0,
    cross_resonance: bool = False,
    used_margin: float = 0.0,
) -> dict:
    """
    完整仓位计算

    Args:
        equity: 有效权益
        sl_distance: 止损距离（百分比，如0.015=1.5%）
        coin: 币种
        signal_type: '共振', '日线', '4H', '做空'
        leverage: 杠杆倍数
        position_mult: 过滤层的仓位调整因子
        cross_resonance: 是否有跨币共振
        used_margin: 已使用保证金

    Returns:
        dict with margin, notional, risk_amount, etc.
    """
    cfg = get_coin(coin)

    # 1. 单笔风险金额
    risk_pct = S.get_risk_per_trade(equity)
    risk_amount = equity * risk_pct

    # 2. 基础保证金
    if sl_distance <= 0:
        return _zero_position("止损距离<=0")

    margin = risk_amount / (sl_distance * leverage)

    # 3. 信号类型仓位上限
    type_limit = S.POSITION_LIMIT.get(signal_type, 0.30)
    max_margin_by_type = equity * type_limit
    margin = min(margin, max_margin_by_type)

    # 4. 仓位调整因子
    margin *= position_mult

    # 5. 跨币共振加仓
    if cross_resonance:
        _, mult, cap = S.ADJ_CROSS_RESONANCE
        margin = min(margin, equity * cap)

    # 6. 单币上限
    margin = min(margin, equity * S.SINGLE_COIN_LIMIT)

    # 7. 总仓位上限
    available = equity * S.TOTAL_POSITION_LIMIT - used_margin
    if available <= 0:
        return _zero_position("总仓位已满")
    margin = min(margin, available)

    # 8. 名义持仓
    notional = margin * leverage

    # 9. 流动性上限
    notional = min(notional, cfg.liquidity_cap)
    margin = notional / leverage

    # 10. 最终保证金不能为负
    if margin <= 0:
        return _zero_position("保证金<=0")

    return {
        'margin': margin,
        'notional': notional,
        'risk_amount': risk_amount,
        'risk_pct': risk_pct,
        'leverage': leverage,
        'position_pct': margin / equity if equity > 0 else 0,
        'skip': False,
        'skip_reason': '',
    }


def _zero_position(reason: str) -> dict:
    return {
        'margin': 0,
        'notional': 0,
        'risk_amount': 0,
        'risk_pct': 0,
        'leverage': 0,
        'position_pct': 0,
        'skip': True,
        'skip_reason': reason,
    }
