use std::{collections::HashMap, str::FromStr};

use non_blank_string_rs::NonBlankString;

use crate::modules::helm::chart::HelmChartScore;

use super::config::KubePrometheusConfig;

pub fn kube_prometheus_score(config: KubePrometheusConfig) -> HelmChartScore {
    //TODO this should be make into a rule with default formatting that can be easily passed as a vec
    //to the overrides or something leaving the user to deal with formatting here seems bad
    let values = r#"
additionalPrometheusRulesMap:
  pvc-alerts:
    groups:
      - name: pvc-alerts
        rules:
          - alert: 'PVC Fill Over 95 Percent In 2 Days'
            expr: |
              (
                kubelet_volume_stats_used_bytes 
                / 
                kubelet_volume_stats_capacity_bytes
              ) > 0.95
              AND
              predict_linear(kubelet_volume_stats_used_bytes[2d], 2 * 24 * 60 * 60)
              / 
              kubelet_volume_stats_capacity_bytes 
              > 0.95
            for: 1m
            labels:
              severity: warning
            annotations:
              description: The PVC {{ $labels.persistentvolumeclaim }} in namespace {{ $labels.namespace }} is predicted to fill over 95% in less than 2 days.
              title: PVC {{ $labels.persistentvolumeclaim }} in namespace {{ $labels.namespace }} will fill over 95% in less than 2 days
"#;
    let mut values_overrides: HashMap<NonBlankString, String> = HashMap::new();


    macro_rules! insert_flag {
        ($key:expr, $val:expr) => {
            values_overrides.insert(NonBlankString::from_str($key).unwrap(), $val.to_string());
        };
    }

    insert_flag!("nodeExporter.enabled", config.node_exporter);
    insert_flag!("windowsMonitoring.enabled", config.windows_monitoring);
    insert_flag!("grafana.enabled", config.grafana);
    insert_flag!("alertmanager.enabled", config.alert_manager);
    insert_flag!("prometheus.enabled", config.prometheus);
    insert_flag!("kubernetes_service_monitors.enabled", config.kubernetes_service_monitors);
    insert_flag!("kubelet.enabled", config.kubelet);
    insert_flag!("kubeControllerManager.enabled", config.kube_controller_manager);
    insert_flag!("kubeProxy.enabled", config.kube_proxy);
    insert_flag!("kubeEtcd.enabled", config.kube_etcd);
    insert_flag!("kubeStateMetrics.enabled", config.kube_state_metrics);
    insert_flag!("prometheusOperator.enabled", config.prometheus_operator);

    
    HelmChartScore {
        namespace: Some(NonBlankString::from_str(&config.namespace).unwrap()),
        release_name: NonBlankString::from_str("kube-prometheus").unwrap(),
        chart_name: NonBlankString::from_str(
            "oci://ghcr.io/prometheus-community/charts/kube-prometheus-stack", //use kube prometheus chart which includes grafana, prometheus, alert
                                                                               //manager, etc
        )
        .unwrap(),
        chart_version: None,
        values_overrides: Some(values_overrides),
        values_yaml: Some(values.to_string()),
        create_namespace: true,
        install_only: true,
        repository: None,
    }
}
