resource "kubernetes_namespace" "sftpgo" {
  metadata {
    name = "sftpgo"
  }
}

resource "kubernetes_manifest" "internal_cert" {
  count = var.tls_enabled ? 1 : 0
  manifest = {
    apiVersion = "cert-manager.io/v1"
    kind       = "Certificate"
    metadata = {
      name      = "internal-cert"
      namespace = kubernetes_namespace.sftpgo.metadata[0].name
    }
    spec = {
      secretName = "internal-cert"
      issuerRef = {
        name = var.issuer
        kind = "ClusterIssuer"
      }
      commonName = var.fqdn
      dnsNames   = [var.fqdn]
    }
  }
}

resource "kubernetes_config_map" "sftpgo" {
  metadata {
    name      = "sftpgo"
    namespace = kubernetes_namespace.sftpgo.metadata[0].name
  }
  data = {
    "sftpgo.json" = local.config
  }
}

resource "kubernetes_secret" "admin_credentials" {
  metadata {
    name      = "admin-credentials"
    namespace = kubernetes_namespace.sftpgo.metadata[0].name
  }
  data = {
    admin_username = var.admin_username
    admin_password = var.admin_password
    smtp_username  = var.smtp_username
    smtp_password  = var.smtp_password
  }
  type = "Opaque"
}

resource "kubernetes_config_map" "object_store_credentials" {
  metadata {
    name      = "nextcloud-object-store-credentials"
    namespace = kubernetes_namespace.sftpgo.metadata[0].name
  }
  data = {
    "credentials" = local.credentials
  }
}

resource "kubernetes_service_account" "sftpgo" {
  metadata {
    name      = "sftpgo-app-sa"
    namespace = kubernetes_namespace.sftpgo.metadata[0].name
  }
  automount_service_account_token = false
}

resource "kubernetes_deployment" "sftpgo" {
  metadata {
    name      = "sftpgo"
    namespace = kubernetes_namespace.sftpgo.metadata[0].name
  }
  spec {
    replicas = 1
    selector {
      match_labels = {
        app = "sftpgo"
      }
    }
    strategy {
      type = "RollingUpdate"
    }
    template {
      metadata {
        labels = {
          app = "sftpgo"
        }
        annotations = {
          "checksum/config"      = local.config_checksum
          "checksum/credentials" = local.credentials_checksum
        }
      }
      spec {
        service_account_name            = kubernetes_service_account.sftpgo.metadata[0].name
        automount_service_account_token = false
        security_context {
          fs_group    = 1000
          run_as_user = 1000
        }
        container {
          name              = "sftpgo"
          image             = "ghcr.io/drakkan/sftpgo:${var.tag}"
          image_pull_policy = "Always"
          args              = ["sftpgo", "serve"]
          env {
            name = "SFTPGO_SMTP__USER"
            value_from {
              secret_key_ref {
                name = kubernetes_secret.admin_credentials.metadata[0].name
                key  = "smtp_username"
              }
            }
          }
          env {
            name = "SFTPGO_SMTP__PASSWORD"
            value_from {
              secret_key_ref {
                name = kubernetes_secret.admin_credentials.metadata[0].name
                key  = "smtp_password"
              }
            }
          }
          env {
            name = "SFTPGO_DEFAULT_ADMIN_USERNAME"
            value_from {
              secret_key_ref {
                name = kubernetes_secret.admin_credentials.metadata[0].name
                key  = "admin_username"
              }
            }
          }
          env {
            name = "SFTPGO_DEFAULT_ADMIN_PASSWORD"
            value_from {
              secret_key_ref {
                name = kubernetes_secret.admin_credentials.metadata[0].name
                key  = "admin_password"
              }
            }
          }
          port {
            container_port = 8081
            name           = "dav"
            protocol       = "TCP"
          }

          port {
            container_port = 8080
            name           = "web"
            protocol       = "TCP"
          }
          port {
            container_port = 10000
            name           = "telemetry"
            protocol       = "TCP"
          }
          liveness_probe {
            http_get {
              path = "/healthz"
              port = "telemetry"
            }
          }
          readiness_probe {
            http_get {
              path = "/healthz"
              port = "telemetry"
            }
          }
          volume_mount {
            mount_path = "/etc/sftpgo/sftpgo.json"
            name       = "config"
            sub_path   = "sftpgo.json"
            read_only  = true
          }
          volume_mount {
            mount_path = "/var/lib/sftpgo"
            name       = "data"
          }
          volume_mount {
            mount_path = "/var/lib/sftpgo/backup"
            name       = "backup"
          }
          volume_mount {
            mount_path = "/var/lib/sftpgo/.aws/credentials"
            name       = "object-store-credentials"
            sub_path   = "credentials"
            read_only  = true
          }
          dynamic "volume_mount" {
            for_each = var.tls_enabled ? [1] : []
            content {
              mount_path = "/etc/ssl/certs/private"
              name       = "internal-cert"
              read_only  = true
            }
          }
        }
        volume {
          name = "config"
          config_map {
            name = kubernetes_config_map.sftpgo.metadata[0].name
          }
        }
        volume {
          name = "data"
          host_path {
            path = local.data_path
          }
        }
        volume {
          name = "backup"
          host_path {
            path = var.backup_folder
          }
        }
        volume {
          name = "object-store-credentials"
          config_map {
            name = kubernetes_config_map.object_store_credentials.metadata[0].name
          }
        }
        dynamic "volume" {
          for_each = var.tls_enabled ? [1] : []
          content {
            name = "internal-cert"
            secret {
              secret_name = kubernetes_manifest.internal_cert[0].manifest["metadata"]["name"]
            }
          }
        }
      }
    }
  }
}

resource "kubernetes_service" "sftpgo_webdav" {
  metadata {
    name      = "webdav"
    namespace = kubernetes_namespace.sftpgo.metadata[0].name
  }
  spec {
    selector = {
      app = "sftpgo"
    }
    port {
      name        = var.tls_enabled ? "davs" : "dav"
      protocol    = "TCP"
      port        = var.tls_enabled ? 443 : 80
      target_port = "dav"
    }
    cluster_ip = "None"
  }
}

resource "kubernetes_service" "sftpgo_web" {
  metadata {
    name      = "web"
    namespace = kubernetes_namespace.sftpgo.metadata[0].name
  }
  spec {
    selector = {
      app = "sftpgo"
    }
    port {
      protocol    = "TCP"
      port        = var.tls_enabled ? 443 : 80
      target_port = "web"
    }
    type = "ClusterIP"
  }
}
