From 97229d3e8ab357cbd43df16458e46a72689681fd Mon Sep 17 00:00:00 2001 From: powerfool Date: Thu, 18 Apr 2024 22:03:57 +0800 Subject: [PATCH] Fixed Tenant Connection and Node IP Display (#322) --- .../dashboard/business/oceanbase/obcluster.go | 2 +- internal/dashboard/handler/conn_handler.go | 38 ++++++---------- internal/dashboard/handler/helper.go | 44 +++++++++++++++++++ 3 files changed, 58 insertions(+), 26 deletions(-) diff --git a/internal/dashboard/business/oceanbase/obcluster.go b/internal/dashboard/business/oceanbase/obcluster.go index 651dd312a..090af2838 100644 --- a/internal/dashboard/business/oceanbase/obcluster.go +++ b/internal/dashboard/business/oceanbase/obcluster.go @@ -184,7 +184,7 @@ func buildOBClusterTopologyResp(ctx context.Context, obcluster *v1alpha1.OBClust Name: observer.Name, Status: convertStatus(observer.Status.Status), StatusDetail: observer.Status.Status, - Address: observer.Status.PodIp, + Address: observer.Status.GetConnectAddr(), // TODO: add metrics Metrics: nil, }) diff --git a/internal/dashboard/handler/conn_handler.go b/internal/dashboard/handler/conn_handler.go index 1f1721e0e..de45ede56 100644 --- a/internal/dashboard/handler/conn_handler.go +++ b/internal/dashboard/handler/conn_handler.go @@ -20,7 +20,6 @@ import ( "net/http" "os" "strconv" - "strings" "time" "github.com/gin-gonic/gin" @@ -31,7 +30,6 @@ import ( "k8s.io/apimachinery/pkg/types" "k8s.io/apimachinery/pkg/util/rand" - "github.com/oceanbase/ob-operator/api/v1alpha1" "github.com/oceanbase/ob-operator/internal/clients" oceanbaseconst "github.com/oceanbase/ob-operator/internal/const/oceanbase" "github.com/oceanbase/ob-operator/internal/dashboard/business/k8s" @@ -196,35 +194,25 @@ func CreateOBTenantConnTerminal(c *gin.Context) (*response.OBConnection, error) } passwd = string(secret.Data["password"]) } - - obzoneList := &v1alpha1.OBZoneList{} - err = clients.ZoneClient.List(c, nn.Namespace, obzoneList, metav1.ListOptions{ - LabelSelector: oceanbaseconst.LabelRefOBCluster + "=" + obtenant.Spec.ClusterName, - }) + conn := &response.OBConnection{} + obcluster, err := clients.GetOBCluster(c, nn.Namespace, obtenant.Spec.ClusterName) if err != nil { - return nil, httpErr.NewInternal(err.Error()) + return nil, httpErr.NewBadRequest(err.Error()) } - if len(obzoneList.Items) == 0 { - return nil, httpErr.NewBadRequest("no obzone found in obcluster " + obtenant.Spec.ClusterName) + // Select unit information from the oceanbase cluster + db, err := getSysClient(c, obcluster, oceanbaseconst.RootUser, oceanbaseconst.SysTenant, obtenant.Spec.Credentials.Root) + if err != nil { + return nil, httpErr.NewInternal(err.Error()) } - - // get full replica observer - fullReplicaMap := make(map[string]struct{}) - for _, pool := range obtenant.Spec.Pools { - if pool.Type != nil && strings.EqualFold(pool.Type.Name, "Full") { - fullReplicaMap[pool.Zone] = struct{}{} - } + units, err := db.ListUnitsWithTenantId(int64(obtenant.Status.TenantRecordInfo.TenantID)) + if err != nil { + return nil, httpErr.NewInternal(err.Error()) } - conn := &response.OBConnection{} - for _, zone := range obzoneList.Items { - if _, ok := fullReplicaMap[zone.Spec.Topology.Zone]; ok { - if len(zone.Status.OBServerStatus) > 0 { - conn.Host = zone.Status.OBServerStatus[0].Server - break - } - } + if len(units) == 0 { + return nil, httpErr.NewInternal("no unit found in obtenant " + obtenant.Name) } + conn.Host = units[0].SvrIp if conn.Host == "" { return nil, httpErr.NewBadRequest("no full replica observer found in obtenant") diff --git a/internal/dashboard/handler/helper.go b/internal/dashboard/handler/helper.go index 9274006cd..4ac55131c 100644 --- a/internal/dashboard/handler/helper.go +++ b/internal/dashboard/handler/helper.go @@ -13,9 +13,20 @@ See the Mulan PSL v2 for more details. package handler import ( + "context" + + "github.com/go-logr/logr" + "github.com/pkg/errors" logger "github.com/sirupsen/logrus" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "github.com/oceanbase/ob-operator/api/v1alpha1" + "github.com/oceanbase/ob-operator/internal/clients" + oceanbaseconst "github.com/oceanbase/ob-operator/internal/const/oceanbase" "github.com/oceanbase/ob-operator/internal/dashboard/model/param" + "github.com/oceanbase/ob-operator/pkg/k8s/client" + "github.com/oceanbase/ob-operator/pkg/oceanbase-sdk/connector" + "github.com/oceanbase/ob-operator/pkg/oceanbase-sdk/operation" ) func loggingCreateOBClusterParam(param *param.CreateOBClusterParam) { @@ -47,3 +58,36 @@ func loggingCreateOBTenantParam(param *param.CreateOBTenantParam) { WithField("Source", param.Source). Infof("Create OBTenant param") } + +func getSysClient(ctx context.Context, obcluster *v1alpha1.OBCluster, userName, tenantName, secretName string) (*operation.OceanbaseOperationManager, error) { + observerList := &v1alpha1.OBServerList{} + err := clients.ServerClient.List(ctx, obcluster.Namespace, observerList, metav1.ListOptions{ + LabelSelector: oceanbaseconst.LabelRefOBCluster + "=" + obcluster.Name, + }) + if err != nil { + return nil, errors.Wrap(err, "Get observer list") + } + if len(observerList.Items) == 0 { + return nil, errors.Errorf("No observer belongs to cluster %s", obcluster.Name) + } + + var s *connector.OceanBaseDataSource + secret, err := client.GetClient().ClientSet.CoreV1().Secrets(obcluster.Namespace).Get(ctx, secretName, metav1.GetOptions{}) + if err != nil { + return nil, errors.Wrapf(err, "Get secret %s", secretName) + } + + password := string(secret.Data["password"]) + for _, observer := range observerList.Items { + address := observer.Status.GetConnectAddr() + s = connector.NewOceanBaseDataSource(address, oceanbaseconst.SqlPort, userName, tenantName, password, oceanbaseconst.DefaultDatabase) + // if err is nil, db connection is already checked available + sysClient, err := operation.GetOceanbaseOperationManager(s) + if err == nil && sysClient != nil { + dummy := logr.Discard() + sysClient.Logger = &dummy + return sysClient, nil + } + } + return nil, errors.Errorf("Can not get oceanbase operation manager of obcluster %s after checked all server", obcluster.Name) +}