diff --git a/build/database/lite/install/oauth2_client.sql b/build/database/lite/install/oauth2_client.sql index 72276be1..a73a4e07 100644 --- a/build/database/lite/install/oauth2_client.sql +++ b/build/database/lite/install/oauth2_client.sql @@ -22,3 +22,4 @@ CREATE TABLE "oauth2_client" ( -- ---------------------------- -- Records of oauth2_client -- ---------------------------- +INSERT INTO "oauth2_client" VALUES (1, 'omc5y0j15emByauth2', 'omcl28ybn6y4w9y9ntzsv88hyByauth2', 'Local', '127.0.0.1', '0', '', 0, 'system', 1745919659089, 'system', 1745920239962, ''); diff --git a/build/database/lite/install/sys_i18n.sql b/build/database/lite/install/sys_i18n.sql index 4b06eb8f..2635836f 100644 --- a/build/database/lite/install/sys_i18n.sql +++ b/build/database/lite/install/sys_i18n.sql @@ -313,8 +313,8 @@ INSERT INTO "sys_i18n" VALUES (277, 'config..export.key', '参数键名', 'Confi INSERT INTO "sys_i18n" VALUES (278, 'config..export.value', '参数键值', 'Config Value'); INSERT INTO "sys_i18n" VALUES (279, 'config..export.type', '系统内置', 'Built In'); INSERT INTO "sys_i18n" VALUES (280, 'config..export.remark', '参数说明', 'Config Description'); -INSERT INTO "sys_i18n" VALUES (281, 'config.sys.titleValue', '5G Core Network', '5G Core Network'); -INSERT INTO "sys_i18n" VALUES (282, 'config.sys.copyrightValue', 'Copyright ©2025 5G Core Network', 'Copyright ©2025 5G Core Network'); +INSERT INTO "sys_i18n" VALUES (281, 'config.sys.titleValue', 'Core Network', 'Core Network'); +INSERT INTO "sys_i18n" VALUES (282, 'config.sys.copyrightValue', 'Copyright ©2025 Core Network', 'Copyright ©2025 Core Network'); INSERT INTO "sys_i18n" VALUES (283, 'config.noData', '没有可访问参数配置数据!', 'No parameter configuration data is accessible!'); INSERT INTO "sys_i18n" VALUES (284, 'config.errKey', '无效 key', 'Invalid key'); INSERT INTO "sys_i18n" VALUES (285, 'config.errValueEq', '变更状态与旧值相等!', 'Change state is equal to the old value!'); diff --git a/build/database/std/install/oauth2_client.sql b/build/database/std/install/oauth2_client.sql index 195d85e2..666f679f 100644 --- a/build/database/std/install/oauth2_client.sql +++ b/build/database/std/install/oauth2_client.sql @@ -24,4 +24,9 @@ CREATE TABLE `oauth2_client` ( SET FOREIGN_KEY_CHECKS = 1; +-- +-- Dumping data for table `oauth2_client` +-- +INSERT INTO `oauth2_client` VALUES (1, 'omc5y0j15emByauth2', 'omcl28ybn6y4w9y9ntzsv88hyByauth2', 'Local', '127.0.0.1', '0', '', 0, 'system', 1745919659089, 'system', 1745920239962, ''); + -- Dump completed on 2025-04-25 15:26:56 diff --git a/build/database/std/install/sys_i18n.sql b/build/database/std/install/sys_i18n.sql index 1a97cc8f..9f89fa73 100644 --- a/build/database/std/install/sys_i18n.sql +++ b/build/database/std/install/sys_i18n.sql @@ -295,8 +295,8 @@ INSERT INTO `sys_i18n` VALUES (277, 'config..export.key', '参数键名', 'Confi INSERT INTO `sys_i18n` VALUES (278, 'config..export.value', '参数键值', 'Config Value'); INSERT INTO `sys_i18n` VALUES (279, 'config..export.type', '系统内置', 'Built In'); INSERT INTO `sys_i18n` VALUES (280, 'config..export.remark', '参数说明', 'Config Description'); -INSERT INTO `sys_i18n` VALUES (281, 'config.sys.titleValue', '5G Core Network', '5G Core Network'); -INSERT INTO `sys_i18n` VALUES (282, 'config.sys.copyrightValue', 'Copyright ©2025 5G Core Network', 'Copyright ©2025 5G Core Network'); +INSERT INTO `sys_i18n` VALUES (281, 'config.sys.titleValue', '5G Core Network', 'Core Network'); +INSERT INTO `sys_i18n` VALUES (282, 'config.sys.copyrightValue', 'Copyright ©2025 Core Network', 'Copyright ©2025 Core Network'); INSERT INTO `sys_i18n` VALUES (283, 'config.noData', '没有可访问参数配置数据!', 'No parameter configuration data is accessible!'); INSERT INTO `sys_i18n` VALUES (284, 'config.errKey', '无效 key', 'Invalid key'); INSERT INTO `sys_i18n` VALUES (285, 'config.errValueEq', '变更状态与旧值相等!', 'Change state is equal to the old value!'); diff --git a/build/vendor/omc/database/lite/install/customized.sql b/build/vendor/omc/database/lite/install/customized.sql index 6b1faf30..173fc039 100644 --- a/build/vendor/omc/database/lite/install/customized.sql +++ b/build/vendor/omc/database/lite/install/customized.sql @@ -1,11 +1,11 @@ -- sys_config -UPDATE `sys_config` SET `config_value` = 'https://www.omc.com' WHERE `config_id` = 6; +UPDATE `sys_config` SET `config_value` = '#' WHERE `config_id` = 6; UPDATE `sys_config` SET `config_value` = 'true' WHERE `config_id` = 28; UPDATE `sys_config` SET `config_value` = 'en_US' WHERE `config_id` = 29; -- sys_i18n -UPDATE `sys_i18n` SET `value_zh` = 'OMC', `value_en` = 'OMC' WHERE `id` = 281; -UPDATE `sys_i18n` SET `value_zh` = 'Copyright ©2024 OMC', `value_en` = 'Copyright ©2024 OMC' WHERE `id` = 282; +UPDATE `sys_i18n` SET `value_zh` = 'Core Network', `value_en` = 'Core Network' WHERE `id` = 281; +UPDATE `sys_i18n` SET `value_zh` = 'Copyright ©2025 Core Network', `value_en` = 'Copyright ©2025 Core Network' WHERE `id` = 282; -- set internationalization switching to ON UPDATE `sys_menu` SET `status_flag` = '1' WHERE `menu_id` = 2122; diff --git a/build/vendor/omc/database/std/install/customized.sql b/build/vendor/omc/database/std/install/customized.sql index 34df6a62..173fc039 100644 --- a/build/vendor/omc/database/std/install/customized.sql +++ b/build/vendor/omc/database/std/install/customized.sql @@ -4,8 +4,8 @@ UPDATE `sys_config` SET `config_value` = 'true' WHERE `config_id` = 28; UPDATE `sys_config` SET `config_value` = 'en_US' WHERE `config_id` = 29; -- sys_i18n -UPDATE `sys_i18n` SET `value_zh` = '5G Core Network', `value_en` = '5G Core Network' WHERE `id` = 281; -UPDATE `sys_i18n` SET `value_zh` = 'Copyright ©2025 5G Core Network', `value_en` = 'Copyright ©2025 5G Core Network' WHERE `id` = 282; +UPDATE `sys_i18n` SET `value_zh` = 'Core Network', `value_en` = 'Core Network' WHERE `id` = 281; +UPDATE `sys_i18n` SET `value_zh` = 'Copyright ©2025 Core Network', `value_en` = 'Copyright ©2025 Core Network' WHERE `id` = 282; -- set internationalization switching to ON UPDATE `sys_menu` SET `status_flag` = '1' WHERE `menu_id` = 2122; diff --git a/src/modules/common/common.go b/src/modules/common/common.go index 7a054bc2..e85c96ad 100644 --- a/src/modules/common/common.go +++ b/src/modules/common/common.go @@ -22,6 +22,16 @@ func Setup(router *gin.Engine) { controller.NewIndex.Handler, ) + // 路由服务器时间 + router.GET("/time", + middleware.RateLimit(middleware.LimitOption{ + Time: 60, + Count: 10, + Type: middleware.LIMIT_IP, + }), + controller.NewTimestamp.Handler, + ) + // 通用请求 commonGroup := router.Group("/common") { diff --git a/src/modules/common/controller/timestamp.go b/src/modules/common/controller/timestamp.go new file mode 100644 index 00000000..77db2507 --- /dev/null +++ b/src/modules/common/controller/timestamp.go @@ -0,0 +1,46 @@ +package controller + +import ( + "time" + + "be.ems/src/framework/resp" + + "github.com/gin-gonic/gin" +) + +// 实例化控制层 TimestampController 结构体 +var NewTimestamp = &TimestampController{} + +// 服务器时间 +// +// PATH /time +type TimestampController struct{} + +// Handler 路由 +// +// GET / +// +// @Tags common +// @Accept json +// @Produce json +// @Success 200 {object} object "Response Results" +// @Summary Server Time +// @Description Server Time +// @Router / [get] +func (s TimestampController) Handler(c *gin.Context) { + now := time.Now() + // 获取当前时间戳 + timestamp := now.UnixMilli() + // 获取时区 + timezone := now.Format("-0700") + // 获取时区名称 + timezoneName := now.Format("MST") + // 获取 RFC3339 格式的时间 + rfc3339 := now.Format(time.RFC3339) + c.JSON(200, resp.OkData(map[string]any{ + "timestamp": timestamp, + "timezone": timezone, + "timezoneName": timezoneName, + "rfc3339": rfc3339, + })) +} diff --git a/src/modules/oauth2/controller/oauth2.go b/src/modules/oauth2/controller/oauth2.go index ca47a1e4..f49a9b2b 100644 --- a/src/modules/oauth2/controller/oauth2.go +++ b/src/modules/oauth2/controller/oauth2.go @@ -51,7 +51,7 @@ func (s Oauth2Controller) Authorize(c *gin.Context) { // 判断IP白名单 if !strings.Contains(info.IPWhite, c.ClientIP()) { - c.JSON(200, resp.ErrMsg("IP whitelist mismatch")) + c.JSON(200, resp.ErrMsg("ip whitelist mismatch")) return } @@ -93,7 +93,7 @@ func (s Oauth2Controller) Token(c *gin.Context) { } // 登录客户端信息 - info, err := s.oauth2Service.ByClient(body.ClientId, body.ClientSecret) + info, err := s.oauth2Service.ByClient(body.ClientId, body.ClientSecret, ipaddr) if err != nil { s.oauth2LogLoginService.Insert( body.ClientId, constants.STATUS_NO, err.Error(), @@ -153,8 +153,12 @@ func (s Oauth2Controller) RefreshToken(c *gin.Context) { } clientId := fmt.Sprint(claims[constants.JWT_CLIENT_ID]) + // 当前请求信息 + ipaddr, location := reqctx.IPAddrLocation(c) + os, browser := reqctx.UaOsBrowser(c) + // 客户端信息 - info, err := s.oauth2Service.ByClient(body.ClientId, body.ClientSecret) + info, err := s.oauth2Service.ByClient(body.ClientId, body.ClientSecret, ipaddr) if err != nil { c.JSON(200, resp.ErrMsg(err.Error())) return @@ -192,9 +196,6 @@ func (s Oauth2Controller) RefreshToken(c *gin.Context) { refreshToken, refreshExpiresIn = token.Oauth2TokenCreate(clientId, deviceFingerprint, "refresh") } - // 当前请求信息 - ipaddr, location := reqctx.IPAddrLocation(c) - os, browser := reqctx.UaOsBrowser(c) // 记录令牌,创建系统访问记录 token.Oauth2InfoCreate(&info, deviceFingerprint, [4]string{ipaddr, location, os, browser}) s.oauth2Service.UpdateLoginDateAndIP(info) diff --git a/src/modules/oauth2/controller/oauth2_client.go b/src/modules/oauth2/controller/oauth2_client.go index ca7a7061..846d18f3 100644 --- a/src/modules/oauth2/controller/oauth2_client.go +++ b/src/modules/oauth2/controller/oauth2_client.go @@ -46,11 +46,11 @@ func (s Oauth2ClientController) Info(c *gin.Context) { } info := s.oauth2ClientService.FindByClientId(clientId) - if info.ClientId == "" || info.ClientId != clientId { - c.JSON(200, resp.ErrMsg("clientId does not exist")) + if info.ClientId == clientId { + c.JSON(200, resp.OkData(info)) return } - c.JSON(200, resp.OkData(info)) + c.JSON(200, resp.ErrMsg("clientId does not exist")) } // Add 新增 @@ -68,8 +68,16 @@ func (s Oauth2ClientController) Add(c *gin.Context) { return } - localHost := strings.Contains(body.IPWhite, "127.0.0.1") || strings.Contains(body.IPWhite, "localhost") || strings.Contains(body.IPWhite, "::1") - if localHost || strings.Contains(body.IPWhite, "::ffff:") { + // 本地IP地址不支持 + localHosts := []string{"127.0.0.1", "localhost", "::ffff:", "::1"} + localHost := false + for _, host := range localHosts { + if strings.Contains(body.IPWhite, host) { + localHost = true + break + } + } + if localHost { c.JSON(200, resp.ErrMsg("no support local host")) return } @@ -98,8 +106,16 @@ func (s Oauth2ClientController) Edit(c *gin.Context) { return } - localHost := strings.Contains(body.IPWhite, "127.0.0.1") || strings.Contains(body.IPWhite, "localhost") || strings.Contains(body.IPWhite, "::1") - if localHost || strings.Contains(body.IPWhite, "::ffff:") { + // 本地IP地址不支持 + localHosts := []string{"127.0.0.1", "localhost", "::ffff:", "::1"} + localHost := false + for _, host := range localHosts { + if strings.Contains(body.IPWhite, host) { + localHost = true + break + } + } + if localHost { c.JSON(200, resp.ErrMsg("no support local host")) return } diff --git a/src/modules/oauth2/oauth2.go b/src/modules/oauth2/oauth2.go index edf1e10a..7cc1cbac 100644 --- a/src/modules/oauth2/oauth2.go +++ b/src/modules/oauth2/oauth2.go @@ -5,7 +5,6 @@ import ( "be.ems/src/framework/logger" "be.ems/src/framework/middleware" - monitorController "be.ems/src/modules/monitor/controller" "be.ems/src/modules/oauth2/controller" ) @@ -70,14 +69,6 @@ func Setup(router *gin.Engine) { ) } - // ==== 开放接口 ==== - - openApiGroup := router.Group("/open-api") - { - openApiGroup.GET("/monitor/system", - middleware.AuthorizeOauth2(nil), - monitorController.NewSystem.Info, - ) - } - + // ==== 授权认证的开放接口 ==== + openAPI(router) } diff --git a/src/modules/oauth2/open_api.go b/src/modules/oauth2/open_api.go new file mode 100644 index 00000000..84f96e03 --- /dev/null +++ b/src/modules/oauth2/open_api.go @@ -0,0 +1,33 @@ +package oauth2 + +import ( + "github.com/gin-gonic/gin" + + "be.ems/src/framework/middleware" + monitorController "be.ems/src/modules/monitor/controller" + neController "be.ems/src/modules/network_element/controller" +) + +// openAPI 客户端授权开放接口 +func openAPI(router *gin.Engine) { + openApiGroup := router.Group("/open-api") + + // 监控 + monitorGroup := openApiGroup.Group("/monitor") + { + monitorGroup.GET("/system", + middleware.AuthorizeOauth2(nil), + monitorController.NewSystem.Info, + ) + } + + // 网元 + neGroup := openApiGroup.Group("/ne") + { + neGroup.GET("/state", + middleware.AuthorizeOauth2(nil), + neController.NewNeInfo.State, + ) + } + +} diff --git a/src/modules/oauth2/service/oauth2.go b/src/modules/oauth2/service/oauth2.go index 40293622..3ca444c4 100644 --- a/src/modules/oauth2/service/oauth2.go +++ b/src/modules/oauth2/service/oauth2.go @@ -54,7 +54,7 @@ func (s Oauth2Service) ValidateCode(code string) error { } // ByClient 客户端信息 -func (s Oauth2Service) ByClient(clientId, clientSecret string) (token.Oauth2Info, error) { +func (s Oauth2Service) ByClient(clientId, clientSecret, ipaddr string) (token.Oauth2Info, error) { info := token.Oauth2Info{} // 查询用户登录账号 @@ -66,9 +66,13 @@ func (s Oauth2Service) ByClient(clientId, clientSecret string) (token.Oauth2Info if len(rows) > 0 { item = rows[0] } - if item.ClientId == "" { + if item.ClientId == "" || item.ClientSecret == "" { return info, fmt.Errorf("clientId or clientSecret is not exist") } + // 判断IP白名单 + if !strings.Contains(item.IPWhite, ipaddr) { + return info, fmt.Errorf("ip whitelist mismatch") + } info.ClientId = clientId // 用户权限组标识