package cluster

import (
	alpha1 "github.com/pingcap/tidb-operator/pkg/apis/pingcap/v1alpha1"
	agentv1 "github.com/tidbcloud/observability/agent-control-server/api/v1"

	cloudv1 "github.com/tidbcloud/infra-api/api/v1"
	"github.com/tidbcloud/infra-provider/pkg/controllers/utils"
	"github.com/tidbcloud/infra-provider/pkg/gitops"
)

func BuildClusterTopology(topology cloudv1.ClusterTopology, provider gitops.Provider) (*agentv1.ClusterTopologyType, error) {
	var clusterTopology agentv1.ClusterTopologyType

	instance, err := provider.FindInstanceType(topology.PD.InstanceType)
	if err != nil {
		return nil, err
	}
	clusterTopology.PD.Replicas = topology.PD.Replicas
	clusterTopology.PD.CPU = instance.CPU
	clusterTopology.PD.Memory = instance.Memory

	instance, err = provider.FindInstanceType(topology.TiDB.InstanceType)
	if err != nil {
		return nil, err
	}
	clusterTopology.TiDB.Replicas = topology.TiDB.Replicas
	clusterTopology.TiDB.CPU = instance.CPU
	clusterTopology.TiDB.Memory = instance.Memory

	instance, err = provider.FindInstanceType(topology.TiKV.InstanceType)
	if err != nil {
		return nil, err
	}
	clusterTopology.TiKV.Replicas = topology.TiKV.Replicas
	clusterTopology.TiKV.CPU = instance.CPU
	clusterTopology.TiKV.Memory = instance.Memory

	if topology.TiFlash.Replicas > 0 {
		instance, err = provider.FindInstanceType(topology.TiFlash.InstanceType)
		if err != nil {
			return nil, err
		}
		clusterTopology.TiFlash.Replicas = topology.TiFlash.Replicas
		clusterTopology.TiFlash.CPU = instance.CPU
		clusterTopology.TiFlash.Memory = instance.Memory
	}

	return &clusterTopology, nil
}

func TiDBClusterPaused(cluster *cloudv1.Cluster, tidbcluster *alpha1.TidbCluster) bool {
	sa := cluster.Spec.Cluster.SuspendAction
	if sa == nil || !sa.SuspendCompute {
		return false
	}

	return allComponentsPaused(cluster, tidbcluster)
}

// allComponentsPaused checks if all components in TiDB Cluster are paused
func allComponentsPaused(cluster *cloudv1.Cluster, tidbcluster *alpha1.TidbCluster) bool {
	componentTemplates := cluster.GetComponents()
	for _, componentTemplate := range componentTemplates {
		ct := componentTemplate.GetComponentType()
		memberType := utils.GetMemberType(ct)
		if !tidbcluster.ComponentIsSuspended(memberType) {
			return false
		}
	}
	return true
}
