写在前面
前段时间对gin做了再次封装 github.com/aide-cloud/…, 正好我的新项目prometheus- manager
github.com/aide-cloud/… 系统还在设计和开发中, 索性就把原本基于 kratos
框架改成gin-plus
.
prometheus- manager
是用于管理和操作prometheus监控系统的应用系统gin-plus
基于gin
http框架封装的规范性业务库, 旨在简化CRUD
, 降低代码冗余, 提升代码可读性
prometheus-manager项目初始化
.
├── Dockerfile
├── LICENSE
├── Makefile
├── README.md
├── cmd
│ ├── prom_agent
│ ├── prom_console
│ └── prom_server
├── deploy
├── doc
├── go.mod
├── go.sum
└── pkg
prom_server
这里只保留了一个模块来演示
./cmd/prom_server
├── cmd.go # 项目启动文件
├── configs # 配置文件目录
│ ├── config-dev.yaml
│ └── config-pro.yaml
├── core.go # 额外的初始化程序
├── internal # 核心功能都在这里面
│ ├── conf # 服务配置
│ │ ├── conf.go # 配置相关的结构体
│ │ └── method.go # 配置相关的结构体方法
│ ├── data # DB、cache、RPC等操作第三方的都放这里
│ │ └── strategy # 规则模块相关data操作
│ │ └── strategy.go
│ ├── server # 该项目为多服务程序, 故此这里可以有多个服务初始化
│ │ ├── http.go # http服务
│ │ ├── timer.go # 定时器服务
│ │ └── watcher.go # 监听服务
│ └── service # 业务逻辑都在这里
│ ├── api.go # 所有服务的入口
│ ├── option.go # api配置项
│ ├── strategy # 规则管理模块, 以及它对应的CRUD操作
│ ├── create.go # 新增规则
│ ├── delete.go # 删除规则
│ ├── detail.go # 规则详情
│ ├── edit.go # 规则编辑
│ ├── list.go # 规则列表
│ └── strategy.go # 规则模块结构体定义和New方法
└── openapi.yaml # 生成的api文档
data
strategy.go
// data模块下, 默认都给包名增加了data前缀
package dataStrategy
import (
"prometheus-manager/pkg/conn"
"prometheus-manager/pkg/model"
// gorm-normalize也是对gorm做的业务封装, 旨在规范项目中的DB操作
// https://github.com/aide-cloud/gorm-normalize
query "github.com/aide-cloud/gorm-normalize"
"gorm.io/gorm"
)
type (
// Strategy 规则模块的data操作结构体定义
Strategy struct {
query.IAction[model.PromStrategy] // 组合gorm-normalize库下的action, 该库为范型实现, 这样实现后, 就具备了基本的CRUD动作
// 下面是基于model.PromStrategy定义的可以做gorm Preload相关的Key
PreloadAlarmPagesKey query.AssociationKey
PreloadCategoriesKey query.AssociationKey
PreloadAlertLevelKey query.AssociationKey
PreloadGroupInfoKey query.AssociationKey
}
// StrategyOption ...
StrategyOption func(*Strategy)
)
// NewStrategy 实例化规则模块
func NewStrategy(opts ...StrategyOption) *Strategy {
strategy := &Strategy{
IAction: query.NewAction(query.WithDB[model.PromStrategy](conn.GetMysqlDB())), // 注册db action
PreloadAlarmPagesKey: "AlarmPages",
PreloadCategoriesKey: "Categories",
PreloadAlertLevelKey: "AlertLevel",
PreloadGroupInfoKey: "GroupInfo",
}
for _, o := range opts {
o(strategy)
}
return strategy
}
// 下面是封装的公共的Preload方法, 规范Preload使用
// PreloadAlarmPages preload alarm_pages
func (l *Strategy) PreloadAlarmPages() query.Scopemethod {
return func(db *gorm.DB) *gorm.DB {
return db.Preload(string(l.PreloadAlarmPagesKey))
}
}
// PreloadCategories preload categories
func (l *Strategy) PreloadCategories() query.Scopemethod {
return func(db *gorm.DB) *gorm.DB {
return db.Preload(string(l.PreloadCategoriesKey))
}
}
// PreloadAlertLevel preload alert_level
func (l *Strategy) PreloadAlertLevel() query.Scopemethod {
return func(db *gorm.DB) *gorm.DB {
return db.Preload(string(l.PreloadAlertLevelKey))
}
}
// PreloadGroupInfo preload group_info
func (l *Strategy) PreloadGroupInfo() query.Scopemethod {
return func(db *gorm.DB) *gorm.DB {
return db.Preload(string(l.PreloadGroupInfoKey))
}
}
service
strategy.go 模块定义
package strategy
import (
ginplus "github.com/aide-cloud/gin-plus"
"github.com/gin-gonic/gin"
)
var _ IStrategy = (*Strategy)(nil)
type (
// IStrategy ...
IStrategy interface {
// 继承ginplus的两个接口, 然后去实现
ginplus.Middlewarer // 模块级别的中间件注册接口
ginplus.MethoderMiddlewarer // 方法级别中间件注册接口
// add interface method
}
// Strategy ...
Strategy struct {
// add child module
}
// Option ...
Option func(*Strategy)
)
// defaultStrategy ...
func defaultStrategy() *Strategy {
return &Strategy{
// add child module
}
}
// NewStrategy ...
func NewStrategy(opts ...Option) *Strategy {
m := defaultStrategy()
for _, o := range opts {
o(m)
}
return m
}
// Middlewares 添加Strategy模块的公共中间件
func (l *Strategy) Middlewares() []gin.HandlerFunc {
return []gin.HandlerFunc{
func(ctx *gin.Context) {
// your code ...
},
// other ...
}
}
// MethoderMiddlewares 添加Strategy模块的方法级别中间件
func (l *Strategy) MethoderMiddlewares() map[string][]gin.HandlerFunc {
return map[string][]gin.HandlerFunc{
// your method middlewares
}
}
create.go 规则创建
package strategy
import (
"context"
query "github.com/aide-cloud/gorm-normalize"
dataStrategy "prometheus-manager/cmd/prom_server/internal/data/strategy"
"prometheus-manager/pkg/alert"
"prometheus-manager/pkg/model"
)
type (
// CreateStrategyReq 请求参数定义(实现ginplus.IValidater就可以直接校验请求参数, 这里没有去做)
CreateStrategyReq struct {
GroupId uint `json:"group_id"`
Alert string `json:"alert"`
Expr string `json:"expr"`
For string `json:"for"`
Labels alert.Labels `json:"labels"`
Annotations alert.Annotations `json:"annotations"`
// AlarmPageIds 告警页面
AlarmPageIds []uint `json:"alarm_page_ids"`
// PromDictIds 规则类型
PromDictIds []uint `json:"prom_dict_ids"`
// AlertLevelId 告警级别
AlertLevelId uint `json:"alert_level_id"`
}
// CreateStrategyResp 相应参数定义
CreateStrategyResp struct {
ID uint `json:"id"`
}
)
// Create 创建prom规则
func (l *Strategy) Create(ctx context.Context, req *CreateStrategyReq) (*CreateStrategyResp, error) {
// 实例化strategy模块data操作
strategyData := dataStrategy.NewStrategy()
// 准备gorm db操作中的关联数据
alarmPages := make([]*model.PromAlarmPage, 0, len(req.AlarmPageIds))
for _, alarmPageId := range req.AlarmPageIds {
alarmPages = append(alarmPages, &model.PromAlarmPage{BaseModel: query.BaseModel{ID: alarmPageId}})
}
promDicts := make([]*model.PromDict, 0, len(req.PromDictIds))
for _, promDictId := range req.PromDictIds {
promDicts = append(promDicts, &model.PromDict{BaseModel: query.BaseModel{ID: promDictId}})
}
// 准备即将创建的新规则数据
newStrategy := &model.PromStrategy{
GroupID: req.GroupId,
Alert: req.Alert,
Expr: req.Expr,
For: req.For,
Labels: req.Labels,
Annotations: req.Annotations,
AlarmPages: alarmPages,
Categories: promDicts,
AlertLevelID: req.AlertLevelId,
}
// 调用strategyData的创建方法, 创建我们的新规则
if err := strategyData.WithContext(ctx).Create(newStrategy); err != nil {
return nil, err
}
// your code ...
return &CreateStrategyResp{ID: newStrategy.ID}, nil
}
delete.go 规则删除
package strategy
import (
"context"
dataStrategy "prometheus-manager/cmd/prom_server/internal/data/strategy"
)
type (
// DeleteStrategyReq 请求参数
DeleteStrategyReq struct {
ID uint `uri:"id" binding:"required"` // 这里的ID从url中获取(/strategy/:id)
}
// DeleteStrategyResp 响应参数
DeleteStrategyResp struct {
ID uint `json:"id"`
}
)
// Delete 删除规则
func (l *Strategy) Delete(ctx context.Context, req *DeleteStrategyReq) (*DeleteStrategyResp, error) {
// 实例化data操作
strategyData := dataStrategy.NewStrategy()
// 执行删除逻辑
if err := strategyData.WithContext(ctx).DeleteByID(req.ID); err != nil {
return nil, err
}
return &DeleteStrategyResp{ID: req.ID}, nil
}
edit.go 规则编辑
package strategy
import (
"context"
dataStrategy "prometheus-manager/cmd/prom_server/internal/data/strategy"
"prometheus-manager/pkg/alert"
"prometheus-manager/pkg/model"
query "github.com/aide-cloud/gorm-normalize"
"gorm.io/gorm"
"gorm.io/gorm/schema"
)
type (
// EditStrategyReq 请求参数
EditStrategyReq struct {
ID uint `uri:"id" binding:"required"` // 修改数据通过ID修改, 所以这里的ID也是放在URL中的
GroupId uint `json:"group_id"`
Alert string `json:"alert"`
Expr string `json:"expr"`
For string `json:"for"`
Labels alert.Labels `json:"labels"`
Annotations alert.Annotations `json:"annotations"`
// AlarmPageIds 告警页面
AlarmPageIds []uint `json:"alarm_page_ids"`
// PromDictIds 规则类型
PromDictIds []uint `json:"prom_dict_ids"`
// AlertLevelId 告警级别
AlertLevelId uint `json:"alert_level_id"`
}
// EditStrategyResp 相应参数
EditStrategyResp struct {
ID uint `json:"id"`
}
)
// Edit 编辑规则
func (l *Strategy) Edit(ctx context.Context, req *EditStrategyReq) (*EditStrategyResp, error) {
// 实例化data操作
strategyData := dataStrategy.NewStrategy()
// 查询要修改的数据是否存在
firstDetail, err := strategyData.WithContext(ctx).FirstByID(req.ID)
if err != nil {
return nil, err
}
// 用查到的数据和传入的数据对比, 得到要修改的数据
updateMap := buildUpdateMap(req, firstDetail)
alarmPages := make([]schema.Tabler, 0, len(req.AlarmPageIds))
for _, alarmPageId := range req.AlarmPageIds {
alarmPages = append(alarmPages, &model.PromAlarmPage{BaseModel: query.BaseModel{ID: alarmPageId}})
}
promDicts := make([]schema.Tabler, 0, len(req.PromDictIds))
for _, promDictId := range req.PromDictIds {
promDicts = append(promDicts, &model.PromDict{BaseModel: query.BaseModel{ID: promDictId}})
}
// 因为这里需要修改规则自身数据, 还要修改规则关联的其他数据, 所以用了事物
err = strategyData.DB().Transaction(func(tx *gorm.DB) error {
// 修改规则自身数据
if err := strategyData.WithDB(tx).WithContext(ctx).UpdateMapByID(req.ID, updateMap); err != nil {
return err
}
// 替换关联的数据
if err := strategyData.WithDB(tx).WithContext(ctx).Scopes(query.WhereID(req.ID)).Association().Replace(strategyData.PreloadAlarmPagesKey, alarmPages...); err != nil {
return err
}
if err := strategyData.WithDB(tx).WithContext(ctx).Scopes(query.WhereID(req.ID)).Association().Replace(strategyData.PreloadCategoriesKey, promDicts...); err != nil {
return err
}
return nil
})
if err != nil {
return nil, err
}
return &EditStrategyResp{ID: req.ID}, nil
}
// buildUpdateMap 返回要修改的新数据
func buildUpdateMap(req *EditStrategyReq, firstDetail *model.PromStrategy) map[string]any {
updateMap := map[string]interface{}{}
if req.GroupId != firstDetail.GroupID {
updateMap["group_id"] = req.GroupId
}
if req.Alert != firstDetail.Alert {
updateMap["alert"] = req.Alert
}
if req.Expr != firstDetail.Expr {
updateMap["expr"] = req.Expr
}
if req.For != firstDetail.For {
updateMap["for"] = req.For
}
if !req.Labels.Equal(firstDetail.Labels) {
updateMap["labels"] = req.Labels
}
if !req.Annotations.Equal(firstDetail.Annotations) {
updateMap["annotations"] = req.Annotations
}
alarmPages := make([]*model.PromAlarmPage, 0, len(req.AlarmPageIds))
for _, alarmPageId := range req.AlarmPageIds {
alarmPages = append(alarmPages, &model.PromAlarmPage{BaseModel: query.BaseModel{ID: alarmPageId}})
}
updateMap["alarm_pages"] = alarmPages
promDicts := make([]*model.PromDict, 0, len(req.PromDictIds))
for _, promDictId := range req.PromDictIds {
promDicts = append(promDicts, &model.PromDict{BaseModel: query.BaseModel{ID: promDictId}})
}
updateMap["categories"] = promDicts
return updateMap
}
detail.go 规则详情
package strategy
import (
"context"
dataStrategy "prometheus-manager/cmd/prom_server/internal/data/strategy"
"prometheus-manager/pkg/alert"
"prometheus-manager/pkg/model"
"prometheus-manager/pkg/times"
)
type (
// DetailStrategyReq 请求参数
DetailStrategyReq struct {
ID uint `uri:"id" binding:"required"` // 这里也是通过ID查询规则详情, 所以ID也是放在URL中
IsDelete bool `form:"is_delete"` // 这个参数用于控制是否查询已经被软删除的数据, 来自于params
}
// DetailStrategyResp 响应参数
DetailStrategyResp struct {
Group *GroupItem `json:"group"`
ID uint `json:"id"`
Alert string `json:"alert"`
Expr string `json:"expr"`
For string `json:"for"`
Labels alert.Labels `json:"labels"` // 标签
Annotations alert.Annotations `json:"annotations"` // 告警文案
AlarmPages []*AlarmPageItem `json:"alarm_pages"`
Categories []*CategoryItem `json:"categories"`
AlertLevel *AlertLevelItem `json:"alert_level"`
Status model.Status `json:"status"`
CreatedAt int64 `json:"created_at"`
UpdatedAt int64 `json:"updated_at"`
DeletedAt int64 `json:"deleted_at"`
}
GroupItem struct {
ID uint `json:"id"`
Name string `json:"name"`
}
AlarmPageItem struct {
ID uint `json:"id"`
Name string `json:"name"`
}
CategoryItem struct {
ID uint `json:"id"`
Name string `json:"name"`
}
AlertLevelItem struct {
ID uint `json:"id"`
Name string `json:"name"`
}
)
// Detail 规则详情
func (l *Strategy) Detail(ctx context.Context, req *DetailStrategyReq) (*DetailStrategyResp, error) {
// 实例化data操作
strategyData := dataStrategy.NewStrategy()
// 查询规则信息
var detailInfo *model.PromStrategy
var err error
if req.IsDelete {
detailInfo, err = strategyData.WithContext(ctx).FirstByIDWithTrashed(req.ID)
} else {
detailInfo, err = strategyData.WithContext(ctx).FirstByID(req.ID)
}
if err != nil {
return nil, err
}
// 组装数据返回
return &DetailStrategyResp{
ID: detailInfo.ID,
Alert: detailInfo.Alert,
Expr: detailInfo.Expr,
For: detailInfo.For,
Labels: detailInfo.Labels,
Annotations: detailInfo.Annotations,
AlertLevel: buildAlertLevelItem(detailInfo.AlertLevel),
AlarmPages: buildAlarmPageItems(detailInfo.AlarmPages),
Categories: buildCategoryItems(detailInfo.Categories),
Group: buidGroupItem(detailInfo.GroupInfo),
Status: detailInfo.Status,
CreatedAt: times.TimeToUnix(detailInfo.CreatedAt),
UpdatedAt: times.TimeToUnix(detailInfo.UpdatedAt),
DeletedAt: int64(detailInfo.DeletedAt),
}, nil
}
func buidGroupItem(group *model.PromGroup) *GroupItem {
if group == nil {
return nil
}
return &GroupItem{
ID: group.ID,
Name: group.Name,
}
}
func buildAlertLevelItem(alertLevel *model.PromDict) *AlertLevelItem {
if alertLevel == nil {
return nil
}
return &AlertLevelItem{
ID: alertLevel.ID,
Name: alertLevel.Name,
}
}
func buildAlarmPageItems(alarmPages []*model.PromAlarmPage) []*AlarmPageItem {
alarmPageItems := make([]*AlarmPageItem, 0, len(alarmPages))
for _, alarmPage := range alarmPages {
if alarmPage == nil {
continue
}
alarmPageItems = append(alarmPageItems, &AlarmPageItem{
ID: alarmPage.ID,
Name: alarmPage.Name,
})
}
return alarmPageItems
}
func buildCategoryItems(categories []*model.PromDict) []*CategoryItem {
categoryItems := make([]*CategoryItem, 0, len(categories))
for _, category := range categories {
if category == nil {
continue
}
categoryItems = append(categoryItems, &CategoryItem{
ID: category.ID,
Name: category.Name,
})
}
return categoryItems
}
list.go 规则列表
package strategy
import (
"context"
dataStrategy "prometheus-manager/cmd/prom_server/internal/data/strategy"
"prometheus-manager/pkg/alert"
"prometheus-manager/pkg/times"
query "github.com/aide-cloud/gorm-normalize"
)
type (
// ListStrategyReq 请求参数
ListStrategyReq struct {
Keyword string `form:"keyword"` // 关键字查询
Curr int `form:"curr"` // 分页相关
Size int `form:"size"`
}
// ListStrategyResp 响应参数
ListStrategyResp struct {
List []*StrategyItem `json:"list"` // 数据列表
Page *query.Page `json:"page"` // 分页信息
}
StrategyItem struct {
ID uint `json:"id"`
Alert string `json:"alert"`
Expr string `json:"expr"`
For string `json:"for"`
Labels alert.Labels `json:"labels"`
// Annotations 告警文案
Annotations alert.Annotations `json:"annotations"`
// AlertLevel 告警级别
AlertLevel *AlertLevelItem `json:"alert_level"`
// GroupInfo 所属规则组
GroupInfo *GroupItem `json:"group_info"`
CreatedAt int64 `json:"created_at"`
UpdatedAt int64 `json:"updated_at"`
DeletedAt int64 `json:"deleted_at"`
}
)
// List 规则列表
func (l *Strategy) List(ctx context.Context, req *ListStrategyReq) (*ListStrategyResp, error) {
// 实例化规则data操作
strategyData := dataStrategy.NewStrategy()
// 构建where条件
wheres := []query.Scopemethod{
query.WhereLikeKeyword(req.Keyword, "alert"), // 基于alert字段模糊查询
strategyData.PreloadAlertLevel(), // 预加载
strategyData.PreloadGroupInfo(), // 预加载
}
// 分页实例
pgInfo := query.NewPage(req.Curr, req.Size)
// 执行查询
strategies, err := strategyData.WithContext(ctx).List(pgInfo, wheres...)
if err != nil {
return nil, err
}
// 组装响应数据
list := make([]*StrategyItem, 0, len(strategies))
for _, strategy := range strategies {
list = append(list, &StrategyItem{
ID: strategy.ID,
Alert: strategy.Alert,
Expr: strategy.Expr,
For: strategy.For,
Labels: strategy.Labels,
Annotations: strategy.Annotations,
AlertLevel: buildAlertLevelItem(strategy.AlertLevel),
GroupInfo: buidGroupItem(strategy.GroupInfo),
CreatedAt: times.TimeToUnix(strategy.CreatedAt),
UpdatedAt: times.TimeToUnix(strategy.UpdatedAt),
DeletedAt: int64(strategy.DeletedAt),
})
}
return &ListStrategyResp{
List: list,
Page: pgInfo,
}, nil
}
api模块声明
api.go
package service
import (
alarmHistory "prometheus-manager/cmd/prom_server/internal/service/alarm_history"
alarmPage "prometheus-manager/cmd/prom_server/internal/service/alarm_page"
promDict "prometheus-manager/cmd/prom_server/internal/service/prom_dict"
"prometheus-manager/cmd/prom_server/internal/service/strategy"
strategyGroup "prometheus-manager/cmd/prom_server/internal/service/strategy_group"
ginplus "github.com/aide-cloud/gin-plus"
"github.com/gin-gonic/gin"
)
var _ IApi = (*Api)(nil)
type (
// IApi ...
IApi interface {
ginplus.Middlewarer
ginplus.MethoderMiddlewarer
// add interface method
}
// Api ...
Api struct {
// add child module
Strategy *strategy.Strategy
StrategyGroup *strategyGroup.StrategyGroup
PromDict *promDict.PromDict
AlarmPage *alarmPage.AlarmPage
History *alarmHistory.AlarmHistory
}
// ApiOption ...
ApiOption func(*Api)
)
// defaultApi ...
func defaultApi() *Api {
return &Api{
// add child module
}
}
// NewApi ...
func NewApi(opts ...ApiOption) *Api {
m := defaultApi()
for _, o := range opts {
o(m)
}
return m
}
// Middlewares 添加Api模块的公共中间件
func (l *Api) Middlewares() []gin.HandlerFunc {
return []gin.HandlerFunc{
func(ctx *gin.Context) {
// your code ...
},
// other ...
}
}
// MethoderMiddlewares ...
func (l *Api) MethoderMiddlewares() map[string][]gin.HandlerFunc {
return map[string][]gin.HandlerFunc{
// your method middlewares
}
}
server
http.go gin-plus http定义
package server
import (
"fmt"
"time"
"prometheus-manager/cmd/prom_server/internal/conf"
"prometheus-manager/cmd/prom_server/internal/service"
alarmHistory "prometheus-manager/cmd/prom_server/internal/service/alarm_history"
alarmPage "prometheus-manager/cmd/prom_server/internal/service/alarm_page"
promDict "prometheus-manager/cmd/prom_server/internal/service/prom_dict"
"prometheus-manager/cmd/prom_server/internal/service/strategy"
strategyGroup "prometheus-manager/cmd/prom_server/internal/service/strategy_group"
ginplus "github.com/aide-cloud/gin-plus"
"github.com/gin-gonic/gin"
"github.com/go-kratos/kratos/v2/log"
)
// NewHttpServer 实例化http服务
func NewHttpServer(server *conf.Server, looger log.Logger) *ginplus.GinEngine {
logHelper := log.NewHelper(log.With(looger, "module", "server/server"))
logHelper.Infof("HttpServer starting")
middle := ginplus.NewMiddleware()
var r *gin.Engine
// 初始化gin实例
if server.Mode == gin.DebugMode {
gin.SetMode(gin.DebugMode)
r = gin.Default()
} else {
gin.SetMode(gin.ReleaseMode)
r = gin.New()
}
r.Use(
middle.Cors(),
middle.Logger(server.Name, time.DateTime),
)
// 初始化ginplus实例
ginplusEngine := ginplus.New(r,
ginplus.WithAddr(fmt.Sprintf("%s:%d", server.Http.Host, server.Http.Port)), // 自定义服务地址, 默认8080
ginplus.AppendHttpMethodPrefixes(httpMethodPrefixes...), // 注册自定义http方法识别的前缀
// 注册api模块
ginplus.WithControllers(
service.NewApi(
service.WithStrategyApi(strategy.NewStrategy()),
service.WithStrategyGroupApi(strategyGroup.NewStrategyGroup()),
service.WithPromDictApi(promDict.NewPromDict()),
service.WithAlarmPageApi(alarmPage.NewAlarmPage()),
service.WithAlarmHistoryApi(alarmHistory.NewAlarmHistory()),
),
),
)
// 注册默认路由
ginplusEngine.RegisterPing().RegisterSwaggerUI().RegisterMetrics()
return ginplusEngine
}
// http方法匹配的前缀, 例如CreateUser就会匹配 POST /user
var httpMethodPrefixes = []ginplus.HttpMethod{
{
Prefix: "Create",
Method: ginplus.Post,
}, {
Prefix: "Update",
Method: ginplus.Put,
}, {
Prefix: "Edit",
Method: ginplus.Put,
}, {
Prefix: "Delete",
Method: ginplus.Delete,
}, {
Prefix: "Detail",
Method: ginplus.Get,
}, {
Prefix: "List",
Method: ginplus.Get,
}, {
Prefix: "Login",
Method: ginplus.Post,
}, {
Prefix: "Logout",
Method: ginplus.Post,
}, {
Prefix: "Register",
Method: ginplus.Post,
},
}
服务启动
cmd.go
package main
import (
"flag"
"prometheus-manager/cmd/prom_server/internal/server"
"prometheus-manager/pkg/hello"
"prometheus-manager/pkg/plog"
ginplus "github.com/aide-cloud/gin-plus"
)
var (
// Version 版本号
Version string
// ServiceName 服务名称
ServiceName = "prom-server"
// configPath 配置文件路径
configPath = flag.String("config", "configs/config.yaml", "config file path")
)
func main() {
flag.Parse()
bc := Init()
// 初始化日志
logger := plog.NewLog()
hello.FmtASCIIGenerator(ServiceName, Version, bc.GetServer().GetMatadata())
// 多服务注册
svs := []ginplus.Server{
server.NewHttpServer(bc.GetServer(), logger),
server.NewWatchServer(bc.GetKafka(), bc.GetAlert(), logger),
server.NewTimer(bc.GetPushStrategy(), logger),
}
// 启动gin-plus
ginplus.NewCtrlC(svs...).Start()
}
启动
❯ make server
Starting development server...
# 根据is_dev判断是否是开发环境,如果是开发环境,使用config-dev.yaml配置文件,否则使用config-prod.yaml配置文件
{"level":"info","msg":"prometheus-manager_server version: "}
prometheus-manager_server service starting...
┌───────────────────────────────────────────────────────────────────────────────────────┐
│ _____ _____ ______ │
│ /\ |_ _|| __ \ | ____| │
│ / \ | | || | | || |__ │
│ / /\ \ | | || | | || __| │
│ / /__\ \ _| |_|| |__| || |____ │
│ /_/ \_\|_____||_____/ |______| │
│ good luck and no bug │
└───────────────────────────────────────────────────────────────────────────────────────┘
┌───────────────────────────────────────────────────────────────────────────────────────
├── Name: prometheus-manager_server
├── Version:
├── ID: WutongMacBook-Pro.local
├── Metadata:
├────── version: 1.0.0
├────── description: prometheus-manager_server is a prometheus manager server
└───────────────────────────────────────────────────────────────────────────────────────
{"level":"info","msg":"moduleserver/servermsgHttpServer starting"}
[GIN-debug] [WARNING] Creating an Engine instance with the Logger and Recovery middleware already attached.
[GIN-debug] [WARNING] Running in "debug" mode. Switch to "release" mode in production.
- using env: export GIN_MODE=release
- using code: gin.SetMode(gin.ReleaseMode)
[GIN-debug] POST /api/strategy/create --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] DELETE /api/strategy/delete/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /api/strategy/detail/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] PUT /api/strategy/edit/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /api/strategy/list --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] POST /api/strategyGroup/create --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] DELETE /api/strategyGroup/delete/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /api/strategyGroup/detail/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] PUT /api/strategyGroup/edit/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] POST /api/strategyGroup/list --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] POST /api/promDict/create --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] DELETE /api/promDict/delete/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /api/promDict/detail/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] PUT /api/promDict/edit/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /api/promDict/list --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] POST /api/alarmPage/create --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] DELETE /api/alarmPage/delete/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /api/alarmPage/detail/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] PUT /api/alarmPage/edit/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /api/alarmPage/list --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /api/alarmHistory/detail/:id --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /api/alarmHistory/list --> github.com/aide-cloud/gin-plus.(*GinEngine).newDefaultHandler.func1 (7 handlers)
[GIN-debug] GET /ping --> github.com/aide-cloud/gin-plus.New.func1 (5 handlers)
[GIN-debug] GET /swagger-ui/*filepath --> github.com/gin-gonic/gin.(*RouterGroup).createStaticHandler.func1 (5 handlers)
[GIN-debug] HEAD /swagger-ui/*filepath --> github.com/gin-gonic/gin.(*RouterGroup).createStaticHandler.func1 (5 handlers)
[GIN-debug] GET /openapi/doc/swagger --> github.com/aide-cloud/gin-plus.registerSwaggerUI.func1 (5 handlers)
[GIN-debug] GET /metrics --> github.com/aide-cloud/gin-plus.registerMetrics.WrapH.func1 (5 handlers)
{"level":"warn","msg":"moduleserver/servermsgNot enabel kafka"}
{"level":"info","msg":"moduleserver/servermsg[WatchServer] server starting"}
2023/10/17 22:04:43 [GIN-PLUS] [INFO] Server is running at 0.0.0.0:8080
{"level":"info","msg":"moduleserver/timermsg[Timer] server starting"}