merge: 合并代码20241211
This commit is contained in:
3
.vscode/extensions.json
vendored
3
.vscode/extensions.json
vendored
@@ -1,3 +0,0 @@
|
||||
{
|
||||
"recommendations": []
|
||||
}
|
||||
25
.vscode/launch.json
vendored
25
.vscode/launch.json
vendored
@@ -18,7 +18,7 @@
|
||||
"type": "go",
|
||||
"request": "launch",
|
||||
"mode": "debug",
|
||||
"program": "d:/local.git/ems.agt/restagent/",
|
||||
"program": "d:/omc.git/be.ems/restagent/",
|
||||
"console": "integratedTerminal"
|
||||
},
|
||||
{
|
||||
@@ -26,16 +26,7 @@
|
||||
"type": "go",
|
||||
"request": "launch",
|
||||
"mode": "debug",
|
||||
"program": "d:/local.git/ems.agt/sshsvc/sshsvc.go",
|
||||
"console": "integratedTerminal"
|
||||
},
|
||||
{
|
||||
"name": "debug loadpconf",
|
||||
"type": "go",
|
||||
"request": "launch",
|
||||
"mode": "debug",
|
||||
"program": "d:/local.git/ems.agt/tools/loadpconf",
|
||||
"args": ["-p","../../config/param/upf_param_config.yaml"],
|
||||
"program": "d:/omc.git/be.ems/sshsvc/sshsvc.go",
|
||||
"console": "integratedTerminal"
|
||||
},
|
||||
{
|
||||
@@ -43,8 +34,16 @@
|
||||
"type": "go",
|
||||
"request": "launch",
|
||||
"mode": "debug",
|
||||
"program": "d:/local.git/ems.agt/crontask",
|
||||
"program": "d:/omc.git/be.ems/crontask",
|
||||
"console": "integratedTerminal"
|
||||
}
|
||||
},
|
||||
{
|
||||
"name": "debug encyaml",
|
||||
"type": "go",
|
||||
"request": "launch",
|
||||
"mode": "debug",
|
||||
"program": "d:/omc.git/be.ems/tools/encode",
|
||||
"console": "integratedTerminal"
|
||||
}
|
||||
]
|
||||
}
|
||||
11
.vscode/settings.json
vendored
11
.vscode/settings.json
vendored
@@ -1,11 +0,0 @@
|
||||
{
|
||||
"go.toolsEnvVars": {
|
||||
"GOARCH": "amd64",
|
||||
"GOOS": "windows"
|
||||
},
|
||||
"go.testEnvVars": {
|
||||
"GOARCH": "wasm",
|
||||
"GOOS": "js"
|
||||
},
|
||||
"commentTranslate.hover.enabled": true
|
||||
}
|
||||
@@ -40,13 +40,14 @@ func (k *KpiCReport) Get(c *gin.Context) {
|
||||
return
|
||||
}
|
||||
if querys.StartTime != "" {
|
||||
conditions = append(conditions, "created_at >= ?")
|
||||
conditions = append(conditions, "(UNIX_TIMESTAMP(created_at) * 1000) >= ?")
|
||||
params = append(params, querys.StartTime)
|
||||
}
|
||||
if querys.EndTime != "" {
|
||||
conditions = append(conditions, "created_at <= ?")
|
||||
conditions = append(conditions, "(UNIX_TIMESTAMP(created_at) * 1000) <= ?")
|
||||
params = append(params, querys.EndTime)
|
||||
}
|
||||
conditions = append(conditions, "kpi_values != 'null'")
|
||||
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
@@ -106,13 +107,14 @@ func (k *KpiCReport) GetReport2FE(c *gin.Context) {
|
||||
return
|
||||
}
|
||||
if querys.StartTime != "" {
|
||||
conditions = append(conditions, "created_at >= ?")
|
||||
conditions = append(conditions, "(UNIX_TIMESTAMP(created_at) * 1000) >= ?")
|
||||
params = append(params, querys.StartTime)
|
||||
}
|
||||
if querys.EndTime != "" {
|
||||
conditions = append(conditions, "created_at <= ?")
|
||||
conditions = append(conditions, "(UNIX_TIMESTAMP(created_at) * 1000) <= ?")
|
||||
params = append(params, querys.EndTime)
|
||||
}
|
||||
conditions = append(conditions, "kpi_values != 'null'")
|
||||
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
@@ -185,13 +187,14 @@ func (k *KpiCReport) GetTotalList(c *gin.Context) {
|
||||
dbg := dborm.DefaultDB().Table(tableName)
|
||||
|
||||
if querys.StartTime != "" {
|
||||
conditions = append(conditions, "created_at >= ?")
|
||||
conditions = append(conditions, "(UNIX_TIMESTAMP(created_at) * 1000) >= ?")
|
||||
params = append(params, querys.StartTime)
|
||||
}
|
||||
if querys.EndTime != "" {
|
||||
conditions = append(conditions, "created_at <= ?")
|
||||
conditions = append(conditions, "(UNIX_TIMESTAMP(created_at) * 1000) <= ?")
|
||||
params = append(params, querys.EndTime)
|
||||
}
|
||||
conditions = append(conditions, "kpi_values != 'null'")
|
||||
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
@@ -253,13 +256,14 @@ func (k *KpiCReport) Total(c *gin.Context) {
|
||||
dbg := dborm.DefaultDB().Table(tableName)
|
||||
|
||||
if querys.StartTime != "" {
|
||||
conditions = append(conditions, "created_at >= ?")
|
||||
conditions = append(conditions, "(UNIX_TIMESTAMP(created_at) * 1000) >= ?")
|
||||
params = append(params, querys.StartTime)
|
||||
}
|
||||
if querys.EndTime != "" {
|
||||
conditions = append(conditions, "created_at <= ?")
|
||||
conditions = append(conditions, "(UNIX_TIMESTAMP(created_at) * 1000) <= ?")
|
||||
params = append(params, querys.EndTime)
|
||||
}
|
||||
conditions = append(conditions, "kpi_values != 'null'")
|
||||
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
|
||||
@@ -3,17 +3,23 @@ package kpi_c_title
|
||||
import (
|
||||
"fmt"
|
||||
"net/http"
|
||||
"regexp"
|
||||
"strconv"
|
||||
"strings"
|
||||
|
||||
"be.ems/lib/dborm"
|
||||
"be.ems/lib/log"
|
||||
"be.ems/lib/services"
|
||||
"be.ems/src/framework/utils/ctx"
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
// get customize kpi total and list
|
||||
func (k *KpiCTitle) GetToalList(c *gin.Context) {
|
||||
var titles []KpiCTitle
|
||||
var conditions []string
|
||||
var params []any
|
||||
i18n := ctx.AcceptLanguage(c)
|
||||
|
||||
var querys KpiCTitleQuery
|
||||
if err := c.ShouldBindQuery(&querys); err != nil {
|
||||
@@ -30,7 +36,10 @@ func (k *KpiCTitle) GetToalList(c *gin.Context) {
|
||||
if status := querys.Status; status != "" {
|
||||
conditions = append(conditions, "status = ?")
|
||||
params = append(params, status)
|
||||
} else {
|
||||
conditions = append(conditions, "status != 'Deleted'")
|
||||
}
|
||||
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
whereSql += strings.Join(conditions, " and ")
|
||||
@@ -62,6 +71,8 @@ func (k *KpiCTitle) GetToalList(c *gin.Context) {
|
||||
return
|
||||
}
|
||||
|
||||
k.expressionAlias(titles, i18n)
|
||||
|
||||
c.JSON(http.StatusOK, services.TotalDataResp(titles, total))
|
||||
//c.JSON(http.StatusOK, titles)
|
||||
}
|
||||
@@ -70,6 +81,7 @@ func (k *KpiCTitle) Get(c *gin.Context) {
|
||||
var titles []KpiCTitle
|
||||
var conditions []string
|
||||
var params []any
|
||||
i18n := ctx.AcceptLanguage(c)
|
||||
|
||||
// construct condition to get
|
||||
if neType := c.Query("neType"); neType != "" {
|
||||
@@ -79,7 +91,10 @@ func (k *KpiCTitle) Get(c *gin.Context) {
|
||||
if status := c.Query("status"); status != "" {
|
||||
conditions = append(conditions, "status = ?")
|
||||
params = append(params, status)
|
||||
} else {
|
||||
conditions = append(conditions, "status != 'Deleted'")
|
||||
}
|
||||
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
whereSql += strings.Join(conditions, " and ")
|
||||
@@ -89,10 +104,38 @@ func (k *KpiCTitle) Get(c *gin.Context) {
|
||||
return
|
||||
}
|
||||
|
||||
k.expressionAlias(titles, i18n)
|
||||
|
||||
c.JSON(http.StatusOK, services.DataResp(titles))
|
||||
//c.JSON(http.StatusOK, titles)
|
||||
}
|
||||
|
||||
// alias customized kpi expression with cn/en title
|
||||
func (k *KpiCTitle) expressionAlias(titles []KpiCTitle, i18n string) {
|
||||
var title *KpiCTitle
|
||||
for i := 0; i < len(titles); i++ {
|
||||
title = &titles[i]
|
||||
title.ExprAlias = *title.Expression
|
||||
re := regexp.MustCompile(`'([^']+)'`)
|
||||
matches := re.FindAllStringSubmatch(title.ExprAlias, -1)
|
||||
|
||||
for _, match := range matches {
|
||||
var alias, sql string
|
||||
if i18n == "zh" {
|
||||
sql = fmt.Sprintf("SELECT cn_title FROM kpi_title WHERE kpi_id='%s'", match[1])
|
||||
} else {
|
||||
sql = fmt.Sprintf("SELECT en_title FROM kpi_title WHERE kpi_id='%s'", match[1])
|
||||
}
|
||||
err := dborm.XCoreDB().QueryRow(sql).Scan(&alias)
|
||||
if err != nil {
|
||||
log.Warn("Failed to QueryRow:", err)
|
||||
continue
|
||||
}
|
||||
title.ExprAlias = regexp.MustCompile(match[1]).ReplaceAllString(title.ExprAlias, alias)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (k *KpiCTitle) Total(c *gin.Context) {
|
||||
var conditions []string
|
||||
var params []any
|
||||
@@ -105,7 +148,10 @@ func (k *KpiCTitle) Total(c *gin.Context) {
|
||||
if status := c.Query("status"); status != "" {
|
||||
conditions = append(conditions, "status = ?")
|
||||
params = append(params, status)
|
||||
} else {
|
||||
conditions = append(conditions, "status != 'Deleted'")
|
||||
}
|
||||
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
whereSql += strings.Join(conditions, " and ")
|
||||
@@ -120,17 +166,49 @@ func (k *KpiCTitle) Total(c *gin.Context) {
|
||||
}
|
||||
|
||||
func (k *KpiCTitle) Post(c *gin.Context) {
|
||||
var title KpiCTitle
|
||||
var title, res KpiCTitle
|
||||
|
||||
if err := c.ShouldBindJSON(&title); err != nil {
|
||||
c.JSON(http.StatusOK, services.ErrResp(err.Error()))
|
||||
return
|
||||
}
|
||||
userName := ctx.LoginUserToUserName(c)
|
||||
title.CreatedBy = &userName
|
||||
result := dborm.DefaultDB().Where("ne_type=? and (kpi_id=? or title=?)", title.NeType, title.KpiID, title.Title).First(&title)
|
||||
if result.RowsAffected > 0 {
|
||||
c.JSON(http.StatusOK, services.ErrResp("custom indicator already exist"))
|
||||
return
|
||||
}
|
||||
|
||||
// Regexp match like AMF.C.01
|
||||
kpiIDRegexp := "^" + *title.NeType + "\\.C\\.[0-9]{2}$"
|
||||
ret := dborm.DefaultDB().Table("kpi_c_title").
|
||||
Where("ne_type=? and kpi_id REGEXP ? ORDER BY kpi_id DESC LIMIT 1", title.NeType, kpiIDRegexp).Scan(&res)
|
||||
if err := ret.Error; err != nil {
|
||||
c.JSON(http.StatusOK, services.ErrResp(err.Error()))
|
||||
return
|
||||
}
|
||||
newKpiID := *title.NeType + ".C" + ".01"
|
||||
if ret.RowsAffected != 0 {
|
||||
maxKpiID := *res.KpiID
|
||||
prefix := maxKpiID[:len(maxKpiID)-2]
|
||||
suffix := maxKpiID[len(maxKpiID)-2:]
|
||||
suffixInt, err := strconv.Atoi(suffix)
|
||||
if err != nil {
|
||||
c.JSON(http.StatusOK, services.ErrResp(err.Error()))
|
||||
return
|
||||
}
|
||||
if suffixInt >= MAX_KPI_C_ID {
|
||||
err := fmt.Errorf("exceed the max customized KPI ID")
|
||||
c.JSON(http.StatusOK, services.ErrResp(err.Error()))
|
||||
return
|
||||
}
|
||||
|
||||
suffixInt++
|
||||
newSuffix := fmt.Sprintf("%02d", suffixInt)
|
||||
newKpiID = prefix + newSuffix
|
||||
}
|
||||
title.KpiID = &newKpiID
|
||||
if err := dborm.DefaultDB().Create(&title).Error; err != nil {
|
||||
c.JSON(http.StatusOK, services.ErrResp(err.Error()))
|
||||
return
|
||||
@@ -178,8 +256,8 @@ func (k *KpiCTitle) Put(c *gin.Context) {
|
||||
func (k *KpiCTitle) Delete(c *gin.Context) {
|
||||
id := c.Param("id")
|
||||
|
||||
if err := dborm.DefaultDB().Delete(&KpiCTitle{}, id).Error; err != nil {
|
||||
c.JSON(http.StatusOK, services.ErrResp("custom indicator not found"))
|
||||
if err := dborm.DefaultDB().Table(k.TableName()).Where("id=?", id).Update("status", "Deleted").Error; err != nil {
|
||||
c.JSON(http.StatusOK, services.ErrResp(err.Error()))
|
||||
return
|
||||
}
|
||||
|
||||
|
||||
@@ -2,12 +2,17 @@ package kpi_c_title
|
||||
|
||||
import "time"
|
||||
|
||||
const (
|
||||
MAX_KPI_C_ID = 99
|
||||
)
|
||||
|
||||
type KpiCTitle struct {
|
||||
ID int `gorm:"column:id;primary_key;auto_increment" json:"id"`
|
||||
NeType *string `gorm:"column:ne_type;default:NULL," json:"neType,omitempty"`
|
||||
KpiID *string `gorm:"column:kpi_id;default:NULL," json:"kpiId,omitempty"`
|
||||
Title *string `gorm:"column:title;default:NULL," json:"title,omitempty"`
|
||||
Expression *string `gorm:"column:expression;default:NULL," json:"expression,omitempty"`
|
||||
ExprAlias string `gorm:"-" json:"exprAlias"`
|
||||
Status string `gorm:"column:status;default:'Active'" json:"status"`
|
||||
Unit *string `gorm:"column:unit" json:"unit,omitempty"`
|
||||
Description *string `gorm:"column:description;default:NULL," json:"description,omitempty"`
|
||||
|
||||
@@ -762,14 +762,14 @@ func GetStateFromNF(w http.ResponseWriter, r *http.Request) {
|
||||
SetHeaders(map[string]string{"Content-Type": "application/json;charset=UTF-8"}).
|
||||
Get(requestURI2NF)
|
||||
if err != nil {
|
||||
log.Error("Get system state from NF is failed:", err)
|
||||
log.Error("Fail to get state:", err)
|
||||
|
||||
errorMessage := services.ErrorMessage{
|
||||
ErrorCode: "1", ErrorInfo: "Internal server error, NF connnect refused",
|
||||
}
|
||||
result["error"] = errorMessage
|
||||
SN, Version, _ := dborm.XormGetNEStateInfo(ne.NeType, ne.NeId)
|
||||
result["serialNum"] = SN
|
||||
result["version"] = Version
|
||||
systemState := make(map[string]interface{})
|
||||
systemState["error"] = errorMessage
|
||||
result["systemState"] = systemState
|
||||
} else {
|
||||
systemState := make(map[string]interface{})
|
||||
_ = json.Unmarshal(resp.Body(), &systemState)
|
||||
@@ -786,49 +786,62 @@ func GetStateFromNF(w http.ResponseWriter, r *http.Request) {
|
||||
response.Data = data
|
||||
services.ResponseWithJson(w, http.StatusOK, response)
|
||||
return
|
||||
}
|
||||
|
||||
if neType == "omc" {
|
||||
} else if neType == "omc" {
|
||||
emsState := GetEMSState("127.0.0.1")
|
||||
services.ResponseWithJson(w, http.StatusOK, emsState)
|
||||
return
|
||||
}
|
||||
|
||||
var neList []dborm.NeInfo
|
||||
err := dborm.XormGetNeInfoByNeType(neType, &neList)
|
||||
if err != nil {
|
||||
log.Error("Failed to dborm.XormGetNeInfoByNeType:", err)
|
||||
services.ResponseInternalServerError500ProcessError(w, err)
|
||||
return
|
||||
}
|
||||
data := make([]map[string]interface{}, 0)
|
||||
for _, ne := range neList {
|
||||
hostUri := fmt.Sprintf("http://%s:%v", ne.Ip, ne.Port)
|
||||
requestURI2NF := fmt.Sprintf("%s/api/rest/systemManagement/v1/elementType/%s/objectType/systemState",
|
||||
hostUri, strings.ToLower(ne.NeType))
|
||||
log.Debug("requestURI2NF:", requestURI2NF)
|
||||
// only support omc and all elementType
|
||||
err := fmt.Errorf("only support omc or all elementTypeValue")
|
||||
log.Error("Fail to get state:", err)
|
||||
services.ResponseInternalServerError500ProcessError(w, err)
|
||||
|
||||
resp, err := client.R().
|
||||
EnableTrace().
|
||||
SetHeaders(map[string]string{"User-Agent": config.GetDefaultUserAgent()}).
|
||||
SetHeaders(map[string]string{"Content-Type": "application/json;charset=UTF-8"}).
|
||||
Get(requestURI2NF)
|
||||
if err != nil {
|
||||
log.Error("Get system state from NF is failed:", err)
|
||||
} else {
|
||||
systemState := make(map[string]interface{})
|
||||
_ = json.Unmarshal(resp.Body(), &systemState)
|
||||
data = append(data, systemState)
|
||||
}
|
||||
}
|
||||
// var neList []dborm.NeInfo
|
||||
// err := dborm.XormGetNeInfoByNeType(neType, &neList)
|
||||
// if err != nil {
|
||||
// log.Error("Failed to dborm.XormGetNeInfoByNeType:", err)
|
||||
// services.ResponseInternalServerError500ProcessError(w, err)
|
||||
// return
|
||||
// }
|
||||
// var omcList []dborm.NeInfo
|
||||
// err = dborm.XormGetNeInfoByNeType("omc", &omcList)
|
||||
// if err != nil {
|
||||
// log.Error("Failed to omc ne list:", err)
|
||||
// services.ResponseInternalServerError500ProcessError(w, err)
|
||||
// return
|
||||
// }
|
||||
// for i, ne := range neList {
|
||||
|
||||
if len(data) == 1 {
|
||||
services.ResponseWithJson(w, http.StatusOK, data[0])
|
||||
return
|
||||
}
|
||||
var response Response
|
||||
response.Data = data
|
||||
services.ResponseWithJson(w, http.StatusOK, response)
|
||||
// }
|
||||
// data := make([]map[string]interface{}, 0)
|
||||
// for _, ne := range neList {
|
||||
// hostUri := fmt.Sprintf("http://%s:%v", ne.Ip, ne.Port)
|
||||
// requestURI2NF := fmt.Sprintf("%s/api/rest/systemManagement/v1/elementType/%s/objectType/systemState",
|
||||
// hostUri, strings.ToLower(ne.NeType))
|
||||
// log.Debug("requestURI2NF:", requestURI2NF)
|
||||
|
||||
// resp, err := client.R().
|
||||
// EnableTrace().
|
||||
// SetHeaders(map[string]string{"User-Agent": config.GetDefaultUserAgent()}).
|
||||
// SetHeaders(map[string]string{"Content-Type": "application/json;charset=UTF-8"}).
|
||||
// Get(requestURI2NF)
|
||||
// if err != nil {
|
||||
// log.Error("Get system state from NF is failed:", err)
|
||||
// } else {
|
||||
// systemState := make(map[string]interface{})
|
||||
// _ = json.Unmarshal(resp.Body(), &systemState)
|
||||
// data = append(data, systemState)
|
||||
// }
|
||||
// }
|
||||
|
||||
// if len(data) == 1 {
|
||||
// services.ResponseWithJson(w, http.StatusOK, data[0])
|
||||
// return
|
||||
// }
|
||||
// var response Response
|
||||
// response.Data = data
|
||||
// services.ResponseWithJson(w, http.StatusOK, response)
|
||||
}
|
||||
|
||||
// GetStateFromNF 旧函数
|
||||
|
||||
@@ -25,7 +25,7 @@ func InitConfig(configFile string) {
|
||||
|
||||
// Get 获取配置信息
|
||||
//
|
||||
// Get("framework.name")
|
||||
// Get("server.port")
|
||||
func Get(key string) any {
|
||||
return v.Get(key)
|
||||
}
|
||||
|
||||
@@ -5,6 +5,7 @@ import (
|
||||
"go/ast"
|
||||
"go/parser"
|
||||
"go/token"
|
||||
"math"
|
||||
"regexp"
|
||||
"strconv"
|
||||
"strings"
|
||||
@@ -29,6 +30,9 @@ func CalcExpr(expr string, paramValues map[string]any) (float64, error) {
|
||||
|
||||
// expression to evaluate
|
||||
result, err := evalExpr(expr)
|
||||
if math.IsNaN(result) {
|
||||
return 0.0, err
|
||||
}
|
||||
return result, err
|
||||
}
|
||||
|
||||
@@ -87,6 +91,10 @@ func evalNode(node ast.Node) (float64, error) {
|
||||
case token.MUL:
|
||||
result = left * right
|
||||
case token.QUO:
|
||||
if right == 0 {
|
||||
return math.NaN(), fmt.Errorf("divisor cannot be zero")
|
||||
}
|
||||
|
||||
result = left / right
|
||||
}
|
||||
case *ast.BasicLit:
|
||||
|
||||
89
lib/log/syslogger.go.bak
Normal file
89
lib/log/syslogger.go.bak
Normal file
@@ -0,0 +1,89 @@
|
||||
//go:build !windows && !nacl && !plan9
|
||||
// +build !windows,!nacl,!plan9
|
||||
|
||||
package log
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"log/syslog"
|
||||
)
|
||||
|
||||
var _ Logger = &SyslogLogger{}
|
||||
|
||||
// SyslogLogger will be depricated
|
||||
type SyslogLogger struct {
|
||||
w *syslog.Writer
|
||||
}
|
||||
|
||||
// NewSyslogLogger implements Logger
|
||||
func NewSyslogLogger(w *syslog.Writer) *SyslogLogger {
|
||||
return &SyslogLogger{w: w}
|
||||
}
|
||||
|
||||
// Trace log content as Trace
|
||||
func (s *SyslogLogger) Trace(v ...interface{}) {
|
||||
_ = s.w.Trace(fmt.Sprint(v...))
|
||||
}
|
||||
|
||||
// Tracef log content as Trace and format
|
||||
func (s *SyslogLogger) Tracef(format string, v ...interface{}) {
|
||||
_ = s.w.Trace(fmt.Sprintf(format, v...))
|
||||
}
|
||||
|
||||
// Debug log content as Debug
|
||||
func (s *SyslogLogger) Debug(v ...interface{}) {
|
||||
_ = s.w.Debug(fmt.Sprint(v...))
|
||||
}
|
||||
|
||||
// Debugf log content as Debug and format
|
||||
func (s *SyslogLogger) Debugf(format string, v ...interface{}) {
|
||||
_ = s.w.Debug(fmt.Sprintf(format, v...))
|
||||
}
|
||||
|
||||
// Error log content as Error
|
||||
func (s *SyslogLogger) Error(v ...interface{}) {
|
||||
_ = s.w.Err(fmt.Sprint(v...))
|
||||
}
|
||||
|
||||
// Errorf log content as Errorf and format
|
||||
func (s *SyslogLogger) Errorf(format string, v ...interface{}) {
|
||||
_ = s.w.Err(fmt.Sprintf(format, v...))
|
||||
}
|
||||
|
||||
// Info log content as Info
|
||||
func (s *SyslogLogger) Info(v ...interface{}) {
|
||||
_ = s.w.Info(fmt.Sprint(v...))
|
||||
}
|
||||
|
||||
// Infof log content as Infof and format
|
||||
func (s *SyslogLogger) Infof(format string, v ...interface{}) {
|
||||
_ = s.w.Info(fmt.Sprintf(format, v...))
|
||||
}
|
||||
|
||||
// Warn log content as Warn
|
||||
func (s *SyslogLogger) Warn(v ...interface{}) {
|
||||
_ = s.w.Warn(fmt.Sprint(v...))
|
||||
}
|
||||
|
||||
// Warnf log content as Warnf and format
|
||||
func (s *SyslogLogger) Warnf(format string, v ...interface{}) {
|
||||
_ = s.w.Warn(fmt.Sprintf(format, v...))
|
||||
}
|
||||
|
||||
// Fatal log content as Fatal
|
||||
func (s *SyslogLogger) Fatal(v ...interface{}) {
|
||||
_ = s.w.Fatal(fmt.Sprint(v...))
|
||||
}
|
||||
|
||||
// Fatalf log content as Fatalf and format
|
||||
func (s *SyslogLogger) Fatalf(format string, v ...interface{}) {
|
||||
_ = s.w.Fatal(fmt.Sprintf(format, v...))
|
||||
}
|
||||
|
||||
// Level shows log level
|
||||
func (s *SyslogLogger) Level() LogLevel {
|
||||
return LOG_NODEF
|
||||
}
|
||||
|
||||
// SetLevel always return error, as current log/syslog package doesn't allow to set priority level after syslog.Writer created
|
||||
func (s *SyslogLogger) SetLevel(l LogLevel) {}
|
||||
@@ -1,7 +1,7 @@
|
||||
# Makefile for rest agent project
|
||||
|
||||
PROJECT = OMC
|
||||
VERSION = 2.2410.4
|
||||
VERSION = 2.2412.1
|
||||
PLATFORM = amd64
|
||||
ARMPLATFORM = aarch64
|
||||
BUILDDIR = ../../build
|
||||
|
||||
Binary file not shown.
BIN
src/assets/dependency/iperf/rpm/iperf-2.1.6-2.el8.aarch64.rpm
Normal file
BIN
src/assets/dependency/iperf/rpm/iperf-2.1.6-2.el8.aarch64.rpm
Normal file
Binary file not shown.
BIN
src/assets/dependency/iperf/rpm/iperf3-3.6-6.ky10.aarch64.rpm
Normal file
BIN
src/assets/dependency/iperf/rpm/iperf3-3.6-6.ky10.aarch64.rpm
Normal file
Binary file not shown.
@@ -142,7 +142,7 @@ func RunTime() time.Time {
|
||||
|
||||
// Get 获取配置信息
|
||||
//
|
||||
// Get("framework.name")
|
||||
// Get("server.port")
|
||||
func Get(key string) any {
|
||||
return viper.Get(key)
|
||||
}
|
||||
|
||||
@@ -1,8 +1,3 @@
|
||||
# 项目信息
|
||||
framework:
|
||||
name: "OMC"
|
||||
version: "2.2410.4"
|
||||
|
||||
# 应用服务配置
|
||||
server:
|
||||
# 服务端口
|
||||
@@ -181,6 +176,10 @@ aes:
|
||||
|
||||
# 用户配置
|
||||
user:
|
||||
# 登录认证,默认打开
|
||||
loginAuth: true
|
||||
# 接口加密,默认打开
|
||||
cryptoApi: true
|
||||
# 密码
|
||||
password:
|
||||
# 密码最大错误次数
|
||||
|
||||
@@ -117,6 +117,9 @@ func DefaultDB() *gorm.DB {
|
||||
|
||||
// 获取数据源
|
||||
func DB(source string) *gorm.DB {
|
||||
if source == "" {
|
||||
source = config.Get("gorm.defaultDataSourceName").(string)
|
||||
}
|
||||
return dbMap[source]
|
||||
}
|
||||
|
||||
|
||||
@@ -24,6 +24,16 @@ import (
|
||||
// 请将中间件放在最前置,对请求优先处理
|
||||
func CryptoApi(requestDecrypt, responseEncrypt bool) gin.HandlerFunc {
|
||||
return func(c *gin.Context) {
|
||||
// 登录认证,默认打开
|
||||
enable := true
|
||||
if v := config.Get("user.cryptoApi"); v != nil && enable {
|
||||
enable = v.(bool)
|
||||
}
|
||||
if !enable {
|
||||
c.Next()
|
||||
return
|
||||
}
|
||||
|
||||
// 请求解密时对请求data注入
|
||||
if requestDecrypt {
|
||||
method := c.Request.Method
|
||||
|
||||
@@ -3,6 +3,7 @@ package middleware
|
||||
import (
|
||||
"strings"
|
||||
|
||||
"be.ems/src/framework/config"
|
||||
AdminConstants "be.ems/src/framework/constants/admin"
|
||||
commonConstants "be.ems/src/framework/constants/common"
|
||||
"be.ems/src/framework/i18n"
|
||||
@@ -36,6 +37,22 @@ var URL_WHITE_LIST = []string{
|
||||
// 同时匹配其中权限 "matchPerms": {"xxx"},
|
||||
func PreAuthorize(options map[string][]string) gin.HandlerFunc {
|
||||
return func(c *gin.Context) {
|
||||
// 登录认证,默认打开
|
||||
enable := true
|
||||
if v := config.Get("user.loginAuth"); v != nil {
|
||||
enable = v.(bool)
|
||||
}
|
||||
if !enable {
|
||||
loginUser, _ := ctxUtils.LoginUser(c)
|
||||
loginUser.UserID = "2"
|
||||
loginUser.User.UserID = "2"
|
||||
loginUser.User.UserName = "admin"
|
||||
loginUser.User.NickName = "admin"
|
||||
c.Set(commonConstants.CTX_LOGIN_USER, loginUser)
|
||||
c.Next()
|
||||
return
|
||||
}
|
||||
|
||||
language := ctxUtils.AcceptLanguage(c)
|
||||
|
||||
requestURI := c.Request.RequestURI
|
||||
|
||||
@@ -59,3 +59,21 @@ func (c *ConnRedis) Close() {
|
||||
c.Client.Close()
|
||||
}
|
||||
}
|
||||
|
||||
// RunCMD 执行单次命令 "GET key"
|
||||
func (c *ConnRedis) RunCMD(cmd string) (any, error) {
|
||||
if c.Client == nil {
|
||||
return "", fmt.Errorf("redis client not connected")
|
||||
}
|
||||
// 写入命令
|
||||
cmdArr := strings.Fields(cmd)
|
||||
if len(cmdArr) == 0 {
|
||||
return "", fmt.Errorf("redis command is empty")
|
||||
}
|
||||
conn := *c.Client
|
||||
args := make([]any, 0)
|
||||
for _, v := range cmdArr {
|
||||
args = append(args, v)
|
||||
}
|
||||
return conn.Do(context.Background(), args...).Result()
|
||||
}
|
||||
|
||||
@@ -4,6 +4,7 @@ import (
|
||||
"context"
|
||||
"fmt"
|
||||
"strings"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"be.ems/src/framework/config"
|
||||
@@ -179,31 +180,22 @@ func GetExpire(source string, key string) (float64, error) {
|
||||
}
|
||||
|
||||
// 获得缓存数据的key列表
|
||||
func GetKeys(source string, pattern string) ([]string, error) {
|
||||
func GetKeys(source string, match string) ([]string, error) {
|
||||
// 数据源
|
||||
rdb := DefaultRDB()
|
||||
if source != "" {
|
||||
rdb = RDB(source)
|
||||
}
|
||||
|
||||
// 初始化变量
|
||||
var keys []string
|
||||
var cursor uint64 = 0
|
||||
keys := make([]string, 0)
|
||||
ctx := context.Background()
|
||||
// 循环遍历获取匹配的键
|
||||
for {
|
||||
// 使用 SCAN 命令获取匹配的键
|
||||
batchKeys, nextCursor, err := rdb.Scan(ctx, cursor, pattern, 1000).Result()
|
||||
if err != nil {
|
||||
logger.Errorf("Failed to scan keys: %v", err)
|
||||
return keys, err
|
||||
}
|
||||
cursor = nextCursor
|
||||
keys = append(keys, batchKeys...)
|
||||
// 当 cursor 为 0,表示遍历完成
|
||||
if cursor == 0 {
|
||||
break
|
||||
}
|
||||
iter := rdb.Scan(ctx, 0, match, 1000).Iterator()
|
||||
if err := iter.Err(); err != nil {
|
||||
logger.Errorf("Failed to scan keys: %v", err)
|
||||
return keys, err
|
||||
}
|
||||
for iter.Next(ctx) {
|
||||
keys = append(keys, iter.Val())
|
||||
}
|
||||
return keys, nil
|
||||
}
|
||||
@@ -261,6 +253,89 @@ func GetHash(source, key string) (map[string]string, error) {
|
||||
return value, nil
|
||||
}
|
||||
|
||||
// 批量获得缓存数据 [key]result
|
||||
func GetHashBatch(source string, keys []string) (map[string]map[string]string, error) {
|
||||
result := make(map[string]map[string]string, 0)
|
||||
if len(keys) == 0 {
|
||||
return result, fmt.Errorf("not keys")
|
||||
}
|
||||
|
||||
// 数据源
|
||||
rdb := DefaultRDB()
|
||||
if source != "" {
|
||||
rdb = RDB(source)
|
||||
}
|
||||
|
||||
// 创建一个有限的并发控制信号通道
|
||||
sem := make(chan struct{}, 10)
|
||||
var wg sync.WaitGroup
|
||||
var mt sync.Mutex
|
||||
batchSize := 1000
|
||||
total := len(keys)
|
||||
if total < batchSize {
|
||||
batchSize = total
|
||||
}
|
||||
|
||||
for i := 0; i < total; i += batchSize {
|
||||
wg.Add(1)
|
||||
go func(start int) {
|
||||
ctx := context.Background()
|
||||
// 并发控制,限制同时执行的 Goroutine 数量
|
||||
sem <- struct{}{}
|
||||
defer func() {
|
||||
<-sem
|
||||
ctx.Done()
|
||||
wg.Done()
|
||||
}()
|
||||
|
||||
// 检查索引是否越界
|
||||
end := start + batchSize
|
||||
if end > total {
|
||||
end = total
|
||||
}
|
||||
pipe := rdb.Pipeline()
|
||||
for _, key := range keys[start:end] {
|
||||
pipe.HGetAll(ctx, key)
|
||||
}
|
||||
|
||||
cmds, err := pipe.Exec(ctx)
|
||||
if err != nil {
|
||||
logger.Errorf("Failed to get hash batch exec err: %v", err)
|
||||
return
|
||||
}
|
||||
|
||||
// 将结果添加到 result map 并发访问
|
||||
mt.Lock()
|
||||
defer mt.Unlock()
|
||||
|
||||
// 处理命令结果
|
||||
for _, cmd := range cmds {
|
||||
if cmd.Err() != nil {
|
||||
logger.Errorf("Failed to get hash batch cmds err: %v", cmd.Err())
|
||||
continue
|
||||
}
|
||||
// 将结果转换为 *redis.StringStringMapCmd 类型
|
||||
rcmd, ok := cmd.(*redis.MapStringStringCmd)
|
||||
if !ok {
|
||||
logger.Errorf("Failed to get hash batch type err: %v", cmd.Err())
|
||||
continue
|
||||
}
|
||||
|
||||
key := "-"
|
||||
args := rcmd.Args()
|
||||
if len(args) > 0 {
|
||||
key = fmt.Sprint(args[1])
|
||||
}
|
||||
|
||||
result[key] = rcmd.Val()
|
||||
}
|
||||
}(i)
|
||||
}
|
||||
|
||||
wg.Wait()
|
||||
return result, nil
|
||||
}
|
||||
|
||||
// 判断是否存在
|
||||
func Has(source string, keys ...string) (bool, error) {
|
||||
// 数据源
|
||||
|
||||
@@ -3,7 +3,7 @@ package controller
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"be.ems/src/framework/config"
|
||||
libGlobal "be.ems/lib/global"
|
||||
"be.ems/src/framework/vo/result"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
@@ -21,8 +21,8 @@ type IndexController struct{}
|
||||
//
|
||||
// GET /
|
||||
func (s *IndexController) Handler(c *gin.Context) {
|
||||
name := config.Get("framework.name").(string)
|
||||
version := config.Get("framework.version").(string)
|
||||
name := "OMC"
|
||||
version := libGlobal.Version
|
||||
// str := "欢迎使用%s核心网管理平台,当前版本:%s,请通过前台地址访问。"
|
||||
str := "Welcome to the %s Core Network Management Platform, current version: %s, please access via the frontend address."
|
||||
c.JSON(200, result.OkMsg(fmt.Sprintf(str, name, version)))
|
||||
|
||||
@@ -30,7 +30,6 @@ func (s *CommontImpl) SystemConfigInfo() map[string]string {
|
||||
// 获取打包注入的全局变量信息
|
||||
infoMap["version"] = global.Version
|
||||
infoMap["buildTime"] = global.BuildTime
|
||||
infoMap["goVer"] = global.GoVer
|
||||
// 系统首次使用标记
|
||||
launchInfo := machine.LaunchInfo
|
||||
if launchInfo != nil {
|
||||
@@ -42,6 +41,8 @@ func (s *CommontImpl) SystemConfigInfo() map[string]string {
|
||||
} else {
|
||||
infoMap[common.LAUNCH_BOOTLOADER] = "true"
|
||||
}
|
||||
// 用户登录认证
|
||||
infoMap["loginAuth"] = fmt.Sprint(config.Get("user.loginAuth"))
|
||||
// 序列号
|
||||
infoMap["serialNum"] = fmt.Sprint(config.Get("omc.sn"))
|
||||
// 获取LOGO类型
|
||||
|
||||
@@ -55,8 +55,8 @@ func (s *UDMAuthController) ResetData(c *gin.Context) {
|
||||
// GET /list
|
||||
func (s *UDMAuthController) List(c *gin.Context) {
|
||||
querys := ctx.QueryMap(c)
|
||||
data := s.udmAuthService.SelectPage(querys)
|
||||
c.JSON(200, result.Ok(data))
|
||||
total, rows := s.udmAuthService.SelectPage(querys)
|
||||
c.JSON(200, result.Ok(map[string]any{"total": total, "rows": rows}))
|
||||
}
|
||||
|
||||
// UDM鉴权用户信息
|
||||
@@ -364,13 +364,12 @@ func (s *UDMAuthController) Export(c *gin.Context) {
|
||||
|
||||
querys["pageNum"] = 1
|
||||
querys["pageSize"] = 10000
|
||||
data := s.udmAuthService.SelectPage(querys)
|
||||
if parse.Number(data["total"]) == 0 {
|
||||
total, rows := s.udmAuthService.SelectPage(querys)
|
||||
if total == 0 {
|
||||
// 导出数据记录为空
|
||||
c.JSON(200, result.ErrMsg(i18n.TKey(language, "app.common.exportEmpty")))
|
||||
return
|
||||
}
|
||||
rows := data["rows"].([]model.UDMAuthUser)
|
||||
|
||||
// rows := s.udmAuthService.SelectList(model.UDMAuthUser{NeId: neId})
|
||||
if len(rows) <= 0 {
|
||||
|
||||
@@ -54,8 +54,8 @@ func (s *UDMSubController) ResetData(c *gin.Context) {
|
||||
// GET /list
|
||||
func (s *UDMSubController) List(c *gin.Context) {
|
||||
querys := ctx.QueryMap(c)
|
||||
data := s.udmSubService.SelectPage(querys)
|
||||
c.JSON(200, result.Ok(data))
|
||||
total, rows := s.udmSubService.SelectPage(querys)
|
||||
c.JSON(200, result.Ok(map[string]any{"total": total, "rows": rows}))
|
||||
}
|
||||
|
||||
// UDM签约用户信息
|
||||
@@ -188,10 +188,9 @@ func (s *UDMSubController) Adds(c *gin.Context) {
|
||||
// 发送MML
|
||||
cmd := fmt.Sprintf("baa udmuser:start_imsi=%s,start_msisdn=%s,sub_num=%s,", body.IMSI, body.MSISDN, num)
|
||||
cmd += s.udmSubService.ParseCommandParams(body)
|
||||
// static_ip指给4G UE分配的静态IP,没有可不带此字段名,批量添加IP会自动递增
|
||||
if body.StaticIp != "" {
|
||||
cmd += fmt.Sprintf(",static_ip=%s", body.StaticIp)
|
||||
}
|
||||
// 去除msisdn参数,避免重复
|
||||
omemsisdn := fmt.Sprintf(",msisdn=%s,", body.MSISDN)
|
||||
cmd = strings.Replace(cmd, omemsisdn, ",", 1)
|
||||
data, err := telnet.ConvertToStr(telnetClient, cmd)
|
||||
if err != nil {
|
||||
c.JSON(200, result.ErrMsg(err.Error()))
|
||||
@@ -369,13 +368,12 @@ func (s *UDMSubController) Export(c *gin.Context) {
|
||||
|
||||
querys["pageNum"] = 1
|
||||
querys["pageSize"] = 10000
|
||||
data := s.udmSubService.SelectPage(querys)
|
||||
if parse.Number(data["total"]) == 0 {
|
||||
total, rows := s.udmSubService.SelectPage(querys)
|
||||
if total == 0 {
|
||||
// 导出数据记录为空
|
||||
c.JSON(200, result.ErrMsg(i18n.TKey(language, "app.common.exportEmpty")))
|
||||
return
|
||||
}
|
||||
rows := data["rows"].([]model.UDMSubUser)
|
||||
|
||||
// rows := s.udmSubService.SelectList(model.UDMSubUser{NeId: neId})
|
||||
if len(rows) <= 0 {
|
||||
|
||||
@@ -7,7 +7,7 @@ type CDREventIMS struct {
|
||||
ID string `json:"id" gorm:"column:id;primaryKey;autoIncrement"`
|
||||
NeType string `json:"neType" gorm:"column:ne_type"`
|
||||
NeName string `json:"neName" gorm:"column:ne_name"`
|
||||
RmUID string `json:"rmUID" gorm:"column:rm_uid"` // 可能没有
|
||||
RmUID string `json:"rmUID" gorm:"column:rm_uid"`
|
||||
Timestamp int64 `json:"timestamp" gorm:"column:timestamp"`
|
||||
CDRJSONStr string `json:"cdrJSON" gorm:"column:cdr_json"`
|
||||
CreatedAt time.Time `json:"createdAt" gorm:"column:created_at;default:CURRENT_TIMESTAMP"`
|
||||
@@ -18,7 +18,7 @@ type CDREventIMSQuery struct {
|
||||
NeType string `json:"neType" form:"neType" binding:"required"` // 网元类型IMS
|
||||
NeID string `json:"neId" form:"neId" binding:"required"`
|
||||
RmUID string `json:"rmUID" form:"rmUID"`
|
||||
RecordType string `json:"recordType" form:"recordType"` // 记录行为 MOC MTC MOSM MTSM
|
||||
RecordType string `json:"recordType" form:"recordType"` // 记录行为 MOC MTC
|
||||
CallerParty string `json:"callerParty" form:"callerParty"` // 主叫号码
|
||||
CalledParty string `json:"calledParty" form:"calledParty"` // 被叫号码
|
||||
StartTime string `json:"startTime" form:"startTime"`
|
||||
|
||||
@@ -1,120 +1,57 @@
|
||||
package repository
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
|
||||
"be.ems/src/framework/datasource"
|
||||
"be.ems/src/framework/logger"
|
||||
"be.ems/src/framework/utils/parse"
|
||||
"be.ems/src/framework/utils/repo"
|
||||
"be.ems/src/modules/network_data/model"
|
||||
)
|
||||
|
||||
// 实例化数据层 UDMAuthUser 结构体
|
||||
var NewUDMAuthUser = &UDMAuthUser{
|
||||
selectSql: `select id, imsi, ne_id, amf, status, ki, algo_index, opc from u_auth_user`,
|
||||
|
||||
resultMap: map[string]string{
|
||||
"id": "ID",
|
||||
"imsi": "IMSI",
|
||||
"ne_id": "NeId",
|
||||
"amf": "Amf",
|
||||
"status": "Status",
|
||||
"ki": "Ki",
|
||||
"algo_index": "AlgoIndex",
|
||||
"opc": "Opc",
|
||||
},
|
||||
}
|
||||
var NewUDMAuthUser = &UDMAuthUser{}
|
||||
|
||||
// UDMAuthUser UDM鉴权信息表 数据层处理
|
||||
type UDMAuthUser struct {
|
||||
// 查询视图对象SQL
|
||||
selectSql string
|
||||
// 结果字段与实体映射
|
||||
resultMap map[string]string
|
||||
}
|
||||
|
||||
// convertResultRows 将结果记录转实体结果组
|
||||
func (r *UDMAuthUser) convertResultRows(rows []map[string]any) []model.UDMAuthUser {
|
||||
arr := make([]model.UDMAuthUser, 0)
|
||||
for _, row := range rows {
|
||||
item := model.UDMAuthUser{}
|
||||
for key, value := range row {
|
||||
if keyMapper, ok := r.resultMap[key]; ok {
|
||||
repo.SetFieldValue(&item, keyMapper, value)
|
||||
}
|
||||
}
|
||||
arr = append(arr, item)
|
||||
}
|
||||
return arr
|
||||
}
|
||||
type UDMAuthUser struct{}
|
||||
|
||||
// ClearAndInsert 清空ne_id后新增实体
|
||||
func (r *UDMAuthUser) ClearAndInsert(neId string, uArr []model.UDMAuthUser) int64 {
|
||||
// 不指定neID时,用 TRUNCATE 清空表快
|
||||
// _, err := datasource.ExecDB("", "TRUNCATE TABLE u_auth_user", nil)
|
||||
_, err := datasource.ExecDB("", "DELETE FROM u_auth_user WHERE ne_id = ?", []any{neId})
|
||||
if err != nil {
|
||||
logger.Errorf("TRUNCATE err => %v", err)
|
||||
result := datasource.DB("").Where("ne_id = ?", neId).Unscoped().Delete(&model.UDMAuthUser{})
|
||||
if result.Error != nil {
|
||||
logger.Errorf("Delete err => %v", result.Error)
|
||||
}
|
||||
return r.Inserts(uArr)
|
||||
}
|
||||
|
||||
// SelectPage 根据条件分页查询
|
||||
func (r *UDMAuthUser) SelectPage(query map[string]any) map[string]any {
|
||||
func (r *UDMAuthUser) SelectPage(query map[string]any) (int64, []model.UDMAuthUser) {
|
||||
tx := datasource.DB("").Model(&model.UDMAuthUser{})
|
||||
// 查询条件拼接
|
||||
var conditions []string
|
||||
var params []any
|
||||
if v, ok := query["imsi"]; ok && v != "" {
|
||||
conditions = append(conditions, "imsi like concat(concat('%', ?), '%')")
|
||||
params = append(params, strings.Trim(v.(string), " "))
|
||||
tx = tx.Where("imsi like concat(concat('%',?), '%')", v)
|
||||
}
|
||||
if v, ok := query["neId"]; ok && v != "" {
|
||||
conditions = append(conditions, "ne_id = ?")
|
||||
params = append(params, v)
|
||||
tx = tx.Where("ne_id =?", v)
|
||||
}
|
||||
if v, ok := query["imsis"]; ok && v != "" {
|
||||
placeholder := repo.KeyPlaceholderByQuery(len(v.([]any)))
|
||||
conditions = append(conditions, fmt.Sprintf("imsi in (%s)", placeholder))
|
||||
for _, v := range v.([]any) {
|
||||
params = append(params, v.(string))
|
||||
}
|
||||
tx = tx.Where("imsi in ?", v)
|
||||
}
|
||||
|
||||
// 构建查询条件语句
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
whereSql += " where " + strings.Join(conditions, " and ")
|
||||
}
|
||||
|
||||
result := map[string]any{
|
||||
"total": 0,
|
||||
"rows": []model.UDMAuthUser{},
|
||||
}
|
||||
var total int64 = 0
|
||||
rows := []model.UDMAuthUser{}
|
||||
|
||||
// 查询数量 长度为0直接返回
|
||||
totalSql := "select count(1) as 'total' from u_auth_user"
|
||||
totalRows, err := datasource.RawDB("", totalSql+whereSql, params)
|
||||
if err != nil {
|
||||
if err := tx.Count(&total).Error; err != nil || total <= 0 {
|
||||
logger.Errorf("total err => %v", err)
|
||||
return result
|
||||
}
|
||||
total := parse.Number(totalRows[0]["total"])
|
||||
if total == 0 {
|
||||
return result
|
||||
} else {
|
||||
result["total"] = total
|
||||
return total, rows
|
||||
}
|
||||
|
||||
// 分页
|
||||
pageNum, pageSize := repo.PageNumSize(query["pageNum"], query["pageSize"])
|
||||
pageSql := " limit ?,? "
|
||||
params = append(params, pageNum*pageSize)
|
||||
params = append(params, pageSize)
|
||||
tx = tx.Offset(int(pageNum * pageSize)).Limit(int(pageSize))
|
||||
|
||||
// 排序
|
||||
orderSql := ""
|
||||
if v, ok := query["sortField"]; ok && v != "" {
|
||||
sortSql := v.(string)
|
||||
if o, ok := query["sortOrder"]; ok && o != nil && v != "" {
|
||||
@@ -124,71 +61,52 @@ func (r *UDMAuthUser) SelectPage(query map[string]any) map[string]any {
|
||||
sortSql += " asc "
|
||||
}
|
||||
}
|
||||
orderSql = fmt.Sprintf(" order by %s ", sortSql)
|
||||
tx = tx.Order(sortSql)
|
||||
}
|
||||
|
||||
// 查询数据
|
||||
querySql := r.selectSql + whereSql + orderSql + pageSql
|
||||
results, err := datasource.RawDB("", querySql, params)
|
||||
if err != nil {
|
||||
if err := tx.Find(&rows).Error; err != nil {
|
||||
logger.Errorf("query err => %v", err)
|
||||
}
|
||||
|
||||
// 转换实体
|
||||
result["rows"] = r.convertResultRows(results)
|
||||
return result
|
||||
return total, rows
|
||||
}
|
||||
|
||||
// SelectList 根据实体查询
|
||||
func (r *UDMAuthUser) SelectList(u model.UDMAuthUser) []model.UDMAuthUser {
|
||||
tx := datasource.DB("").Model(&model.UDMAuthUser{})
|
||||
// 查询条件拼接
|
||||
var conditions []string
|
||||
var params []any
|
||||
if u.IMSI != "" {
|
||||
conditions = append(conditions, "imsi = ?")
|
||||
params = append(params, u.IMSI)
|
||||
tx = tx.Where("imsi = ?", u.IMSI)
|
||||
}
|
||||
if u.NeId != "" {
|
||||
conditions = append(conditions, "ne_id = ?")
|
||||
params = append(params, u.NeId)
|
||||
}
|
||||
|
||||
// 构建查询条件语句
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
whereSql += " where " + strings.Join(conditions, " and ")
|
||||
tx = tx.Where("ne_id = ?", u.NeId)
|
||||
}
|
||||
|
||||
// 查询数据
|
||||
querySql := r.selectSql + whereSql + " order by imsi asc "
|
||||
results, err := datasource.RawDB("", querySql, params)
|
||||
if err != nil {
|
||||
arr := []model.UDMAuthUser{}
|
||||
if err := tx.Order("imsi asc").Find(&arr).Error; err != nil {
|
||||
logger.Errorf("query err => %v", err)
|
||||
}
|
||||
|
||||
// 转换实体
|
||||
return r.convertResultRows(results)
|
||||
return arr
|
||||
}
|
||||
|
||||
// SelectByIMSIAndNeID 通过imsi和ne_id查询
|
||||
func (r *UDMAuthUser) SelectByIMSIAndNeID(imsi, neId string) model.UDMAuthUser {
|
||||
querySql := r.selectSql + " where imsi = ? and ne_id = ?"
|
||||
results, err := datasource.RawDB("", querySql, []any{imsi, neId})
|
||||
if err != nil {
|
||||
tx := datasource.DB("").Model(&model.UDMAuthUser{})
|
||||
item := model.UDMAuthUser{}
|
||||
// 查询条件拼接
|
||||
tx = tx.Where("imsi = ? and ne_id = ?", imsi, neId)
|
||||
// 查询数据
|
||||
if err := tx.Order("imsi asc").Limit(1).Find(&item).Error; err != nil {
|
||||
logger.Errorf("query err => %v", err)
|
||||
return model.UDMAuthUser{}
|
||||
}
|
||||
// 转换实体
|
||||
rows := r.convertResultRows(results)
|
||||
if len(rows) > 0 {
|
||||
return rows[0]
|
||||
}
|
||||
return model.UDMAuthUser{}
|
||||
return item
|
||||
}
|
||||
|
||||
// Insert 批量添加
|
||||
func (r *UDMAuthUser) Inserts(uArr []model.UDMAuthUser) int64 {
|
||||
tx := datasource.DefaultDB().CreateInBatches(uArr, 3000)
|
||||
tx := datasource.DB("").CreateInBatches(uArr, 3000)
|
||||
if err := tx.Error; err != nil {
|
||||
logger.Errorf("CreateInBatches err => %v", err)
|
||||
}
|
||||
|
||||
@@ -1,156 +1,60 @@
|
||||
package repository
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
|
||||
"be.ems/src/framework/datasource"
|
||||
"be.ems/src/framework/logger"
|
||||
"be.ems/src/framework/utils/parse"
|
||||
"be.ems/src/framework/utils/repo"
|
||||
"be.ems/src/modules/network_data/model"
|
||||
)
|
||||
|
||||
// 实例化数据层 UDMSubUser 结构体
|
||||
var NewUDMSub = &UDMSubUser{
|
||||
selectSql: `select
|
||||
id, imsi, msisdn, ne_id,
|
||||
am_dat, ambr, nssai, rat, arfb, sar, cn_type, rfsp_index, reg_timer, ue_usage_type, active_time, mico, odb_ps, group_id,
|
||||
eps_dat, eps_flag, eps_odb, hplmn_odb, ard, epstpl, context_id, apn_mum, apn_context, static_ip,
|
||||
sm_data, smf_sel, cag
|
||||
from u_sub_user`,
|
||||
|
||||
resultMap: map[string]string{
|
||||
"id": "ID",
|
||||
"imsi": "IMSI",
|
||||
"msisdn": "MSISDN",
|
||||
"ne_id": "NeId",
|
||||
|
||||
"am_dat": "AmDat",
|
||||
"ambr": "UeAmbrTpl",
|
||||
"nssai": "NssaiTpl",
|
||||
"rat": "RatRestrictions",
|
||||
"arfb": "AreaForbiddenTpl",
|
||||
"sar": "ServiceAreaRestrictionTpl",
|
||||
"cn_type": "CnTypeRestrictions",
|
||||
"rfsp_index": "RfspIndex",
|
||||
"reg_timer": "SubsRegTime",
|
||||
"ue_usage_type": "UeUsageType",
|
||||
"active_time": "ActiveTime",
|
||||
"mico": "MicoAllowed",
|
||||
"odb_ps": "OdbPs",
|
||||
"group_id": "GroupId",
|
||||
|
||||
"eps_dat": "EpsDat",
|
||||
"eps_flag": "EpsFlag",
|
||||
"eps_odb": "EpsOdb",
|
||||
"hplmn_odb": "HplmnOdb",
|
||||
"ard": "Ard",
|
||||
"epstpl": "Epstpl",
|
||||
"context_id": "ContextId",
|
||||
"apn_mum": "ApnNum",
|
||||
"apn_context": "ApnContext",
|
||||
"static_ip": "StaticIp",
|
||||
|
||||
"sm_data": "SmData",
|
||||
"smf_sel": "SmfSel",
|
||||
"cag": "Cag",
|
||||
},
|
||||
}
|
||||
var NewUDMSub = &UDMSubUser{}
|
||||
|
||||
// UDMSubUser UDM签约信息表 数据层处理
|
||||
type UDMSubUser struct {
|
||||
// 查询视图对象SQL
|
||||
selectSql string
|
||||
// 结果字段与实体映射
|
||||
resultMap map[string]string
|
||||
}
|
||||
|
||||
// convertResultRows 将结果记录转实体结果组
|
||||
func (r *UDMSubUser) convertResultRows(rows []map[string]any) []model.UDMSubUser {
|
||||
arr := make([]model.UDMSubUser, 0)
|
||||
for _, row := range rows {
|
||||
item := model.UDMSubUser{}
|
||||
for key, value := range row {
|
||||
if keyMapper, ok := r.resultMap[key]; ok {
|
||||
repo.SetFieldValue(&item, keyMapper, value)
|
||||
}
|
||||
}
|
||||
arr = append(arr, item)
|
||||
}
|
||||
return arr
|
||||
}
|
||||
type UDMSubUser struct{}
|
||||
|
||||
// ClearAndInsert 清空ne_id后新增实体
|
||||
func (r *UDMSubUser) ClearAndInsert(neId string, u []model.UDMSubUser) int64 {
|
||||
// 不指定neID时,用 TRUNCATE 清空表快
|
||||
// _, err := datasource.ExecDB("", "TRUNCATE TABLE u_sub_user", nil)
|
||||
_, err := datasource.ExecDB("", "DELETE FROM u_sub_user WHERE ne_id = ?", []any{neId})
|
||||
if err != nil {
|
||||
logger.Errorf("TRUNCATE err => %v", err)
|
||||
result := datasource.DB("").Where("ne_id = ?", neId).Unscoped().Delete(&model.UDMSubUser{})
|
||||
if result.Error != nil {
|
||||
logger.Errorf("Delete err => %v", result.Error)
|
||||
}
|
||||
|
||||
return r.Inserts(u)
|
||||
}
|
||||
|
||||
// SelectPage 根据条件分页查询字典类型
|
||||
func (r *UDMSubUser) SelectPage(query map[string]any) map[string]any {
|
||||
func (r *UDMSubUser) SelectPage(query map[string]any) (int64, []model.UDMSubUser) {
|
||||
tx := datasource.DB("").Model(&model.UDMSubUser{})
|
||||
// 查询条件拼接
|
||||
var conditions []string
|
||||
var params []any
|
||||
if v, ok := query["imsi"]; ok && v != "" {
|
||||
conditions = append(conditions, "imsi like concat(concat('%', ?), '%')")
|
||||
params = append(params, strings.Trim(v.(string), " "))
|
||||
tx = tx.Where("imsi like concat(concat('%', ?), '%')", v)
|
||||
}
|
||||
if v, ok := query["msisdn"]; ok && v != "" {
|
||||
conditions = append(conditions, "msisdn like concat(concat('%', ?), '%')")
|
||||
params = append(params, strings.Trim(v.(string), " "))
|
||||
tx = tx.Where("msisdn like concat(concat('%', ?), '%')", v)
|
||||
}
|
||||
if v, ok := query["neId"]; ok && v != "" {
|
||||
conditions = append(conditions, "ne_id = ?")
|
||||
params = append(params, v)
|
||||
tx = tx.Where("ne_id =?", v)
|
||||
}
|
||||
if v, ok := query["imsis"]; ok && v != "" {
|
||||
placeholder := repo.KeyPlaceholderByQuery(len(v.([]any)))
|
||||
conditions = append(conditions, fmt.Sprintf("imsi in (%s)", placeholder))
|
||||
for _, v := range v.([]any) {
|
||||
params = append(params, v.(string))
|
||||
}
|
||||
tx = tx.Where("imsi in ?", v)
|
||||
}
|
||||
|
||||
// 构建查询条件语句
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
whereSql += " where " + strings.Join(conditions, " and ")
|
||||
}
|
||||
|
||||
result := map[string]any{
|
||||
"total": 0,
|
||||
"rows": []model.UDMSubUser{},
|
||||
}
|
||||
var total int64 = 0
|
||||
rows := []model.UDMSubUser{}
|
||||
|
||||
// 查询数量 长度为0直接返回
|
||||
totalSql := "select count(1) as 'total' from u_sub_user"
|
||||
totalRows, err := datasource.RawDB("", totalSql+whereSql, params)
|
||||
if err != nil {
|
||||
if err := tx.Count(&total).Error; err != nil || total <= 0 {
|
||||
logger.Errorf("total err => %v", err)
|
||||
return result
|
||||
}
|
||||
total := parse.Number(totalRows[0]["total"])
|
||||
if total == 0 {
|
||||
return result
|
||||
} else {
|
||||
result["total"] = total
|
||||
return total, rows
|
||||
}
|
||||
|
||||
// 分页
|
||||
pageNum, pageSize := repo.PageNumSize(query["pageNum"], query["pageSize"])
|
||||
pageSql := " limit ?,? "
|
||||
params = append(params, pageNum*pageSize)
|
||||
params = append(params, pageSize)
|
||||
tx = tx.Offset(int(pageNum * pageSize)).Limit(int(pageSize))
|
||||
|
||||
// 排序
|
||||
orderSql := ""
|
||||
if v, ok := query["sortField"]; ok && v != "" {
|
||||
sortSql := v.(string)
|
||||
if o, ok := query["sortOrder"]; ok && o != nil && v != "" {
|
||||
@@ -160,72 +64,52 @@ func (r *UDMSubUser) SelectPage(query map[string]any) map[string]any {
|
||||
sortSql += " asc "
|
||||
}
|
||||
}
|
||||
orderSql = fmt.Sprintf(" order by %s ", sortSql)
|
||||
tx = tx.Order(sortSql)
|
||||
}
|
||||
|
||||
// 查询数据
|
||||
querySql := r.selectSql + whereSql + orderSql + pageSql
|
||||
results, err := datasource.RawDB("", querySql, params)
|
||||
if err != nil {
|
||||
if err := tx.Find(&rows).Error; err != nil {
|
||||
logger.Errorf("query err => %v", err)
|
||||
return result
|
||||
}
|
||||
|
||||
// 转换实体
|
||||
result["rows"] = r.convertResultRows(results)
|
||||
return result
|
||||
return total, rows
|
||||
}
|
||||
|
||||
// SelectList 根据实体查询
|
||||
func (r *UDMSubUser) SelectList(u model.UDMSubUser) []model.UDMSubUser {
|
||||
tx := datasource.DB("").Model(&model.UDMSubUser{})
|
||||
// 查询条件拼接
|
||||
var conditions []string
|
||||
var params []any
|
||||
if u.IMSI != "" {
|
||||
conditions = append(conditions, "imsi = ?")
|
||||
params = append(params, u.IMSI)
|
||||
tx = tx.Where("imsi = ?", u.IMSI)
|
||||
}
|
||||
if u.NeId != "" {
|
||||
conditions = append(conditions, "ne_id = ?")
|
||||
params = append(params, u.NeId)
|
||||
}
|
||||
|
||||
// 构建查询条件语句
|
||||
whereSql := ""
|
||||
if len(conditions) > 0 {
|
||||
whereSql += " where " + strings.Join(conditions, " and ")
|
||||
tx = tx.Where("ne_id = ?", u.NeId)
|
||||
}
|
||||
|
||||
// 查询数据
|
||||
querySql := r.selectSql + whereSql + " order by imsi asc "
|
||||
results, err := datasource.RawDB("", querySql, params)
|
||||
if err != nil {
|
||||
arr := []model.UDMSubUser{}
|
||||
if err := tx.Order("imsi asc").Find(&arr).Error; err != nil {
|
||||
logger.Errorf("query err => %v", err)
|
||||
}
|
||||
|
||||
// 转换实体
|
||||
return r.convertResultRows(results)
|
||||
return arr
|
||||
}
|
||||
|
||||
// SelectByIMSIAndNeID 通过imsi和ne_id查询
|
||||
func (r *UDMSubUser) SelectByIMSIAndNeID(imsi, neId string) model.UDMSubUser {
|
||||
querySql := r.selectSql + " where imsi = ? and ne_id = ?"
|
||||
results, err := datasource.RawDB("", querySql, []any{imsi, neId})
|
||||
if err != nil {
|
||||
tx := datasource.DB("").Model(&model.UDMSubUser{})
|
||||
item := model.UDMSubUser{}
|
||||
// 查询条件拼接
|
||||
tx = tx.Where("imsi = ? and ne_id = ?", imsi, neId)
|
||||
// 查询数据
|
||||
if err := tx.Order("imsi asc").Limit(1).Find(&item).Error; err != nil {
|
||||
logger.Errorf("query err => %v", err)
|
||||
return model.UDMSubUser{}
|
||||
}
|
||||
// 转换实体
|
||||
rows := r.convertResultRows(results)
|
||||
if len(rows) > 0 {
|
||||
return rows[0]
|
||||
}
|
||||
return model.UDMSubUser{}
|
||||
return item
|
||||
}
|
||||
|
||||
// Insert 批量添加
|
||||
func (r *UDMSubUser) Inserts(uArr []model.UDMSubUser) int64 {
|
||||
tx := datasource.DefaultDB().CreateInBatches(uArr, 2000)
|
||||
tx := datasource.DB("").CreateInBatches(uArr, 2000)
|
||||
if err := tx.Error; err != nil {
|
||||
logger.Errorf("CreateInBatches err => %v", err)
|
||||
}
|
||||
|
||||
@@ -43,14 +43,18 @@ func (r *UDMAuthUser) dataByRedis(imsi, neId string) []model.UDMAuthUser {
|
||||
if err != nil {
|
||||
return arr
|
||||
}
|
||||
for _, key := range ausfArr {
|
||||
m, err := redis.GetHash(source, key)
|
||||
if err != nil {
|
||||
mkv, err := redis.GetHashBatch(source, ausfArr)
|
||||
if err != nil {
|
||||
return arr
|
||||
}
|
||||
|
||||
for k, m := range mkv {
|
||||
if k == "-" {
|
||||
continue
|
||||
}
|
||||
|
||||
// 跳过-号数据 ausf:360000100000130
|
||||
imsi := key[5:]
|
||||
imsi := k[5:]
|
||||
if strings.Contains(imsi, "-") {
|
||||
continue
|
||||
}
|
||||
@@ -97,7 +101,7 @@ func (r *UDMAuthUser) ParseInfo(imsi, neId string, data map[string]string) model
|
||||
}
|
||||
|
||||
// SelectPage 分页查询数据库
|
||||
func (r *UDMAuthUser) SelectPage(query map[string]any) map[string]any {
|
||||
func (r *UDMAuthUser) SelectPage(query map[string]any) (int64, []model.UDMAuthUser) {
|
||||
return r.udmAuthRepository.SelectPage(query)
|
||||
}
|
||||
|
||||
|
||||
@@ -44,14 +44,24 @@ func (r *UDMSubUser) dataByRedis(imsi, neId string) []model.UDMSubUser {
|
||||
if err != nil {
|
||||
return arr
|
||||
}
|
||||
for _, key := range udmsdArr {
|
||||
m, err := redis.GetHash(source, key)
|
||||
if err != nil {
|
||||
mkv, err := redis.GetHashBatch(source, udmsdArr)
|
||||
if err != nil {
|
||||
return arr
|
||||
}
|
||||
|
||||
for k, m := range mkv {
|
||||
if k == "-" {
|
||||
continue
|
||||
}
|
||||
|
||||
// 跳过-号数据 udm-sd:360000100000130
|
||||
imsi := k[7:]
|
||||
if strings.Contains(imsi, "-") {
|
||||
continue
|
||||
}
|
||||
|
||||
a := model.UDMSubUser{
|
||||
IMSI: key[7:], // udm-sd:360000100000130
|
||||
IMSI: imsi, // udm-sd:360000100000130
|
||||
MSISDN: m["gpsi"], // 8612300000130
|
||||
NeId: neId,
|
||||
SmfSel: m["smf-sel"], // def_snssai
|
||||
@@ -170,7 +180,7 @@ func (r *UDMSubUser) ParseInfo(imsi, neId string, data map[string]string) model.
|
||||
}
|
||||
|
||||
// SelectPage 分页查询数据库
|
||||
func (r *UDMSubUser) SelectPage(query map[string]any) map[string]any {
|
||||
func (r *UDMSubUser) SelectPage(query map[string]any) (int64, []model.UDMSubUser) {
|
||||
return r.udmSubRepository.SelectPage(query)
|
||||
}
|
||||
|
||||
@@ -337,6 +347,7 @@ func (r *UDMSubUser) ParseCommandParams(item model.UDMSubUser) string {
|
||||
if item.ApnContext != "" {
|
||||
conditions = append(conditions, fmt.Sprintf("apn_context=%s", item.ApnContext))
|
||||
}
|
||||
// static_ip指给4G UE分配的静态IP,没有可不带此字段名,批量添加IP会自动递增
|
||||
if item.StaticIp != "" {
|
||||
conditions = append(conditions, fmt.Sprintf("static_ip=%s", item.StaticIp))
|
||||
}
|
||||
@@ -348,8 +359,7 @@ func (r *UDMSubUser) ParseCommandParams(item model.UDMSubUser) string {
|
||||
if item.SmData != "" {
|
||||
conditions = append(conditions, fmt.Sprintf("sm_data=%s", item.SmData))
|
||||
}
|
||||
if item.Cag != "" {
|
||||
conditions = append(conditions, fmt.Sprintf("cag=%s", item.Cag))
|
||||
}
|
||||
conditions = append(conditions, fmt.Sprintf("cag=%s", item.Cag))
|
||||
|
||||
return strings.Join(conditions, ",")
|
||||
}
|
||||
|
||||
@@ -199,16 +199,16 @@ func (s *NeConfigController) DataInfo(c *gin.Context) {
|
||||
}
|
||||
c.JSON(200, result.OkData(resData))
|
||||
return
|
||||
} else {
|
||||
// 网元直连
|
||||
resData, err := neFetchlink.NeConfigInfo(neInfo, query.ParamName)
|
||||
if err != nil {
|
||||
c.JSON(200, result.ErrMsg(err.Error()))
|
||||
return
|
||||
}
|
||||
|
||||
c.JSON(200, result.Ok(resData))
|
||||
}
|
||||
|
||||
// 网元直连
|
||||
resData, err := neFetchlink.NeConfigInfo(neInfo, query.ParamName)
|
||||
if err != nil {
|
||||
c.JSON(200, result.ErrMsg(err.Error()))
|
||||
return
|
||||
}
|
||||
|
||||
c.JSON(200, result.Ok(resData))
|
||||
}
|
||||
|
||||
// 网元参数配置数据修改
|
||||
@@ -242,15 +242,15 @@ func (s *NeConfigController) DataEdit(c *gin.Context) {
|
||||
}
|
||||
c.JSON(200, result.OkData(resData))
|
||||
return
|
||||
} else {
|
||||
// 网元直连
|
||||
resData, err := neFetchlink.NeConfigUpdate(neInfo, body.ParamName, body.Loc, body.ParamData)
|
||||
if err != nil {
|
||||
c.JSON(200, result.ErrMsg(err.Error()))
|
||||
return
|
||||
}
|
||||
c.JSON(200, result.OkData(resData))
|
||||
}
|
||||
|
||||
// 网元直连
|
||||
resData, err := neFetchlink.NeConfigUpdate(neInfo, body.ParamName, body.Loc, body.ParamData)
|
||||
if err != nil {
|
||||
c.JSON(200, result.ErrMsg(err.Error()))
|
||||
return
|
||||
}
|
||||
c.JSON(200, result.OkData(resData))
|
||||
}
|
||||
|
||||
// 网元参数配置数据新增(array)
|
||||
|
||||
@@ -79,6 +79,13 @@ func (s *NeHostController) Add(c *gin.Context) {
|
||||
return
|
||||
}
|
||||
|
||||
if body.GroupID == "1" {
|
||||
// 主机信息操作【%s】失败,禁止操作网元
|
||||
msg := i18n.TKey(language, "neHost.banNE")
|
||||
c.JSON(200, result.ErrMsg(msg))
|
||||
return
|
||||
}
|
||||
|
||||
// 检查属性值唯一
|
||||
uniqueHost := s.neHostService.CheckUniqueHostTitle(body.GroupID, body.Title, body.HostType, "")
|
||||
if !uniqueHost {
|
||||
|
||||
@@ -111,8 +111,28 @@ func (r *NeHost) SelectPage(query map[string]any) map[string]any {
|
||||
params = append(params, pageNum*pageSize)
|
||||
params = append(params, pageSize)
|
||||
|
||||
// 排序
|
||||
orderSql := ""
|
||||
if sv, ok := query["sortField"]; ok && sv != "" {
|
||||
sortSql := fmt.Sprint(sv)
|
||||
if sortSql == "updateTime" {
|
||||
sortSql = "update_time"
|
||||
}
|
||||
if sortSql == "createTime" {
|
||||
sortSql = "create_time"
|
||||
}
|
||||
if ov, ok := query["sortOrder"]; ok && ov != "" {
|
||||
if fmt.Sprint(ov) == "desc" {
|
||||
sortSql += " desc "
|
||||
} else {
|
||||
sortSql += " asc "
|
||||
}
|
||||
}
|
||||
orderSql = fmt.Sprintf(" order by %s ", sortSql)
|
||||
}
|
||||
|
||||
// 查询数据
|
||||
querySql := r.selectSql + whereSql + pageSql
|
||||
querySql := r.selectSql + whereSql + orderSql + pageSql
|
||||
results, err := datasource.RawDB("", querySql, params)
|
||||
if err != nil {
|
||||
logger.Errorf("query err => %v", err)
|
||||
|
||||
@@ -18,6 +18,7 @@ var neListSort = []string{
|
||||
"IMS",
|
||||
"AMF",
|
||||
"AUSF",
|
||||
"UDR",
|
||||
"UDM",
|
||||
"SMF",
|
||||
"PCF",
|
||||
|
||||
@@ -120,6 +120,9 @@ func (r *NeConfigBackup) NeConfigLocalToNe(neInfo model.NeInfo, localFile string
|
||||
sshClient.RunCMD(fmt.Sprintf("sudo mkdir -p /usr/local/etc/iwf && sudo cp -rf %s/iwf/* /usr/local/etc/iwf && sudo chmod 755 /usr/local/etc/iwf/*.yaml", neDirTemp))
|
||||
} else if neTypeLower == "omc" {
|
||||
sshClient.RunCMD(fmt.Sprintf("sudo mkdir -p /usr/local/omc/etc && sudo cp -rf %s/* /usr/local/omc/etc && sudo chmod 755 /usr/local/omc/etc/*.{yaml,conf}", neDirTemp))
|
||||
} else if neTypeLower == "smsc" {
|
||||
chmodFile := "sudo chmod 755 /usr/local/etc/smsc/{*sys.conf,*conf.txt,conf/is41_operation.conf}"
|
||||
sshClient.RunCMD(fmt.Sprintf("sudo mkdir -p /usr/local/etc/smsc/conf && sudo cp -rf %s/* /usr/local/etc/smsc && %s", neDirTemp, chmodFile))
|
||||
} else {
|
||||
neEtcPath := fmt.Sprintf("/usr/local/etc/%s", neTypeLower)
|
||||
chmodFile := fmt.Sprintf("sudo chmod 755 %s/*.yaml", neEtcPath)
|
||||
@@ -175,6 +178,9 @@ func (r *NeConfigBackup) NeConfigNeToLocal(neInfo model.NeInfo) (string, error)
|
||||
sshClient.RunCMD(fmt.Sprintf("mkdir -p %s/iwf && sudo cp -rf /usr/local/etc/iwf/*.yaml %s/iwf", neDirTemp, neDirTemp))
|
||||
} else if neTypeLower == "omc" {
|
||||
sshClient.RunCMD(fmt.Sprintf("mkdir -p %s && sudo cp -rf /usr/local/omc/etc/*.{yaml,conf} %s", neDirTemp, neDirTemp))
|
||||
} else if neTypeLower == "smsc" {
|
||||
sshClient.RunCMD(fmt.Sprintf("mkdir -p %s && sudo cp -rf /usr/local/etc/smsc/{*.yaml,*.conf,*conf.txt} %s", neDirTemp, neDirTemp))
|
||||
sshClient.RunCMD(fmt.Sprintf("sudo cp -rf /usr/local/etc/smsc/conf %s/conf", neDirTemp))
|
||||
} else {
|
||||
nePath := fmt.Sprintf("/usr/local/etc/%s/*.yaml", neTypeLower)
|
||||
if neTypeLower == "mme" {
|
||||
|
||||
@@ -149,6 +149,13 @@ func (r *NeHost) DeleteByIds(hostIds []string) (int64, error) {
|
||||
return 0, fmt.Errorf("neHost.noData")
|
||||
}
|
||||
|
||||
for _, v := range ids {
|
||||
if v.GroupID == "1" {
|
||||
// 主机信息操作【%s】失败,禁止操作网元
|
||||
return 0, fmt.Errorf("neHost.banNE")
|
||||
}
|
||||
}
|
||||
|
||||
if len(ids) == len(hostIds) {
|
||||
rows := r.neHostRepository.DeleteByIds(hostIds)
|
||||
return rows, nil
|
||||
|
||||
@@ -79,6 +79,28 @@ func (r *NeInfo) ClearNeCacheByNeType(neType string) bool {
|
||||
return delOk
|
||||
}
|
||||
|
||||
// SelectNeInfoByNeType 通过ne_type查询网元信息
|
||||
func (r *NeInfo) SelectNeInfoByNeType(neType string) []model.NeInfo {
|
||||
neInfo := make([]model.NeInfo, 0)
|
||||
key := fmt.Sprintf("%s%s:*", cachekey.NE_KEY, strings.ToUpper(neType))
|
||||
jsonStr, _ := redis.Get("", key)
|
||||
if len(jsonStr) > 7 {
|
||||
err := json.Unmarshal([]byte(jsonStr), &neInfo)
|
||||
if err != nil {
|
||||
return neInfo
|
||||
}
|
||||
} else {
|
||||
neInfo = r.neInfoRepository.SelectList(model.NeInfo{NeType: neType})
|
||||
for _, v := range neInfo {
|
||||
key := fmt.Sprintf("%s%s:%s", cachekey.NE_KEY, strings.ToUpper(v.NeType), v.NeId)
|
||||
redis.Del("", key)
|
||||
values, _ := json.Marshal(v)
|
||||
redis.Set("", key, string(values))
|
||||
}
|
||||
}
|
||||
return neInfo
|
||||
}
|
||||
|
||||
// SelectNeInfoByRmuid 通过rmUID查询网元信息
|
||||
func (r *NeInfo) SelectNeInfoByRmuid(rmUid string) model.NeInfo {
|
||||
var neInfo model.NeInfo
|
||||
@@ -910,22 +932,25 @@ func (r *NeInfo) neConfPara5GDataConvert(content map[string]any) map[string]stri
|
||||
"DNN_IMS": basic["dnn_ims"].(string),
|
||||
|
||||
// external
|
||||
"N2_IP": external["amfn2_ip"].(string),
|
||||
"UE_POOL": external["ue_pool"].(string),
|
||||
"UE_IP": ueIP,
|
||||
"UE_MASK": ueMask,
|
||||
"UE_CIDR": ueCicr,
|
||||
"UPF_TYPE": external["upf_type"].(string), // StandardUPF LightUPF
|
||||
"N3_IP": n3IP,
|
||||
"N3_MASK": n3Mask,
|
||||
"N3_GW": external["upfn3_gw"].(string),
|
||||
"N3_PCI": external["upfn3_pci"].(string),
|
||||
"N3_MAC": external["upfn3_mac"].(string),
|
||||
"N6_IP": n6IP,
|
||||
"N6_MASK": n6Mask,
|
||||
"N6_GW": external["upfn6_gw"].(string),
|
||||
"N6_PCI": external["upfn6_pci"].(string),
|
||||
"N6_MAC": external["upfn6_mac"].(string),
|
||||
"N2_IP": external["amfn2_ip"].(string),
|
||||
"UE_POOL": external["ue_pool"].(string), // 轻量版才用配置
|
||||
"UE_IP": ueIP,
|
||||
"UE_MASK": ueMask,
|
||||
"UE_CIDR": ueCicr,
|
||||
"UPF_TYPE": external["upf_type"].(string), // 类型 StandardUPF LightUPF
|
||||
"UPF_DRIVER_TYPE": external["upf_driver_type"].(string), // 网卡驱动 vmxnet3 host dpdk
|
||||
"N3_IP": n3IP,
|
||||
"N3_MASK": n3Mask,
|
||||
"N3_GW": external["upfn3_gw"].(string),
|
||||
"N3_PCI": external["upfn3_pci"].(string),
|
||||
"N3_MAC": external["upfn3_mac"].(string),
|
||||
"N3_NIC_NAME": external["upfn3_card_name"].(string), // 网卡名 eth0
|
||||
"N6_IP": n6IP,
|
||||
"N6_MASK": n6Mask,
|
||||
"N6_GW": external["upfn6_gw"].(string),
|
||||
"N6_PCI": external["upfn6_pci"].(string),
|
||||
"N6_MAC": external["upfn6_mac"].(string),
|
||||
"N6_NIC_NAME": external["upfn6_card_name"].(string), // 网卡名 eth0
|
||||
|
||||
"SIP_IP": external["ims_sip_ip"].(string),
|
||||
|
||||
|
||||
@@ -239,7 +239,7 @@ func (r *NeVersion) operateCommand(action, neType string, neFilePaths []string)
|
||||
pkgCmdStr := fmt.Sprintf("sudo dpkg -i %s", strings.Join(neFilePaths, " "))
|
||||
fileExt := filepath.Ext(strings.ToLower(neFilePaths[0]))
|
||||
if strings.HasSuffix(fileExt, "rpm") {
|
||||
pkgCmdStr = fmt.Sprintf("sudo rpm -Uvh %s", strings.Join(neFilePaths, " "))
|
||||
pkgCmdStr = fmt.Sprintf("sudo rpm -Uvh --reinstall %s", strings.Join(neFilePaths, " "))
|
||||
}
|
||||
|
||||
// 组合命令输入
|
||||
@@ -257,7 +257,7 @@ func (r *NeVersion) operateCommand(action, neType string, neFilePaths []string)
|
||||
// 升级软件包
|
||||
pkgCmdStr = fmt.Sprintf("sudo M_PARAM=upgrade dpkg -i %s", strings.Join(neFilePaths, " "))
|
||||
if strings.HasSuffix(fileExt, "rpm") {
|
||||
pkgCmdStr = fmt.Sprintf("sudo M_PARAM=upgrade rpm -Uvh %s", strings.Join(neFilePaths, " "))
|
||||
pkgCmdStr = fmt.Sprintf("sudo M_PARAM=upgrade rpm -Uvh --reinstall %s", strings.Join(neFilePaths, " "))
|
||||
}
|
||||
omcStrArr = append(omcStrArr, pkgCmdStr)
|
||||
}
|
||||
@@ -428,22 +428,35 @@ func (r *NeVersion) operateCommand(action, neType string, neFilePaths []string)
|
||||
cmdStrArr = append(cmdStrArr, "sudo cp /usr/local/etc/upf/default/upfForwarder_1.yaml /usr/local/etc/upf/upfForwarder_1.yaml \n")
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i \"s/172.16.5.190/%s/g\" /usr/local/etc/upf/upfcfg.yaml \n", para5GData["UPF_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i \"s/localhost/%s/g\" /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UPF_IP"]))
|
||||
// UE
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/ueIpv4: 10.2.1.0/s/ueIpv4: 10.2.1.0/ueIpv4: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UE_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/ueIpv4Mask: 255.255.255.0/s/ueIpv4Mask: 255.255.255.0/ueIpv4Mask: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UE_MASK"]))
|
||||
// N3
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i \"s/192.168.8.190/%s/g\" /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N3\"/,/ipv4Mask: 255.255.240.0/s/ipv4Mask: 255.255.240.0/ipv4Mask: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_MASK"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N3\"/,/gatewayIpv4: 192.168.1.254/s/gatewayIpv4: 192.168.1.254/gatewayIpv4: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_GW"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N3\"/,/interfacePCI: \"0000:00:00.0\"/s/interfacePCI: \"0000:00:00.0\"/interfacePCI: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_PCI"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N3\"/,/macAddr: \"00:00:00:00:00:00\"/s/macAddr: \"00:00:00:00:00:00\"/macAddr: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_MAC"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N3/,/ipv4Mask: 255.255.240.0/s/ipv4Mask: 255.255.240.0/ipv4Mask: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_MASK"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N3/,/gatewayIpv4: 192.168.1.254/s/gatewayIpv4: 192.168.1.254/gatewayIpv4: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_GW"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N3/,/interfacePCI: \"0000:00:00.0\"/s/interfacePCI: \"0000:00:00.0\"/interfacePCI: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_PCI"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N3/,/macAddr: \"00:00:00:00:00:00\"/s/macAddr: \"00:00:00:00:00:00\"/macAddr: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_MAC"]))
|
||||
// 标准版 N6
|
||||
if para5GData["UPF_TYPE"] == "StandardUPF" {
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i \"s/192.168.8.191/%s/g\" /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N3\"/,/driverType: .*/s/driverType: .*/driverType: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UPF_DRIVER_TYPE"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N3\"/,/systemNetworkCardName: .*/s/systemNetworkCardName: .*/systemNetworkCardName: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_NIC_NAME"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/driverType: .*/s/driverType: .*/driverType: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UPF_DRIVER_TYPE"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/systemNetworkCardName: .*/s/systemNetworkCardName: .*/systemNetworkCardName: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_NIC_NAME"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/ipv4Mask: 255.255.240.0/s/ipv4Mask: 255.255.240.0/ipv4Mask: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_MASK"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/gatewayIpv4: 192.168.1.254/s/gatewayIpv4: 192.168.1.254/gatewayIpv4: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_GW"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/interfacePCI: \"0000:00:00.0\"/s/interfacePCI: \"0000:00:00.0\"/interfacePCI: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_PCI"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/macAddr: \"00:00:00:00:00:00\"/s/macAddr: \"00:00:00:00:00:00\"/macAddr: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_MAC"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N3/,/driverType: .*/s/driverType: .*/driverType: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UPF_DRIVER_TYPE"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N3/,/systemNetworkCardName: .*/s/systemNetworkCardName: .*/systemNetworkCardName: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N3_NIC_NAME"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N6/,/driverType: .*/s/driverType: .*/driverType: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UPF_DRIVER_TYPE"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N6/,/systemNetworkCardName: .*/s/systemNetworkCardName: .*/systemNetworkCardName: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_NIC_NAME"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N6/,/ipv4Mask: 255.255.240.0/s/ipv4Mask: 255.255.240.0/ipv4Mask: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_MASK"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N6/,/gatewayIpv4: 192.168.1.254/s/gatewayIpv4: 192.168.1.254/gatewayIpv4: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_GW"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N6/,/interfacePCI: \"0000:00:00.0\"/s/interfacePCI: \"0000:00:00.0\"/interfacePCI: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_PCI"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N6/,/macAddr: \"00:00:00:00:00:00\"/s/macAddr: \"00:00:00:00:00:00\"/macAddr: \"%s\"/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["N6_MAC"]))
|
||||
// 路由
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo ip route add '%s/%s' via '%s' \n", para5GData["UE_IP"], para5GData["UE_CIDR"], para5GData["N6_IP"]))
|
||||
}
|
||||
@@ -451,7 +464,12 @@ func (r *NeVersion) operateCommand(action, neType string, neFilePaths []string)
|
||||
if para5GData["UPF_TYPE"] == "LightUPF" {
|
||||
cmdStrArr = append(cmdStrArr, "sudo sed -i \"s/192.168.8.191/0.0.0.0/g\" /usr/local/etc/upf/upfForwarder_1.yaml \n")
|
||||
cmdStrArr = append(cmdStrArr, "sudo sed -i \"s/type: upfd/type: tun/g\" /usr/local/etc/upf/upfForwarder_1.yaml \n")
|
||||
cmdStrArr = append(cmdStrArr, "sudo sed -i 's/driverType: vmxnet3/driverType: \"\"/g' /usr/local/etc/upf/upfForwarder_1.yaml \n")
|
||||
cmdStrArr = append(cmdStrArr, "sudo sed -i 's/driverType: .*/driverType: \"\"/g' /usr/local/etc/upf/upfForwarder_1.yaml \n")
|
||||
// UE
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N6/,/ueIpv4: 10.2.1.0/s/ueIpv4: 10.2.1.0/ueIpv4: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UE_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: N6/,/ueIpv4Mask: 255.255.255.0/s/ueIpv4Mask: 255.255.255.0/ueIpv4Mask: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UE_MASK"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/ueIpv4: 10.2.1.0/s/ueIpv4: 10.2.1.0/ueIpv4: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UE_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i '/- interfaceType: \"N6\"/,/ueIpv4Mask: 255.255.255.0/s/ueIpv4Mask: 255.255.255.0/ueIpv4Mask: %s/' /usr/local/etc/upf/upfForwarder_1.yaml \n", para5GData["UE_MASK"]))
|
||||
}
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("grep -qxF '%s upf' /etc/hosts || echo '%s upf' | sudo tee -a /etc/hosts \n", para5GData["UPF_IP"], para5GData["UPF_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("grep -qxF '%s upfn3' /etc/hosts || echo '%s upfn3' | sudo tee -a /etc/hosts \n", para5GData["N3_IP"], para5GData["N3_IP"]))
|
||||
@@ -539,14 +557,14 @@ func (r *NeVersion) operateCommand(action, neType string, neFilePaths []string)
|
||||
if strings.Contains(pkgCmdStr, "adb") {
|
||||
para5GData := NewNeInfo.Para5GData
|
||||
cmdStrArr = append(cmdStrArr, "sudo cp /usr/local/etc/adb/default/adb.conf /usr/local/etc/adb/adb.conf \n")
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i \"s/bind 127.0.0.1/bind 127.0.0.1 %s/g\" /usr/local/etc/adb/adb.conf \n", para5GData["DB_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i \"s/bind 127.0.0.1/bind %s/g\" /usr/local/etc/adb/adb.conf \n", para5GData["DB_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, "sudo service adb restart \n")
|
||||
}
|
||||
// kvdb
|
||||
if strings.Contains(pkgCmdStr, "kvdb") {
|
||||
para5GData := NewNeInfo.Para5GData
|
||||
cmdStrArr = append(cmdStrArr, "sudo cp /usr/local/etc/kvdb/default/kvdb.conf /usr/local/etc/kvdb/kvdb.conf \n")
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i \"s/bind 127.0.0.1/bind 127.0.0.1 %s/g\" /usr/local/etc/kvdb/kvdb.conf \n", para5GData["DB_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, fmt.Sprintf("sudo sed -i \"s/bind 127.0.0.1/bind %s/g\" /usr/local/etc/kvdb/kvdb.conf \n", para5GData["DB_IP"]))
|
||||
cmdStrArr = append(cmdStrArr, "sudo service kvdb restart \n")
|
||||
}
|
||||
}
|
||||
@@ -671,17 +689,20 @@ func (r *NeVersion) operateDome(action string, neVersion model.NeVersion) error
|
||||
smscHost := fmt.Sprintf("%s smsc.ims.%s.3gppnetwork.org", para5GData["SMSC_IP"], mnc_mcc)
|
||||
smscHostCMD := fmt.Sprintf("grep -qxF '%s' /etc/hosts || echo '%s' | sudo tee -a /etc/hosts \n", smscHost, smscHost)
|
||||
smscIPCMD := fmt.Sprintf("grep -qxF '%s smsc' /etc/hosts || echo '%s smsc' | sudo tee -a /etc/hosts \n", para5GData["SMSC_IP"], para5GData["SMSC_IP"])
|
||||
smsHost := fmt.Sprintf("sudo sed -i '/^%s smsc.*smsc$/c\\' /etc/hosts", para5GData["SIP_IP"])
|
||||
|
||||
// IMS 配置
|
||||
imsNEs := NewNeInfo.SelectList(model.NeInfo{NeType: "IMS"}, false, false)
|
||||
for _, v := range imsNEs {
|
||||
NewNeInfo.NeRunSSHCmd(v.NeType, v.NeId, smscIPCMD)
|
||||
NewNeInfo.NeRunSSHCmd(v.NeType, v.NeId, smscHostCMD)
|
||||
NewNeInfo.NeRunSSHCmd(v.NeType, v.NeId, smsHost)
|
||||
NewNeInfo.NeRunSSHCmd(v.NeType, v.NeId, "sudo sed -i '/^#!define WITH_SMS/ s/^/#/' /usr/local/etc/ims/vars.cfg")
|
||||
NewNeInfo.NeRunSSHCmd(v.NeType, v.NeId, "ims-stop || true && ims-start")
|
||||
}
|
||||
// UDM 配置
|
||||
smscASName := fmt.Sprintf("sudo sed -i '/- name: sms_as/{n;s|serverName: .*|serverName: sip:%s:5060|}' /usr/local/etc/udm/as.yaml", para5GData["SMSC_IP"])
|
||||
smscASAddress := fmt.Sprintf("sudo sed -i '/- name: sms_as/{n;s|diameterAddress: .*|diameterAddress: smsc.ims.%s.3gppnetwork.org|}' /usr/local/etc/udm/as.yaml", mnc_mcc)
|
||||
smscASName := fmt.Sprintf("sudo sed -i \"/- name: 'sms_as'/{n;s|serverName: .*|serverName: 'sip:%s:5060'|}\" /usr/local/etc/udm/as.yaml", para5GData["SMSC_IP"])
|
||||
smscASAddress := fmt.Sprintf("sudo sed -i \"/- name: 'sms_as'/{n;n;n;s|diameterAddress: .*|diameterAddress: 'smsc.ims.%s.3gppnetwork.org'|}\" /usr/local/etc/udm/as.yaml", mnc_mcc)
|
||||
udmNEs := NewNeInfo.SelectList(model.NeInfo{NeType: "UDM"}, false, false)
|
||||
for _, v := range udmNEs {
|
||||
NewNeInfo.NeRunSSHCmd(v.NeType, v.NeId, smscIPCMD)
|
||||
|
||||
@@ -37,15 +37,16 @@ type IPerfController struct {
|
||||
func (s *IPerfController) Version(c *gin.Context) {
|
||||
language := ctx.AcceptLanguage(c)
|
||||
var query struct {
|
||||
NeType string `form:"neType" binding:"required"` // 网元类型
|
||||
NeID string `form:"neId" binding:"required"` // 网元ID
|
||||
NeType string `form:"neType" binding:"required"` // 网元类型
|
||||
NeId string `form:"neId" binding:"required"` // 网元ID
|
||||
Version string `form:"version" binding:"required,oneof=V2 V3"` // 版本
|
||||
}
|
||||
if err := c.ShouldBindQuery(&query); err != nil {
|
||||
c.JSON(400, result.CodeMsg(400, i18n.TKey(language, "app.common.err400")))
|
||||
return
|
||||
}
|
||||
|
||||
output, err := s.iperfService.Version(query.NeType, query.NeID)
|
||||
output, err := s.iperfService.Version(query.NeType, query.NeId, query.Version)
|
||||
if err != nil {
|
||||
c.JSON(200, result.ErrMsg(i18n.TKey(language, err.Error())))
|
||||
return
|
||||
@@ -60,15 +61,16 @@ func (s *IPerfController) Version(c *gin.Context) {
|
||||
func (s *IPerfController) Install(c *gin.Context) {
|
||||
language := ctx.AcceptLanguage(c)
|
||||
var body struct {
|
||||
NeType string `json:"neType" binding:"required"` // 网元类型
|
||||
NeID string `json:"neId" binding:"required"` // 网元ID
|
||||
NeType string `json:"neType" binding:"required"` // 网元类型
|
||||
NeId string `json:"neId" binding:"required"` // 网元ID
|
||||
Version string `form:"version" binding:"required,oneof=V2 V3"` // 版本
|
||||
}
|
||||
if err := c.ShouldBindBodyWithJSON(&body); err != nil {
|
||||
c.JSON(400, result.CodeMsg(400, i18n.TKey(language, "app.common.err400")))
|
||||
return
|
||||
}
|
||||
|
||||
if err := s.iperfService.Install(body.NeType, body.NeID); err != nil {
|
||||
if err := s.iperfService.Install(body.NeType, body.NeId, body.Version); err != nil {
|
||||
c.JSON(200, result.ErrMsg(i18n.TKey(language, err.Error())))
|
||||
return
|
||||
}
|
||||
|
||||
@@ -22,17 +22,39 @@ var NewIPerf = &IPerf{}
|
||||
type IPerf struct{}
|
||||
|
||||
// Version 查询版本信息
|
||||
func (s *IPerf) Version(meType, neId string) (string, error) {
|
||||
// 检查是否安装iperf3
|
||||
output, err := neService.NewNeInfo.NeRunSSHCmd(meType, neId, "iperf3 --version")
|
||||
func (s *IPerf) Version(meType, neId, version string) (string, error) {
|
||||
if version != "V2" && version != "V3" {
|
||||
return "", fmt.Errorf("iperf version is required V2 or V3")
|
||||
}
|
||||
cmd := "iperf3 --version"
|
||||
if version == "V2" {
|
||||
cmd = "iperf -v"
|
||||
}
|
||||
|
||||
// 网元主机的SSH客户端
|
||||
sshClient, err := neService.NewNeInfo.NeRunSSHClient(meType, neId)
|
||||
if err != nil {
|
||||
return "", fmt.Errorf("iperf3 not installed")
|
||||
return "", err
|
||||
}
|
||||
defer sshClient.Close()
|
||||
|
||||
// 检查是否安装iperf
|
||||
output, err := sshClient.RunCMD(cmd)
|
||||
if err != nil {
|
||||
if version == "V2" && strings.HasSuffix(err.Error(), "status 1") { // V2 版本
|
||||
return strings.TrimSpace(output), nil
|
||||
}
|
||||
return "", fmt.Errorf("iperf %s not installed", version)
|
||||
}
|
||||
return strings.TrimSpace(output), err
|
||||
}
|
||||
|
||||
// Install 安装iperf3
|
||||
func (s *IPerf) Install(meType, neId string) error {
|
||||
func (s *IPerf) Install(meType, neId, version string) error {
|
||||
if version != "V2" && version != "V3" {
|
||||
return fmt.Errorf("iperf version is required V2 or V3")
|
||||
}
|
||||
|
||||
// 网元主机的SSH客户端
|
||||
sshClient, err := neService.NewNeInfo.NeRunSSHClient(meType, neId)
|
||||
if err != nil {
|
||||
@@ -56,9 +78,16 @@ func (s *IPerf) Install(meType, neId string) error {
|
||||
depDir = "assets/dependency/iperf3/deb"
|
||||
// sudo apt remove iperf3 libiperf0 libsctp1 libsctp-dev lksctp-tools
|
||||
} else if _, err := sshClient.RunCMD("sudo yum --version"); err == nil {
|
||||
depPkg = "sudo rpm -Uvh --force"
|
||||
depPkg = "sudo rpm -Uvh --nosignature --reinstall --force"
|
||||
depDir = "assets/dependency/iperf3/rpm"
|
||||
// yum remove iperf3 iperf3-help.noarch
|
||||
} else {
|
||||
return fmt.Errorf("iperf %s not supported install", version)
|
||||
}
|
||||
|
||||
// V2版本和V3版本的安装包路径不同
|
||||
if version == "V2" {
|
||||
depDir = strings.Replace(depDir, "iperf3", "iperf", 1)
|
||||
}
|
||||
|
||||
// 从 embed.FS 中读取默认配置文件内容
|
||||
@@ -72,19 +101,19 @@ func (s *IPerf) Install(meType, neId string) error {
|
||||
// 打开本地文件
|
||||
localFile, err := assetsDir.Open(fmt.Sprintf("%s/%s", depDir, d.Name()))
|
||||
if err != nil {
|
||||
return fmt.Errorf("iperf3 file local error")
|
||||
return fmt.Errorf("iperf %s file local error", version)
|
||||
}
|
||||
defer localFile.Close()
|
||||
// 创建远程文件
|
||||
remotePath := fmt.Sprintf("%s/%s", nePath, d.Name())
|
||||
remoteFile, err := sftpClient.Client.Create(remotePath)
|
||||
if err != nil {
|
||||
return fmt.Errorf("iperf3 file remote error")
|
||||
return fmt.Errorf("iperf %s file remote error", version)
|
||||
}
|
||||
defer remoteFile.Close()
|
||||
// 使用 io.Copy 将嵌入的文件内容复制到目标文件
|
||||
if _, err := io.Copy(remoteFile, localFile); err != nil {
|
||||
return fmt.Errorf("iperf3 file copy error")
|
||||
return fmt.Errorf("iperf %s file copy error", version)
|
||||
}
|
||||
neFilePaths = append(neFilePaths, remotePath)
|
||||
}
|
||||
@@ -98,7 +127,7 @@ func (s *IPerf) Install(meType, neId string) error {
|
||||
// 安装软件包
|
||||
pkgInstall := fmt.Sprintf("%s %s", depPkg, strings.Join(neFilePaths, " "))
|
||||
if _, err := sshClient.RunCMD(pkgInstall); err != nil {
|
||||
return fmt.Errorf("iperf3 install error")
|
||||
return fmt.Errorf("iperf %s install error", version)
|
||||
}
|
||||
return err
|
||||
}
|
||||
@@ -108,7 +137,7 @@ func (s *IPerf) Run(client *wsModel.WSClient, reqMsg wsModel.WSRequest) {
|
||||
// 必传requestId确认消息
|
||||
if reqMsg.RequestID == "" {
|
||||
msg := "message requestId is required"
|
||||
logger.Infof("ws IPerf3 Run UID %s err: %s", client.BindUid, msg)
|
||||
logger.Infof("ws IPerf Run UID %s err: %s", client.BindUid, msg)
|
||||
msgByte, _ := json.Marshal(result.ErrMsg(msg))
|
||||
client.MsgChan <- msgByte
|
||||
return
|
||||
@@ -126,7 +155,7 @@ func (s *IPerf) Run(client *wsModel.WSClient, reqMsg wsModel.WSRequest) {
|
||||
time.Sleep(1 * time.Second)
|
||||
client.StopChan <- struct{}{}
|
||||
return
|
||||
case "iperf3":
|
||||
case "iperf":
|
||||
// SSH会话消息接收写入会话
|
||||
var command string
|
||||
command, err = s.parseOptions(reqMsg.Data)
|
||||
@@ -155,7 +184,7 @@ func (s *IPerf) Run(client *wsModel.WSClient, reqMsg wsModel.WSRequest) {
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
logger.Warnf("ws IPerf3 Run UID %s err: %s", client.BindUid, err.Error())
|
||||
logger.Warnf("ws IPerf Run UID %s err: %s", client.BindUid, err.Error())
|
||||
msgByte, _ := json.Marshal(result.ErrMsg(err.Error()))
|
||||
client.MsgChan <- msgByte
|
||||
if err == io.EOF {
|
||||
@@ -175,7 +204,8 @@ func (s *IPerf) parseOptions(reqData any) (string, error) {
|
||||
msgByte, _ := json.Marshal(reqData)
|
||||
var data struct {
|
||||
Command string `json:"command"` // 命令字符串
|
||||
Client bool `json:"client"` // 服务端或客户端,默认服务端
|
||||
Version string `json:"version"` // 服务版本,默认V3
|
||||
Mode string `json:"mode"` // 服务端或客户端,默认客户端client
|
||||
Host string `json:"host"` // 客户端连接到的服务端IP地址
|
||||
// Server or Client
|
||||
Port int `json:"port"` // 服务端口
|
||||
@@ -183,17 +213,25 @@ func (s *IPerf) parseOptions(reqData any) (string, error) {
|
||||
// Server
|
||||
OneOff bool `json:"oneOff"` // 只进行一次连接
|
||||
// Client
|
||||
UDP bool `json:"udp"` // use UDP rather than TCP
|
||||
Time int `json:"time"` // 以秒为单位的传输时间(默认为 10 秒)
|
||||
Reverse bool `json:"reverse"` // 以反向模式运行(服务器发送,客户端接收)
|
||||
Window string `json:"window"` // 设置窗口大小/套接字缓冲区大小
|
||||
UDP bool `json:"udp"` // use UDP rather than TCP
|
||||
Time int `json:"time"` // 以秒为单位的传输时间(默认为 10 秒)
|
||||
Reverse bool `json:"reverse"` // 以反向模式运行(服务器发送,客户端接收)
|
||||
Window string `json:"window"` // 设置窗口大小/套接字缓冲区大小
|
||||
Parallel int `json:"parallel"` // 运行的并行客户端流数量
|
||||
Bitrate int `json:"bitrate"` // 以比特/秒为单位(0 表示无限制)
|
||||
}
|
||||
if err := json.Unmarshal(msgByte, &data); err != nil {
|
||||
logger.Warnf("ws processor parseClient err: %s", err.Error())
|
||||
return "", fmt.Errorf("query data structure error")
|
||||
}
|
||||
if data.Version != "V3" && data.Version != "V2" {
|
||||
return "", fmt.Errorf("query data version support V3 or V2")
|
||||
}
|
||||
|
||||
command := []string{"iperf3"}
|
||||
if data.Version == "V2" {
|
||||
command = []string{"iperf"}
|
||||
}
|
||||
// 命令字符串高优先级
|
||||
if data.Command != "" {
|
||||
command = append(command, data.Command)
|
||||
@@ -201,16 +239,14 @@ func (s *IPerf) parseOptions(reqData any) (string, error) {
|
||||
return strings.Join(command, " "), nil
|
||||
}
|
||||
|
||||
if data.Client && data.Host == "" {
|
||||
if data.Mode != "client" && data.Mode != "server" {
|
||||
return "", fmt.Errorf("query data mode support client or server")
|
||||
}
|
||||
if data.Mode == "client" && data.Host == "" {
|
||||
return "", fmt.Errorf("query data client host empty")
|
||||
}
|
||||
if !data.Client {
|
||||
command = append(command, "-s")
|
||||
// Server
|
||||
if data.OneOff {
|
||||
command = append(command, "-1")
|
||||
}
|
||||
} else {
|
||||
|
||||
if data.Mode == "client" {
|
||||
command = append(command, "-c")
|
||||
command = append(command, data.Host)
|
||||
// Client
|
||||
@@ -220,6 +256,12 @@ func (s *IPerf) parseOptions(reqData any) (string, error) {
|
||||
if data.Time > 0 {
|
||||
command = append(command, fmt.Sprintf("-t %d", data.Time))
|
||||
}
|
||||
if data.Bitrate > 0 {
|
||||
command = append(command, fmt.Sprintf("-b %d", data.Bitrate))
|
||||
}
|
||||
if data.Parallel > 0 {
|
||||
command = append(command, fmt.Sprintf("-P %d", data.Parallel))
|
||||
}
|
||||
if data.Reverse {
|
||||
command = append(command, "-R")
|
||||
}
|
||||
@@ -227,6 +269,13 @@ func (s *IPerf) parseOptions(reqData any) (string, error) {
|
||||
command = append(command, fmt.Sprintf("-w %s", data.Window))
|
||||
}
|
||||
}
|
||||
if data.Mode == "server" {
|
||||
command = append(command, "-s")
|
||||
// Server
|
||||
if data.OneOff {
|
||||
command = append(command, "-1")
|
||||
}
|
||||
}
|
||||
|
||||
// Server or Client
|
||||
if data.Port > 0 {
|
||||
|
||||
69
src/modules/ws/controller/ws_redis.go
Normal file
69
src/modules/ws/controller/ws_redis.go
Normal file
@@ -0,0 +1,69 @@
|
||||
package controller
|
||||
|
||||
import (
|
||||
"be.ems/src/framework/i18n"
|
||||
"be.ems/src/framework/logger"
|
||||
"be.ems/src/framework/redis"
|
||||
"be.ems/src/framework/utils/ctx"
|
||||
"be.ems/src/framework/vo/result"
|
||||
neService "be.ems/src/modules/network_element/service"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
// Redis 终端
|
||||
//
|
||||
// GET /redis?hostId=1
|
||||
func (s *WSController) Redis(c *gin.Context) {
|
||||
language := ctx.AcceptLanguage(c)
|
||||
var query struct {
|
||||
HostId string `form:"hostId" binding:"required"` // 连接主机ID
|
||||
}
|
||||
if err := c.ShouldBindQuery(&query); err != nil {
|
||||
c.JSON(400, result.CodeMsg(400, i18n.TKey(language, "app.common.err400")))
|
||||
return
|
||||
}
|
||||
|
||||
// 登录用户信息
|
||||
loginUser, err := ctx.LoginUser(c)
|
||||
if err != nil {
|
||||
c.JSON(401, result.CodeMsg(401, i18n.TKey(language, err.Error())))
|
||||
return
|
||||
}
|
||||
|
||||
neHost := neService.NewNeHost.SelectById(query.HostId)
|
||||
if neHost.HostID != query.HostId || neHost.HostType != "redis" {
|
||||
// 没有可访问主机信息数据!
|
||||
c.JSON(200, result.ErrMsg(i18n.TKey(language, "neHost.noData")))
|
||||
return
|
||||
}
|
||||
|
||||
// 创建链接Redis客户端
|
||||
var connRedis redis.ConnRedis
|
||||
neHost.CopyTo(&connRedis)
|
||||
client, err := connRedis.NewClient()
|
||||
if err != nil {
|
||||
// 连接主机失败,请检查连接参数后重试
|
||||
c.JSON(200, result.ErrMsg(i18n.TKey(language, "neHost.errByHostInfo")))
|
||||
return
|
||||
}
|
||||
defer client.Close()
|
||||
|
||||
// 将 HTTP 连接升级为 WebSocket 连接
|
||||
wsConn := s.wsService.UpgraderWs(c.Writer, c.Request)
|
||||
if wsConn == nil {
|
||||
return
|
||||
}
|
||||
defer wsConn.Close()
|
||||
|
||||
wsClient := s.wsService.ClientCreate(loginUser.UserID, nil, wsConn, client)
|
||||
go s.wsService.ClientWriteListen(wsClient)
|
||||
go s.wsService.ClientReadListen(wsClient, s.wsReceiveService.Redis)
|
||||
|
||||
// 等待停止信号
|
||||
for value := range wsClient.StopChan {
|
||||
s.wsService.ClientClose(wsClient.ID)
|
||||
logger.Infof("ws Stop Client UID %s %s", wsClient.BindUid, value)
|
||||
return
|
||||
}
|
||||
}
|
||||
@@ -4,9 +4,12 @@ import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"io"
|
||||
"reflect"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"be.ems/src/framework/logger"
|
||||
"be.ems/src/framework/redis"
|
||||
"be.ems/src/framework/telnet"
|
||||
"be.ems/src/framework/utils/ssh"
|
||||
"be.ems/src/framework/vo/result"
|
||||
@@ -104,7 +107,7 @@ func (s *WSReceive) Shell(client *model.WSClient, reqMsg model.WSRequest) {
|
||||
command := reqMsg.Data.(string)
|
||||
sshClientSession := client.ChildConn.(*ssh.SSHClientSession)
|
||||
_, err = sshClientSession.Write(command)
|
||||
case "ssh_resize":
|
||||
case "resize":
|
||||
// SSH会话窗口重置
|
||||
msgByte, _ := json.Marshal(reqMsg.Data)
|
||||
var data struct {
|
||||
@@ -225,7 +228,7 @@ func (s *WSReceive) Telnet(client *model.WSClient, reqMsg model.WSRequest) {
|
||||
command := reqMsg.Data.(string)
|
||||
telnetClientSession := client.ChildConn.(*telnet.TelnetClientSession)
|
||||
_, err = telnetClientSession.Write(command)
|
||||
case "telnet_resize":
|
||||
case "resize":
|
||||
// Telnet会话窗口重置
|
||||
msgByte, _ := json.Marshal(reqMsg.Data)
|
||||
var data struct {
|
||||
@@ -256,3 +259,76 @@ func (s *WSReceive) Telnet(client *model.WSClient, reqMsg model.WSRequest) {
|
||||
client.MsgChan <- resByte
|
||||
}
|
||||
}
|
||||
|
||||
// Redis 接收终端交互业务处理
|
||||
func (s *WSReceive) Redis(client *model.WSClient, reqMsg model.WSRequest) {
|
||||
// 必传requestId确认消息
|
||||
if reqMsg.RequestID == "" {
|
||||
msg := "message requestId is required"
|
||||
logger.Infof("ws Shell UID %s err: %s", client.BindUid, msg)
|
||||
msgByte, _ := json.Marshal(result.ErrMsg(msg))
|
||||
client.MsgChan <- msgByte
|
||||
return
|
||||
}
|
||||
|
||||
var resByte []byte
|
||||
var err error
|
||||
|
||||
switch reqMsg.Type {
|
||||
case "close":
|
||||
s.close(client)
|
||||
return
|
||||
case "redis":
|
||||
// Redis会话消息接收写入会话
|
||||
command := fmt.Sprint(reqMsg.Data)
|
||||
redisClientSession := client.ChildConn.(*redis.ConnRedis)
|
||||
output, err := redisClientSession.RunCMD(command)
|
||||
dataStr := ""
|
||||
if err != nil {
|
||||
dataStr = fmt.Sprintf("%s \r\n", err.Error())
|
||||
} else {
|
||||
// 获取结果的反射类型
|
||||
resultType := reflect.TypeOf(output)
|
||||
switch resultType.Kind() {
|
||||
case reflect.Slice:
|
||||
// 如果是切片类型需要进一步判断是否是 []string 或 []interface{}
|
||||
if resultType.Elem().Kind() == reflect.String {
|
||||
dataStr = fmt.Sprintf("%s \r\n", strings.Join(output.([]string), "\r\n"))
|
||||
} else if resultType.Elem().Kind() == reflect.Interface {
|
||||
arr := []string{}
|
||||
for _, v := range output.([]any) {
|
||||
arr = append(arr, fmt.Sprintf("%s", v))
|
||||
}
|
||||
dataStr = fmt.Sprintf("%s \r\n", strings.Join(arr, "\r\n"))
|
||||
}
|
||||
case reflect.Ptr:
|
||||
dataStr = "\r\n"
|
||||
case reflect.String, reflect.Int64:
|
||||
dataStr = fmt.Sprintf("%s \r\n", output)
|
||||
default:
|
||||
dataStr = fmt.Sprintf("%s \r\n", output)
|
||||
}
|
||||
}
|
||||
resByte, _ = json.Marshal(result.Ok(map[string]any{
|
||||
"requestId": reqMsg.RequestID,
|
||||
"data": dataStr,
|
||||
}))
|
||||
default:
|
||||
err = fmt.Errorf("message type %s not supported", reqMsg.Type)
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
logger.Warnf("ws Shell UID %s err: %s", client.BindUid, err.Error())
|
||||
msgByte, _ := json.Marshal(result.ErrMsg(err.Error()))
|
||||
client.MsgChan <- msgByte
|
||||
if err == io.EOF {
|
||||
// 等待1s后关闭连接
|
||||
time.Sleep(1 * time.Second)
|
||||
client.StopChan <- struct{}{}
|
||||
}
|
||||
return
|
||||
}
|
||||
if len(resByte) > 0 {
|
||||
client.MsgChan <- resByte
|
||||
}
|
||||
}
|
||||
|
||||
@@ -35,6 +35,11 @@ func Setup(router *gin.Engine) {
|
||||
collectlogs.OperateLog(collectlogs.OptionNew("log.operate.title.ws", collectlogs.BUSINESS_TYPE_OTHER)),
|
||||
controller.NewWSController.Telnet,
|
||||
)
|
||||
wsGroup.GET("/redis",
|
||||
middleware.PreAuthorize(nil),
|
||||
collectlogs.OperateLog(collectlogs.OptionNew("log.operate.title.ws", collectlogs.BUSINESS_TYPE_OTHER)),
|
||||
controller.NewWSController.Redis,
|
||||
)
|
||||
wsGroup.GET("/view",
|
||||
middleware.PreAuthorize(nil),
|
||||
collectlogs.OperateLog(collectlogs.OptionNew("log.operate.title.ws", collectlogs.BUSINESS_TYPE_OTHER)),
|
||||
|
||||
Reference in New Issue
Block a user