using Health.Domain;
using Health.Domain.Enums;

namespace Health.Application.HealthRecords;

public static class HealthRecordRules
{
    public static bool CheckAbnormal(HealthRecordUpsertRequest request) => request.Type switch
    {
        HealthMetricType.BloodPressure => request.Systolic >= 140 || request.Diastolic >= 90 || request.Systolic <= 89 || request.Diastolic <= 59,
        HealthMetricType.HeartRate => request.Value > 100 || request.Value < 60,
        HealthMetricType.Glucose => request.Value > 6.1m || request.Value < 3.9m,
        HealthMetricType.SpO2 => request.Value <= 94,
        HealthMetricType.Weight => false,
        _ => false
    };

    /// <summary>
    /// 合法性校验——拦截物理上不可能的数值（负数、超量程等），不合法即抛 ValidationException。
    /// 注意：这与 CheckAbnormal（医学异常预警）是两回事，前者拦脏数据，后者只是标记偏离正常范围。
    /// </summary>
    public static void Validate(HealthRecordUpsertRequest request)
    {
        switch (request.Type)
        {
            case HealthMetricType.BloodPressure:
                var sys = Required(request.Systolic, "收缩压");
                var dia = Required(request.Diastolic, "舒张压");
                InRange(sys, 40, 300, "收缩压", "mmHg");
                InRange(dia, 20, 250, "舒张压", "mmHg");
                if (sys <= dia)
                    throw new ValidationException("收缩压必须大于舒张压");
                break;
            case HealthMetricType.HeartRate:
                InRange(Required(request.Value, "心率"), 20m, 300m, "心率", "次/分");
                break;
            case HealthMetricType.Glucose:
                InRange(Required(request.Value, "血糖"), 0.5m, 60m, "血糖", "mmol/L");
                break;
            case HealthMetricType.SpO2:
                InRange(Required(request.Value, "血氧"), 50m, 100m, "血氧", "%");
                break;
            case HealthMetricType.Weight:
                InRange(Required(request.Value, "体重"), 1m, 500m, "体重", "kg");
                break;
        }
    }

    private static int Required(int? value, string field) =>
        value ?? throw new ValidationException($"{field}不能为空");

    private static decimal Required(decimal? value, string field) =>
        value ?? throw new ValidationException($"{field}不能为空");

    private static void InRange(decimal value, decimal min, decimal max, string field, string unit)
    {
        if (value < min || value > max)
            throw new ValidationException($"{field}应在 {min}~{max} {unit} 之间，当前值 {value} 不合理");
    }
}
