From 765e4e066044164a00acec2a54a08b769d263148 Mon Sep 17 00:00:00 2001 From: xiaochaoren1 Date: Fri, 15 Nov 2024 16:25:02 +0800 Subject: [PATCH] feat: querier support language parameter --- server/querier/common/const.go | 1 + server/querier/common/parameters.go | 1 + .../querier/engine/clickhouse/clickhouse.go | 76 +++++++-- .../querier/engine/clickhouse/common/const.go | 1 + .../engine/clickhouse/metrics/ext_common.go | 4 +- .../engine/clickhouse/metrics/metrics.go | 154 +++++++++++------- .../engine/clickhouse/tag/description.go | 132 ++++++++------- server/querier/router/query.go | 1 + 8 files changed, 236 insertions(+), 134 deletions(-) diff --git a/server/querier/common/const.go b/server/querier/common/const.go index e6125adca61..5b5ebef88b5 100644 --- a/server/querier/common/const.go +++ b/server/querier/common/const.go @@ -46,6 +46,7 @@ const ( ) const ( + HEADER_KEY_LANGUAGE = "X-Language" HEADER_KEY_X_ORG_ID = "X-Org-Id" DEFAULT_ORG_ID = "1" ) diff --git a/server/querier/common/parameters.go b/server/querier/common/parameters.go index f1c4bf106ab..209fffd5b28 100644 --- a/server/querier/common/parameters.go +++ b/server/querier/common/parameters.go @@ -34,6 +34,7 @@ type QuerierParams struct { NoPreWhere bool ORGID string SimpleSql bool + Language string } type TempoParams struct { diff --git a/server/querier/engine/clickhouse/clickhouse.go b/server/querier/engine/clickhouse/clickhouse.go index e92c5c5d171..0669d046a9b 100644 --- a/server/querier/engine/clickhouse/clickhouse.go +++ b/server/querier/engine/clickhouse/clickhouse.go @@ -259,8 +259,10 @@ func ShowTagTypeMetrics(tagDescriptions, result *common.Result, db, table string clientName := tagSlice[1].(string) serverName := tagSlice[2].(string) displayName := tagSlice[3].(string) - tagType := tagSlice[4].(string) - permissions := tagSlice[7].([]bool) + displayNameZH := tagSlice[4].(string) + displayNameEN := tagSlice[5].(string) + tagType := tagSlice[6].(string) + permissions := tagSlice[9].([]bool) if slices.Contains([]string{"auto_custom_tag", "time", "id"}, tagType) { continue } @@ -270,8 +272,8 @@ func ShowTagTypeMetrics(tagDescriptions, result *common.Result, db, table string if name == "lb_listener" || name == "pod_ingress" { continue } - if len(tagSlice) >= 12 { - notSupportedOperators := tagSlice[11].([]string) + if len(tagSlice) >= 16 { + notSupportedOperators := tagSlice[15].([]string) // not support select if slices.Contains(notSupportedOperators, "select") { continue @@ -280,14 +282,18 @@ func ShowTagTypeMetrics(tagDescriptions, result *common.Result, db, table string if slices.Contains([]string{"l4_flow_log", "l7_flow_log", "application_map", "network_map", "vtap_flow_edge_port", "vtap_app_edge_port"}, table) { if serverName == clientName { clientNameMetric := []interface{}{ - clientName, true, displayName, "", metrics.METRICS_TYPE_NAME_MAP["tag"], - "Tag", metrics.METRICS_OPERATORS, permissions, table, "", + clientName, true, displayName, displayNameZH, displayNameEN, "", "", "", metrics.METRICS_TYPE_NAME_MAP["tag"], + "Tag", metrics.METRICS_OPERATORS, permissions, table, "", "", "", } result.Values = append(result.Values, clientNameMetric) } else { var ( - serverDisplayName = displayName - clientDisplayName = displayName + serverDisplayName = displayName + clientDisplayName = displayName + serverDisplayNameZH = chCommon.TagServerChPrefix + " " + displayName + serverDisplayNameEN = chCommon.TagServerEnPrefix + " " + displayName + clientDisplayNameZH = chCommon.TagClientChPrefix + " " + displayName + clientDisplayNameEN = chCommon.TagClientEnPrefix + " " + displayName ) if config.Cfg.Language == "en" { serverDisplayName = chCommon.TagServerEnPrefix + " " + displayName @@ -302,19 +308,19 @@ func ShowTagTypeMetrics(tagDescriptions, result *common.Result, db, table string } } serverNameMetric := []interface{}{ - serverName, true, serverDisplayName, "", metrics.METRICS_TYPE_NAME_MAP["tag"], - "Tag", metrics.METRICS_OPERATORS, permissions, table, "", + serverName, true, serverDisplayName, serverDisplayNameZH, serverDisplayNameEN, "", "", "", metrics.METRICS_TYPE_NAME_MAP["tag"], + "Tag", metrics.METRICS_OPERATORS, permissions, table, "", "", "", } clientNameMetric := []interface{}{ - clientName, true, clientDisplayName, "", metrics.METRICS_TYPE_NAME_MAP["tag"], - "Tag", metrics.METRICS_OPERATORS, permissions, table, "", + clientName, true, clientDisplayName, clientDisplayNameZH, clientDisplayNameEN, "", "", "", metrics.METRICS_TYPE_NAME_MAP["tag"], + "Tag", metrics.METRICS_OPERATORS, permissions, table, "", "", "", } result.Values = append(result.Values, serverNameMetric, clientNameMetric) } } else { nameMetric := []interface{}{ - name, true, displayName, "", metrics.METRICS_TYPE_NAME_MAP["tag"], - "Tag", metrics.METRICS_OPERATORS, permissions, table, "", + name, true, displayName, displayName, displayName, "", "", "", metrics.METRICS_TYPE_NAME_MAP["tag"], + "Tag", metrics.METRICS_OPERATORS, permissions, table, "", "", "", } result.Values = append(result.Values, nameMetric) } @@ -360,6 +366,42 @@ func dataVisibilityfiltering(visibilityFilterRegexp *regexp.Regexp, values []int return visibilityFilterValues } +func formatTagByLanguage(language string, values []interface{}) { + for _, value := range values { + displaynameZH := value.([]interface{})[4].(string) + displaynameEN := value.([]interface{})[5].(string) + descriptionZH := value.([]interface{})[11].(string) + descriptionEN := value.([]interface{})[12].(string) + if language == chCommon.LanguageEN { + value.([]interface{})[3] = displaynameEN + value.([]interface{})[10] = descriptionEN + } else { + value.([]interface{})[3] = displaynameZH + value.([]interface{})[10] = descriptionZH + } + } +} + +func formatMetricByLanguage(language string, values []interface{}) { + for _, value := range values { + displaynameZH := value.([]interface{})[3].(string) + displaynameEN := value.([]interface{})[4].(string) + unitZH := value.([]interface{})[6].(string) + unitEN := value.([]interface{})[7].(string) + descriptionZH := value.([]interface{})[14].(string) + descriptionEN := value.([]interface{})[15].(string) + if language == chCommon.LanguageEN { + value.([]interface{})[2] = displaynameEN + value.([]interface{})[5] = unitEN + value.([]interface{})[13] = descriptionEN + } else { + value.([]interface{})[2] = displaynameZH + value.([]interface{})[5] = unitZH + value.([]interface{})[13] = descriptionZH + } + } +} + func (e *CHEngine) ParseShowSql(sql string, args *common.QuerierParams, DebugInfo *client.DebugInfo) (*common.Result, []string, bool, error) { var visibilityFilterRegexp *regexp.Regexp sqlSplit := strings.Fields(sql) @@ -428,6 +470,9 @@ func (e *CHEngine) ParseShowSql(sql string, args *common.QuerierParams, DebugInf if len(visibilityFilter) > 0 && e.DB != chCommon.DB_NAME_DEEPFLOW_TENANT { result.Values = dataVisibilityfiltering(visibilityFilterRegexp, result.Values) } + if args.Language != "" { + formatMetricByLanguage(args.Language, result.Values) + } return result, []string{}, true, err case 4: // show tag X values from Y X, Y not nil result, sqlList, err := tagdescription.GetTagValues(e.DB, table, sql, args.QueryCacheTTL, args.ORGID, args.UseQueryCache) @@ -441,6 +486,9 @@ func (e *CHEngine) ParseShowSql(sql string, args *common.QuerierParams, DebugInf if len(visibilityFilter) > 0 && e.DB != chCommon.DB_NAME_DEEPFLOW_TENANT { data.Values = dataVisibilityfiltering(visibilityFilterRegexp, data.Values) } + if args.Language != "" { + formatTagByLanguage(args.Language, data.Values) + } return data, []string{}, true, err case 6: // show tables... if e.DB == chCommon.DB_NAME_DEEPFLOW_TENANT && len(visibilityFilter) > 0 { diff --git a/server/querier/engine/clickhouse/common/const.go b/server/querier/engine/clickhouse/common/const.go index ac9a7b5a8b4..5fdd28a8f89 100644 --- a/server/querier/engine/clickhouse/common/const.go +++ b/server/querier/engine/clickhouse/common/const.go @@ -37,6 +37,7 @@ const TagServerChPrefix = "服务端" const TagClientChPrefix = "客户端" const TagServerEnPrefix = "Server" const TagClientEnPrefix = "Client" +const LanguageEN = "en" var DB_TABLE_MAP = map[string][]string{ DB_NAME_FLOW_LOG: []string{"l4_flow_log", "l7_flow_log", "l4_packet", "l7_packet"}, diff --git a/server/querier/engine/clickhouse/metrics/ext_common.go b/server/querier/engine/clickhouse/metrics/ext_common.go index 559bb21c1e3..8e5a2d0d460 100644 --- a/server/querier/engine/clickhouse/metrics/ext_common.go +++ b/server/querier/engine/clickhouse/metrics/ext_common.go @@ -72,8 +72,8 @@ func GetExtMetrics(db, table, where, queryCacheTTL, orgID string, useQueryCache dbField := fmt.Sprintf("if(indexOf(%s, '%s')=0, null, %s[indexOf(%s, '%s')])", metrics_names_field, externalTag, metrics_values_field, metrics_names_field, externalTag) metricName := fmt.Sprintf("metrics.%s", externalTag) lm := NewMetrics( - i, dbField, metricName, "", METRICS_TYPE_COUNTER, - "metrics", []bool{true, true, true}, "", tableName, "", "", + i, dbField, metricName, metricName, metricName, "", "", "", METRICS_TYPE_COUNTER, + "metrics", []bool{true, true, true}, "", tableName, "", "", "", "", ) loadMetrics[fmt.Sprintf("%s-%s", metricName, tableName)] = lm } diff --git a/server/querier/engine/clickhouse/metrics/metrics.go b/server/querier/engine/clickhouse/metrics/metrics.go index 235b8e27e1b..75c4a16255d 100644 --- a/server/querier/engine/clickhouse/metrics/metrics.go +++ b/server/querier/engine/clickhouse/metrics/metrics.go @@ -44,18 +44,24 @@ var DB_DESCRIPTIONS map[string]interface{} var letterRegexp = regexp.MustCompile("^[a-zA-Z]") type Metrics struct { - Index int // 索引 - DBField string // 数据库字段 - DisplayName string // 描述 - Unit string // 单位 - Type int // 指标量类型 - Category string // 类别 - Condition string // 聚合过滤 - IsAgg bool // 是否为聚合指标量 - Permissions []bool // 指标量的权限控制 - Table string // 所属表 - Description string // 描述 - TagType string // Tag type of metric's tag type + Index int // 索引 + DBField string // 数据库字段 + DisplayName string // 描述 + DisplayNameZH string // 描述 + DisplayNameEN string // 描述 + Unit string // 单位 + UnitZH string // 单位 + UnitEN string // 单位 + Type int // 指标量类型 + Category string // 类别 + Condition string // 聚合过滤 + IsAgg bool // 是否为聚合指标量 + Permissions []bool // 指标量的权限控制 + Table string // 所属表 + Description string // 描述 + DescriptionZH string // 描述 + DescriptionEN string // 描述 + TagType string // Tag type of metric's tag type } func (m *Metrics) Replace(metrics *Metrics) { @@ -74,21 +80,27 @@ func (m *Metrics) SetIsAgg(isAgg bool) *Metrics { } func NewMetrics( - index int, dbField string, displayname string, unit string, metricType int, category string, - permissions []bool, condition string, table string, description string, tagType string, + index int, dbField string, displayname string, displaynameZH string, displaynameEN string, unit string, unitZH string, unitEN string, metricType int, category string, + permissions []bool, condition string, table string, description string, descriptionZH string, descriptionEN string, tagType string, ) *Metrics { return &Metrics{ - Index: index, - DBField: dbField, - DisplayName: displayname, - Unit: unit, - Type: metricType, - Category: category, - Permissions: permissions, - Condition: condition, - Table: table, - Description: description, - TagType: tagType, + Index: index, + DBField: dbField, + DisplayName: displayname, + DisplayNameZH: displaynameZH, + DisplayNameEN: displaynameEN, + Unit: unit, + UnitZH: unitZH, + UnitEN: unitEN, + Type: metricType, + Category: category, + Permissions: permissions, + Condition: condition, + Table: table, + Description: description, + DescriptionZH: descriptionZH, + DescriptionEN: descriptionEN, + TagType: tagType, } } @@ -123,8 +135,10 @@ func GetTagTypeMetrics(tagDescriptions *common.Result, newAllMetrics map[string] clientName := tagSlice[1].(string) serverName := tagSlice[2].(string) displayName := tagSlice[3].(string) - tagType := tagSlice[4].(string) - permissions := tagSlice[7].([]bool) + displayNameZH := tagSlice[4].(string) + displayNameEN := tagSlice[5].(string) + tagType := tagSlice[6].(string) + permissions := tagSlice[9].([]bool) if slices.Contains([]string{"auto_custom_tag", "time", "id"}, tagType) { continue @@ -135,8 +149,8 @@ func GetTagTypeMetrics(tagDescriptions *common.Result, newAllMetrics map[string] if name == "lb_listener" || name == "pod_ingress" { continue } - if len(tagSlice) >= 12 { - notSupportedOperators := tagSlice[11].([]string) + if len(tagSlice) >= 16 { + notSupportedOperators := tagSlice[15].([]string) // not support select if slices.Contains(notSupportedOperators, "select") { continue @@ -158,42 +172,48 @@ func GetTagTypeMetrics(tagDescriptions *common.Result, newAllMetrics map[string] if slices.Contains([]string{"l4_flow_log", "l7_flow_log", "application_map", "network_map", "vtap_flow_edge_port", "vtap_app_edge_port"}, table) { if serverName == clientName { clientNameMetric := NewMetrics( - 0, clientNameDBField, displayName, "", METRICS_TYPE_NAME_MAP["tag"], - "Tag", permissions, "", table, "", tagType, + 0, clientNameDBField, displayName, displayNameZH, displayNameEN, "", "", "", METRICS_TYPE_NAME_MAP["tag"], + "Tag", permissions, "", table, "", "", "", tagType, ) newAllMetrics[clientName] = clientNameMetric } else { var ( - serverDisplayName = displayName - clientDisplayName = displayName + serverDisplayName = displayName + clientDisplayName = displayName + serverDisplayNameZH = displayName + clientDisplayNameZH = displayName + serverDisplayNameEN = ckcommon.TagServerEnPrefix + " " + displayName + clientDisplayNameEN = ckcommon.TagClientEnPrefix + " " + displayName ) + if letterRegexp.MatchString(serverName) { + serverDisplayNameZH = ckcommon.TagServerChPrefix + " " + displayName + clientDisplayNameZH = ckcommon.TagClientChPrefix + " " + displayName + } else { + serverDisplayNameZH = ckcommon.TagServerChPrefix + displayName + clientDisplayNameZH = ckcommon.TagClientChPrefix + displayName + } if config.Cfg.Language == "en" { - serverDisplayName = ckcommon.TagServerEnPrefix + " " + displayName - clientDisplayName = ckcommon.TagClientEnPrefix + " " + displayName + serverDisplayName = serverDisplayNameEN + clientDisplayName = clientDisplayNameEN } else if config.Cfg.Language == "ch" { - if letterRegexp.MatchString(serverName) { - serverDisplayName = ckcommon.TagServerChPrefix + " " + displayName - clientDisplayName = ckcommon.TagClientChPrefix + " " + displayName - } else { - serverDisplayName = ckcommon.TagServerChPrefix + displayName - clientDisplayName = ckcommon.TagClientChPrefix + displayName - } + serverDisplayName = serverDisplayNameZH + clientDisplayName = clientDisplayNameZH } serverNameMetric := NewMetrics( - 0, serverNameDBField, serverDisplayName, "", METRICS_TYPE_NAME_MAP["tag"], - "Tag", permissions, "", table, "", tagType, + 0, serverNameDBField, serverDisplayName, serverDisplayNameZH, serverDisplayNameEN, "", "", "", METRICS_TYPE_NAME_MAP["tag"], + "Tag", permissions, "", table, "", "", "", tagType, ) clientNameMetric := NewMetrics( - 0, clientNameDBField, clientDisplayName, "", METRICS_TYPE_NAME_MAP["tag"], - "Tag", permissions, "", table, "", tagType, + 0, clientNameDBField, clientDisplayName, clientDisplayNameZH, clientDisplayNameEN, "", "", "", METRICS_TYPE_NAME_MAP["tag"], + "Tag", permissions, "", table, "", "", "", tagType, ) newAllMetrics[serverName] = serverNameMetric newAllMetrics[clientName] = clientNameMetric } } else { nameMetric := NewMetrics( - 0, nameDBField, displayName, "", METRICS_TYPE_NAME_MAP["tag"], - "Tag", permissions, "", table, "", tagType, + 0, nameDBField, displayName, displayName, displayName, "", "", "", METRICS_TYPE_NAME_MAP["tag"], + "Tag", permissions, "", table, "", "", "", tagType, ) newAllMetrics[name] = nameMetric } @@ -219,16 +239,16 @@ func GetMetrics(field, db, table, orgID string) (*Metrics, bool) { metrics_names_field, metrics_values_field := METRICS_ARRAY_NAME_MAP[db][0], METRICS_ARRAY_NAME_MAP[db][1] metric := NewMetrics( 0, fmt.Sprintf("if(indexOf(%s, '%s')=0,null,%s[indexOf(%s, '%s')])", metrics_names_field, fieldName, metrics_values_field, metrics_names_field, fieldName), - field, "", METRICS_TYPE_COUNTER, - "metrics", []bool{true, true, true}, "", table, "", "", + field, field, field, "", "", "", METRICS_TYPE_COUNTER, + "metrics", []bool{true, true, true}, "", table, "", "", "", "", ) newAllMetrics[field] = metric } else if fieldSplit[0] == "tag" { fieldName := strings.Replace(field, "tag.", "", 1) metric := NewMetrics( 0, fmt.Sprintf("if(indexOf(tag_names, '%s')=0,null,tag_values[indexOf(tag_names, '%s')])", fieldName, fieldName), - field, "", METRICS_TYPE_NAME_MAP["tag"], - "Tag", []bool{true, true, true}, "", table, "", "", + field, field, field, "", "", "", METRICS_TYPE_NAME_MAP["tag"], + "Tag", []bool{true, true, true}, "", table, "", "", "", "", ) newAllMetrics[field] = metric } @@ -347,8 +367,8 @@ func GetMetricsByDBTableDynamic(db, table, where, queryCacheTTL, orgID string, u } metrics["metrics"] = NewMetrics( len(metrics), "metrics", - "metrics", "", METRICS_TYPE_ARRAY, - "metrics", []bool{true, true, true}, "", table, "", "", + "metrics", "metrics", "metrics", "", "", "", METRICS_TYPE_ARRAY, + "metrics", []bool{true, true, true}, "", table, "", "", "", "", ) return metrics, err } @@ -364,8 +384,8 @@ func GetMetricsByDBTableDynamic(db, table, where, queryCacheTTL, orgID string, u } metrics["metrics"] = NewMetrics( len(metrics), "metrics", - "metrics", "", METRICS_TYPE_ARRAY, - "metrics", []bool{true, true, true}, "", table, "", "", + "metrics", "metrics", "metrics", "", "", "", METRICS_TYPE_ARRAY, + "metrics", []bool{true, true, true}, "", table, "", "", "", "", ) return metrics, err } @@ -377,7 +397,7 @@ func GetMetricsByDBTableDynamic(db, table, where, queryCacheTTL, orgID string, u func GetMetricsDescriptionsByDBTable(db, table string, allMetrics map[string]*Metrics) []interface{} { /* columns := []interface{}{ - "name", "is_agg", "display_name", "unit", "type", "category", "operators", "permissions", "table" + "name", "is_agg", "display_name", "display_name_zh", "display_name_en", "unit", "unit_zh", "unit_en", "type", "category", "operators", "permissions", "table", "description", "description_zh", "description_en" } */ values := make([]interface{}, len(allMetrics)) for field, metrics := range allMetrics { @@ -390,9 +410,9 @@ func GetMetricsDescriptionsByDBTable(db, table string, allMetrics map[string]*Me } } values[metrics.Index] = []interface{}{ - field, metrics.IsAgg, metrics.DisplayName, metrics.Unit, metrics.Type, + field, metrics.IsAgg, metrics.DisplayName, metrics.DisplayNameZH, metrics.DisplayNameEN, metrics.Unit, metrics.UnitZH, metrics.UnitEN, metrics.Type, metrics.Category, METRICS_OPERATORS, metrics.Permissions, metrics.Table, - metrics.Description, + metrics.Description, metrics.DescriptionZH, metrics.DescriptionEN, } } return values @@ -455,7 +475,7 @@ func GetMetricsDescriptions(db, table, where, queryCacheTTL, orgID string, useQu values = append(values, metricValues...) } columns := []interface{}{ - "name", "is_agg", "display_name", "unit", "type", "category", "operators", "permissions", "table", "description", + "name", "is_agg", "display_name", "display_name_zh", "display_name_en", "unit", "unit_zh", "unit_en", "type", "category", "operators", "permissions", "table", "description", "description_zh", "description_en", } return &common.Result{ Columns: columns, @@ -582,6 +602,8 @@ func LoadMetrics(db string, table string, dbDescription map[string]interface{}) if ok { metricsData, ok := tableDate.(map[string]interface{})[table] metricsDataLanguage, _ := tableDate.(map[string]interface{})[table+"."+config.Cfg.Language] + metricsDataLanguageZH, _ := tableDate.(map[string]interface{})[table+".ch"] + metricsDataLanguageEN, _ := tableDate.(map[string]interface{})[table+".en"] if ok { loadMetrics = make(map[string]*Metrics) for i, metrics := range metricsData.([][]interface{}) { @@ -597,12 +619,20 @@ func LoadMetrics(db string, table string, dbDescription map[string]interface{}) return nil, errors.New(fmt.Sprintf("parse metrics permission failed! db:%s table:%s metrics:%v", db, table, metrics)) } metricsLanguage := metricsDataLanguage.([][]interface{})[i] + metricsLanguageZH := metricsDataLanguageZH.([][]interface{})[i] + metricsLanguageEN := metricsDataLanguageEN.([][]interface{})[i] displayName := metricsLanguage[1].(string) + displayNameZH := metricsLanguageZH[1].(string) + displayNameEN := metricsLanguageEN[1].(string) unit := metricsLanguage[2].(string) + unitZH := metricsLanguageZH[2].(string) + unitEN := metricsLanguageEN[2].(string) description := metricsLanguage[3].(string) + descriptionZH := metricsLanguageZH[3].(string) + descriptionEN := metricsLanguageEN[3].(string) lm := NewMetrics( - i, metrics[1].(string), displayName, unit, metricType, - metrics[3].(string), permissions, "", table, description, "", + i, metrics[1].(string), displayName, displayNameZH, displayNameEN, unit, unitZH, unitEN, metricType, + metrics[3].(string), permissions, "", table, description, descriptionZH, descriptionEN, "", ) loadMetrics[metrics[0].(string)] = lm } diff --git a/server/querier/engine/clickhouse/tag/description.go b/server/querier/engine/clickhouse/tag/description.go index 63e4c92b34c..d8056ce78e9 100644 --- a/server/querier/engine/clickhouse/tag/description.go +++ b/server/querier/engine/clickhouse/tag/description.go @@ -90,10 +90,16 @@ type TagDescription struct { ClientName string ServerName string DisplayName string + DisplayNameZH string + DisplayNameEN string Type string EnumFile string + EnumFileZH string + EnumFileEN string Category string Description string + DescriptionZH string + DescriptionEN string Operators []string Permissions []bool RelatedTag string @@ -103,8 +109,8 @@ type TagDescription struct { } func NewTagDescription( - name, clientName, serverName, displayName, tagType, enumFile, category string, - permissions []bool, description, relatedTag string, deprecated bool, notSupportedOperators []string, table string, + name, clientName, serverName, displayName, displayNameZH, displayNameEN, tagType, enumFile, enumFileZH, enumFileEN, category string, + permissions []bool, description, descriptionZH, descriptionEN, relatedTag string, deprecated bool, notSupportedOperators []string, table string, ) *TagDescription { operators, ok := tagTypeToOperators[tagType] if !ok { @@ -115,12 +121,18 @@ func NewTagDescription( ClientName: clientName, ServerName: serverName, DisplayName: displayName, + DisplayNameZH: displayNameZH, + DisplayNameEN: displayNameEN, Type: tagType, EnumFile: enumFile, + EnumFileZH: enumFileZH, + EnumFileEN: enumFileEN, Category: category, Operators: operators, Permissions: permissions, Description: description, + DescriptionZH: descriptionZH, + DescriptionEN: descriptionEN, RelatedTag: relatedTag, Deprecated: deprecated, NotSupportedOperators: notSupportedOperators, @@ -202,15 +214,23 @@ func LoadTagDescriptions(tagData map[string]interface{}) error { } key := TagDescriptionKey{DB: db, Table: table, TagName: tag[0].(string)} tagLanguage := dbTagData.(map[string]interface{})[table+"."+config.Cfg.Language].([][]interface{})[i] + tagLanguageZH := dbTagData.(map[string]interface{})[table+".ch"].([][]interface{})[i] + tagLanguageEN := dbTagData.(map[string]interface{})[table+".en"].([][]interface{})[i] TAG_DESCRIPTION_KEYS = append(TAG_DESCRIPTION_KEYS, key) enumFile := tag[4].(string) enumFile = tag[4].(string) + "." + config.Cfg.Language + enumFileZH := tag[4].(string) + ".ch" + enumFileEN := tag[4].(string) + ".en" displayName := tagLanguage[1].(string) + displayNameZH := tagLanguageZH[1].(string) + displayNameEN := tagLanguageEN[1].(string) des := tagLanguage[2].(string) + desZH := tagLanguageZH[2].(string) + desEN := tagLanguageEN[2].(string) description := NewTagDescription( - tag[0].(string), tag[1].(string), tag[2].(string), displayName, - tag[3].(string), enumFile, tag[5].(string), permissions, des, "", deprecated, notSupportedOperators, table, + tag[0].(string), tag[1].(string), tag[2].(string), displayName, displayNameZH, displayNameEN, + tag[3].(string), enumFile, enumFileZH, enumFileEN, tag[5].(string), permissions, des, desZH, desEN, "", deprecated, notSupportedOperators, table, ) TAG_DESCRIPTIONS[key] = description enumFileToTagType[enumFile] = tag[3].(string) @@ -662,8 +682,8 @@ func LoadTagDescriptions(tagData map[string]interface{}) error { func GetStaticTagDescriptions(db, table string) (response *common.Result, err error) { response = &common.Result{ Columns: []interface{}{ - "name", "client_name", "server_name", "display_name", "type", "category", - "operators", "permissions", "description", "related_tag", "deprecated", "not_supported_operators", "table", + "name", "client_name", "server_name", "display_name", "display_name_zh", "display_name_en", "type", "category", + "operators", "permissions", "description", "description_zh", "description_en", "related_tag", "deprecated", "not_supported_operators", "table", }, Values: []interface{}{}, } @@ -675,8 +695,8 @@ func GetStaticTagDescriptions(db, table string) (response *common.Result, err er response.Values = append( response.Values, []interface{}{ - tag.Name, tag.ClientName, tag.ServerName, tag.DisplayName, tag.Type, - tag.Category, tag.Operators, tag.Permissions, tag.Description, tag.RelatedTag, tag.Deprecated, tag.NotSupportedOperators, "", + tag.Name, tag.ClientName, tag.ServerName, tag.DisplayName, tag.DisplayNameZH, tag.DisplayNameEN, tag.Type, + tag.Category, tag.Operators, tag.Permissions, tag.Description, tag.DescriptionZH, tag.DescriptionEN, tag.RelatedTag, tag.Deprecated, tag.NotSupportedOperators, "", }, ) } @@ -691,18 +711,18 @@ func GetStaticTagDescriptions(db, table string) (response *common.Result, err er } if slices.Contains(common.PEER_TABLES, table) { response.Values = append(response.Values, []interface{}{ - tagName, tagName + "_0", tagName + "_1", tagDisplayName, "auto_custom_tag", - "Custom Tag", []string{}, []bool{true, true, true}, AutoCustomTag.Description, AutoCustomTag.TagFields, false, []string{}, "", + tagName, tagName + "_0", tagName + "_1", tagDisplayName, tagDisplayName, tagDisplayName, "auto_custom_tag", + "Custom Tag", []string{}, []bool{true, true, true}, AutoCustomTag.Description, AutoCustomTag.Description, AutoCustomTag.Description, AutoCustomTag.TagFields, false, []string{}, "", }) } else if table == "alert_event" { response.Values = append(response.Values, []interface{}{ - tagName, tagName + "_0", tagName + "_1", tagDisplayName, "auto_custom_tag", - "Custom Tag", []string{}, []bool{true, true, true}, AutoCustomTag.Description, AutoCustomTag.TagFields, false, []string{"select", "group"}, "", + tagName, tagName + "_0", tagName + "_1", tagDisplayName, tagDisplayName, tagDisplayName, "auto_custom_tag", + "Custom Tag", []string{}, []bool{true, true, true}, AutoCustomTag.Description, AutoCustomTag.Description, AutoCustomTag.Description, AutoCustomTag.TagFields, false, []string{"select", "group"}, "", }) } else if !slices.Contains(noCustomTagDB, db) && !slices.Contains(noCustomTagTable, table) { response.Values = append(response.Values, []interface{}{ - tagName, tagName, tagName, tagDisplayName, "auto_custom_tag", - "Custom Tag", []string{}, []bool{true, true, true}, AutoCustomTag.Description, AutoCustomTag.TagFields, false, []string{}, "", + tagName, tagName, tagName, tagDisplayName, tagDisplayName, tagDisplayName, "auto_custom_tag", + "Custom Tag", []string{}, []bool{true, true, true}, AutoCustomTag.Description, AutoCustomTag.Description, AutoCustomTag.Description, AutoCustomTag.TagFields, false, []string{}, "", }) } } @@ -710,8 +730,8 @@ func GetStaticTagDescriptions(db, table string) (response *common.Result, err er if slices.Contains([]string{ckcommon.DB_NAME_EXT_METRICS, ckcommon.DB_NAME_DEEPFLOW_ADMIN, ckcommon.DB_NAME_DEEPFLOW_TENANT, ckcommon.DB_NAME_PROFILE, ckcommon.DB_NAME_PROMETHEUS}, db) { response.Values = append(response.Values, []interface{}{ - "tag", "tag", "tag", "tag", "map", - "Native Tag", []string{}, []bool{true, true, true}, "tag", "", false, []string{}, "", + "tag", "tag", "tag", "tag", "tag", "tag", "map", + "Native Tag", []string{}, []bool{true, true, true}, "tag", "tag", "tag", "", false, []string{}, "", }) } return @@ -721,8 +741,8 @@ func GetStaticTagDescriptions(db, table string) (response *common.Result, err er func GetDynamicTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, useQueryCache bool, ctx context.Context, DebugInfo *client.DebugInfo) (response *common.Result, err error) { response = &common.Result{ Columns: []interface{}{ - "name", "client_name", "server_name", "display_name", "type", "category", - "operators", "permissions", "description", "related_tag", "deprecated", "not_supported_operators", "table", + "name", "client_name", "server_name", "display_name", "display_name_zh", "display_name_en", "type", "category", + "operators", "permissions", "description", "description_zh", "description_en", "related_tag", "deprecated", "not_supported_operators", "table", }, Values: []interface{}{}, } @@ -755,13 +775,13 @@ func GetDynamicTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, u labelKey := "k8s.label." + key.(string) if slices.Contains(common.PEER_TABLES, table) { response.Values = append(response.Values, []interface{}{ - labelKey, labelKey + "_0", labelKey + "_1", labelKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + labelKey, labelKey + "_0", labelKey + "_1", labelKey, labelKey, labelKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } else if !slices.Contains(noCustomTagDB, db) && !slices.Contains(noCustomTagTable, table) { response.Values = append(response.Values, []interface{}{ - labelKey, labelKey, labelKey, labelKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + labelKey, labelKey, labelKey, labelKey, labelKey, labelKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } } @@ -785,13 +805,13 @@ func GetDynamicTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, u annotationKey := "k8s.annotation." + key.(string) if slices.Contains(common.PEER_TABLES, table) { response.Values = append(response.Values, []interface{}{ - annotationKey, annotationKey + "_0", annotationKey + "_1", annotationKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + annotationKey, annotationKey + "_0", annotationKey + "_1", annotationKey, annotationKey, annotationKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } else if !slices.Contains(noCustomTagDB, db) && !slices.Contains(noCustomTagTable, table) { response.Values = append(response.Values, []interface{}{ - annotationKey, annotationKey, annotationKey, annotationKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + annotationKey, annotationKey, annotationKey, annotationKey, annotationKey, annotationKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } } @@ -812,13 +832,13 @@ func GetDynamicTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, u envKey := "k8s.env." + key.(string) if slices.Contains(common.PEER_TABLES, table) { response.Values = append(response.Values, []interface{}{ - envKey, envKey + "_0", envKey + "_1", envKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + envKey, envKey + "_0", envKey + "_1", envKey, envKey, envKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } else if !slices.Contains(noCustomTagDB, db) && !slices.Contains(noCustomTagTable, table) { response.Values = append(response.Values, []interface{}{ - envKey, envKey, envKey, envKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + envKey, envKey, envKey, envKey, envKey, envKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } } @@ -838,13 +858,13 @@ func GetDynamicTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, u chostCloudTagKey := "cloud.tag." + key.(string) if slices.Contains(common.PEER_TABLES, table) { response.Values = append(response.Values, []interface{}{ - chostCloudTagKey, chostCloudTagKey + "_0", chostCloudTagKey + "_1", chostCloudTagKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + chostCloudTagKey, chostCloudTagKey + "_0", chostCloudTagKey + "_1", chostCloudTagKey, chostCloudTagKey, chostCloudTagKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } else if !slices.Contains(noCustomTagDB, db) && !slices.Contains(noCustomTagTable, table) { response.Values = append(response.Values, []interface{}{ - chostCloudTagKey, chostCloudTagKey, chostCloudTagKey, chostCloudTagKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + chostCloudTagKey, chostCloudTagKey, chostCloudTagKey, chostCloudTagKey, chostCloudTagKey, chostCloudTagKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } } @@ -864,13 +884,13 @@ func GetDynamicTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, u osAPPTagKey := "os.app." + key.(string) if slices.Contains(common.PEER_TABLES, table) { response.Values = append(response.Values, []interface{}{ - osAPPTagKey, osAPPTagKey + "_0", osAPPTagKey + "_1", osAPPTagKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + osAPPTagKey, osAPPTagKey + "_0", osAPPTagKey + "_1", osAPPTagKey, osAPPTagKey, osAPPTagKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } else if !slices.Contains(noCustomTagDB, db) && !slices.Contains(noCustomTagTable, table) { response.Values = append(response.Values, []interface{}{ - osAPPTagKey, osAPPTagKey, osAPPTagKey, osAPPTagKey, "map_item", - "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", false, notSupportOperator, "", + osAPPTagKey, osAPPTagKey, osAPPTagKey, osAPPTagKey, osAPPTagKey, osAPPTagKey, "map_item", + "Custom Tag", tagTypeToOperators["string"], []bool{true, true, true}, "", "", "", "", false, notSupportOperator, "", }) } } @@ -942,8 +962,8 @@ func GetDynamicTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, u if db == "_prometheus" { externalTag := tagName.(string) response.Values = append(response.Values, []interface{}{ - externalTag, externalTag, externalTag, externalTag, "map_item", - "Native Tag", tagTypeToOperators["string"], []bool{true, true, true}, externalTag, "", false, notSupportOperator, tableName, + externalTag, externalTag, externalTag, externalTag, externalTag, externalTag, "map_item", + "Native Tag", tagTypeToOperators["string"], []bool{true, true, true}, externalTag, externalTag, externalTag, "", false, notSupportOperator, tableName, }) } else if table == "alert_event" { externalTag := tagName.(string) @@ -952,34 +972,34 @@ func GetDynamicTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, u if strings.HasPrefix(externalTag, "cloud.tag.") || strings.HasPrefix(externalTag, "k8s.label.") || strings.HasPrefix(externalTag, "os.app.") || strings.HasPrefix(externalTag, "k8s.annotation.") || strings.HasPrefix(externalTag, "k8s.env.") { categoryValue = "Custom Tag" response.Values = append(response.Values, []interface{}{ - externalTag, externalTag, externalTag, externalTag, "map_item", - categoryValue, tagTypeToOperators["string"], []bool{true, true, true}, externalTag, "", false, notSupportOperator, tableName, + externalTag, externalTag, externalTag, externalTag, externalTag, externalTag, "map_item", + categoryValue, tagTypeToOperators["string"], []bool{true, true, true}, externalTag, externalTag, externalTag, "", false, notSupportOperator, tableName, }) } else if strings.HasPrefix(externalTag, "tag.") || strings.HasPrefix(externalTag, "attribute.") { categoryValue = "Native Tag" response.Values = append(response.Values, []interface{}{ - externalTag, externalTag, externalTag, externalTag, "map_item", - categoryValue, tagTypeToOperators["string"], []bool{true, true, true}, externalTag, "", false, notSupportOperator, tableName, + externalTag, externalTag, externalTag, externalTag, externalTag, externalTag, "map_item", + categoryValue, tagTypeToOperators["string"], []bool{true, true, true}, externalTag, externalTag, externalTag, "", false, notSupportOperator, tableName, }) } else { categoryValue = _tagName.([]interface{})[2].(string) response.Values = append(response.Values, []interface{}{ - externalTag, externalTag, externalTag, externalTag, categoryValue, - categoryValue, tagTypeToOperators[categoryValue], []bool{true, true, true}, externalTag, "", false, notSupportOperator, tableName, + externalTag, externalTag, externalTag, externalTag, externalTag, externalTag, categoryValue, + categoryValue, tagTypeToOperators[categoryValue], []bool{true, true, true}, externalTag, externalTag, externalTag, "", false, notSupportOperator, tableName, }) } } else if slices.Contains(tagNativeTagDB, db) { externalTag := "tag." + tagName.(string) response.Values = append(response.Values, []interface{}{ - externalTag, externalTag, externalTag, externalTag, "map_item", - "Native Tag", tagTypeToOperators["string"], []bool{true, true, true}, externalTag, "", false, notSupportOperator, tableName, + externalTag, externalTag, externalTag, externalTag, externalTag, externalTag, "map_item", + "Native Tag", tagTypeToOperators["string"], []bool{true, true, true}, externalTag, externalTag, externalTag, "", false, notSupportOperator, tableName, }) } else { externalTag := "attribute." + tagName.(string) response.Values = append(response.Values, []interface{}{ - externalTag, externalTag, externalTag, externalTag, "map_item", - "Native Tag", tagTypeToOperators["string"], []bool{true, true, true}, externalTag, "", false, notSupportOperator, tableName, + externalTag, externalTag, externalTag, externalTag, externalTag, externalTag, "map_item", + "Native Tag", tagTypeToOperators["string"], []bool{true, true, true}, externalTag, externalTag, externalTag, "", false, notSupportOperator, tableName, }) } } @@ -989,8 +1009,8 @@ func GetDynamicTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, u func GetAlertEventTagDescriptions(staticTag, dynamicTag *common.Result) (response *common.Result, err error) { response = &common.Result{ Columns: []interface{}{ - "name", "client_name", "server_name", "display_name", "type", "category", - "operators", "permissions", "description", "related_tag", "deprecated", "not_supported_operators", "table", + "name", "client_name", "server_name", "display_name", "display_name_zh", "display_name_en", "type", "category", + "operators", "permissions", "description", "description_zh", "description_en", "related_tag", "deprecated", "not_supported_operators", "table", }, Values: []interface{}{}, } @@ -1023,8 +1043,8 @@ func GetTagDescriptions(db, table, rawSql, queryCacheTTL, orgID string, useQuery table = strings.Trim(table, "`") response = &common.Result{ Columns: []interface{}{ - "name", "client_name", "server_name", "display_name", "type", "category", - "operators", "permissions", "description", "related_tag", "deprecated", "not_supported_operators", "table", + "name", "client_name", "server_name", "display_name", "display_name_zh", "display_name_en", "type", "category", + "operators", "permissions", "description", "description_zh", "description_en", "related_tag", "deprecated", "not_supported_operators", "table", }, Values: []interface{}{}, } @@ -1108,7 +1128,7 @@ func GetEnumTagValues(db, table, sql string) (map[string][]interface{}, error) { func GetEnumTags(db, table, sql string) (*common.Result, error) { response := &common.Result{ Columns: []interface{}{ - "name", "client_name", "server_name", "display_name", "type", "category", + "name", "client_name", "server_name", "display_name", "display_name_zh", "display_name_en", "type", "category", "operators", "permissions", "description", "related_tag", "deprecated", "not_supported_operators", "table", }, Values: []interface{}{}, @@ -1121,7 +1141,7 @@ func GetEnumTags(db, table, sql string) (*common.Result, error) { enumTagSlice = append(enumTagSlice, tagDescription.Name) response.Values = append(response.Values, []interface{}{ - tagDescription.Name, tagDescription.ClientName, tagDescription.ServerName, tagDescription.DisplayName, tagDescription.Type, + tagDescription.Name, tagDescription.ClientName, tagDescription.ServerName, tagDescription.DisplayName, tagDescription.DisplayNameZH, tagDescription.DisplayNameEN, tagDescription.Type, tagDescription.Category, tagDescription.Operators, tagDescription.Permissions, tagDescription.Description, tagDescription.RelatedTag, tagDescription.Deprecated, tagDescription.NotSupportedOperators, "", }) } diff --git a/server/querier/router/query.go b/server/querier/router/query.go index a275171b486..c7df1cd602e 100644 --- a/server/querier/router/query.go +++ b/server/querier/router/query.go @@ -48,6 +48,7 @@ func executeQuery() gin.HandlerFunc { args.QueryUUID = c.Query("query_uuid") args.NoPreWhere, _ = strconv.ParseBool(c.DefaultQuery("no_prewhere", "false")) args.ORGID = c.Request.Header.Get(common.HEADER_KEY_X_ORG_ID) + args.Language = c.Request.Header.Get(common.HEADER_KEY_LANGUAGE) // if no org_id in header, set default org id if args.ORGID == "" { args.ORGID = common.DEFAULT_ORG_ID