use serde::{Deserialize, Serialize};

#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Serialize, Deserialize)]
#[serde(rename_all = "lowercase")]
pub enum Tier {
    Free,
    Beacon,
    Studio,
    Enterprise,
}

impl Tier {
    pub fn parse_tier(s: &str) -> Self {
        match s {
            "beacon" => Tier::Beacon,
            "studio" => Tier::Studio,
            "enterprise" => Tier::Enterprise,
            _ => Tier::Free,
        }
    }

    pub fn vault_fact_limit(&self) -> Option<usize> {
        match self {
            Tier::Free => Some(500),
            Tier::Beacon => Some(10_000),
            Tier::Studio | Tier::Enterprise => None,
        }
    }

    pub fn cloud_token_quota(&self) -> Option<u64> {
        match self {
            Tier::Free => None,
            Tier::Beacon => Some(100_000),
            Tier::Studio => Some(1_000_000),
            Tier::Enterprise => None,
        }
    }

    pub fn cloud_sync_enabled(&self) -> bool {
        matches!(self, Tier::Beacon | Tier::Studio | Tier::Enterprise)
    }

    pub fn team_vault_enabled(&self) -> bool {
        matches!(self, Tier::Studio | Tier::Enterprise)
    }

    pub fn upgrade_url(&self) -> &'static str {
        "https://betterctx.com/upgrade"
    }
}

/// Check whether the current tier allows an action and return an upgrade prompt if not.
pub fn gate(tier: &Tier, required: &Tier, feature: &str) -> Result<(), String> {
    if tier >= required {
        Ok(())
    } else {
        Err(format!(
            "{feature} requires the {required:?} tier. Upgrade at {}",
            tier.upgrade_url()
        ))
    }
}
