package grpcli

import (
	"context"
	"net/http"
	"strings"

	service_config "github.com/tidbcloud/dataflow-service-ng/internal/config"
	"github.com/tidbcloud/dataflow-service-ng/pkg/grpc/grpcli/portforward"
	"go.uber.org/zap"
	"google.golang.org/api/googleapi"
	"google.golang.org/grpc"
	"k8s.io/client-go/kubernetes"
	"k8s.io/client-go/tools/clientcmd"

	"github.com/sercand/kuberesolver/v5"
	"github.com/tidbcloud/dataflow-service-ng/pkg/log"
	tigrpc "github.com/tidbcloud/tiinf/transport/tigrpc/client"
)

func MustBuildGrpcClientConnection(ctx context.Context, addr string) *grpc.ClientConn {
	logger := log.GetLogger(ctx)
	opts := []tigrpc.Option{tigrpc.WithDefault()}
	if strings.HasPrefix(addr, "kubernetes:///") {
		debugCfg := service_config.Global().DebugConfig
		if debugCfg.Enable {
			config, err := clientcmd.BuildConfigFromFlags("", debugCfg.InfraConfig)
			if err != nil {
				logger.Fatal("initialize kubeconfig failed", zap.Error(err))
			}
			clientSet, err := kubernetes.NewForConfig(config)
			if err != nil {
				logger.Fatal("initialize kube client failed", zap.Error(err))
			}
			portforward.RegisterClusterWithSchema(clientSet, config, "kubernetes")
		} else {
			kuberesolver.RegisterInCluster()
			opts = append(opts, tigrpc.WithLoadBalance())
		}
	}
	logger.Info("initializing client", zap.String("addr", addr))
	conn, err := tigrpc.NewClientConn(addr, opts...)
	if err != nil {
		logger.Fatal("initialize client failed", zap.String("addr", addr), zap.Error(err))
	}
	return conn
}

func IsNotFound(err error) bool {
	if err == nil {
		return false
	}
	ae, ok := err.(*googleapi.Error)
	return ok && ae.Code == http.StatusNotFound
}
