Files
kra-new/cmd/alert_trigger_http_test.go
T

127 lines
4.7 KiB
Go

package main
import (
"bytes"
"context"
"encoding/json"
"fmt"
"net/http"
"net/http/httptest"
"path/filepath"
"testing"
"time"
"github.com/gin-gonic/gin"
"github.com/glebarez/sqlite"
"gorm.io/gorm"
businessbiz "kra/internal/biz/business"
taskbiz "kra/internal/biz/task"
businessdata "kra/internal/data/business"
taskdata "kra/internal/data/task"
"kra/internal/server/handler"
"kra/internal/server/router"
taskservice "kra/internal/service/task"
"kra/internal/worker"
platformtask "kra/pkg/task"
)
func TestAlertTriggerThroughNativeTaskHTTP(t *testing.T) {
db, err := gorm.Open(sqlite.Open(filepath.Join(t.TempDir(), "alert-task.db")), &gorm.Config{})
if err != nil {
t.Fatal(err)
}
pool, _ := db.DB()
t.Cleanup(func() { _ = pool.Close() })
for _, step := range append(taskdata.Migrations(), businessdata.Migrations()...) {
if err := step.Migrate(db); err != nil {
t.Fatal(err)
}
}
for _, sql := range []string{
"CREATE TABLE sys_users(id INTEGER,username TEXT,level INTEGER,parent_id INTEGER,id_path TEXT,authority_id INTEGER,deleted_at DATETIME)",
"CREATE TABLE tab_promote(id INTEGER,source_db TEXT,busier_id INTEGER,account TEXT,promote_level INTEGER,status INTEGER,last_login_time INTEGER,create_time INTEGER)",
"INSERT INTO sys_users VALUES(10,'一级',1,0,'0',901,NULL),(20,'二级',2,10,'0,10',902,NULL),(30,'三级',3,20,'0,10,20',903,NULL)",
"INSERT INTO sys_user_bind_platform(user_id,source_db,platform_busier_id,platform_busier_account,status) VALUES(30,'lx',7,'绑定','0')",
"INSERT INTO tab_promote VALUES(10,'lx',7,'测试渠道',1,1,0,1)",
"INSERT INTO sys_alert_rule(rule_name,rule_type,monitor_metric,creator_id,unlogin_days,warning_color,enabled,is_deleted) VALUES('未登录规则','未登录',3,10,1,'red',1,0)",
} {
if err := db.Exec(sql).Error; err != nil {
t.Fatal(err)
}
}
provider := businessHTTPData{db}
registry := platformtask.NewRegistry()
tasks := taskbiz.NewTaskUsecaseWithRegistry(taskdata.NewTaskRepo(reportTaskHTTPData{provider}), registry)
alerts := businessbiz.NewAlertTriggerUsecase(businessdata.NewAlertTriggerRepo(provider))
worker.NewTaskMethods(tasks, nil, nil, nil, nil, alerts).RegisterTasks(registry)
scheduler := worker.NewTaskScheduler(tasks, nil, worker.NewTaskExecutorWithRegistry(tasks, registry), nil)
defer func() {
ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
defer cancel()
_ = scheduler.Stop(ctx)
}()
engine := gin.New()
router.RegisterTask(engine.Group(""), handler.NewTask(taskservice.NewTaskService(taskbiz.NewTaskApplicationUsecase(tasks, scheduler))))
server := httptest.NewServer(engine)
defer server.Close()
call := func(method, path string, body any) map[string]any {
t.Helper()
raw, _ := json.Marshal(body)
req, _ := http.NewRequest(method, server.URL+"/timedTask/"+path, bytes.NewReader(raw))
req.Header.Set("Content-Type", "application/json")
res, err := server.Client().Do(req)
if err != nil {
t.Fatal(err)
}
defer res.Body.Close()
var result map[string]any
if err := json.NewDecoder(res.Body).Decode(&result); err != nil {
t.Fatal(err)
}
if result["code"] != float64(0) {
t.Fatalf("预警任务 HTTP 失败: %+v", result)
}
return result["data"].(map[string]any)
}
call("POST", "createTimedTask", map[string]any{"name": "预警 HTTP 演练", "spec": "@daily", "executorType": "method", "methodName": "alertTriggerTask", "enabled": false})
var id uint
if err := db.Table("sys_timed_tasks").Select("id").Where("name=?", "预警 HTTP 演练").Scan(&id).Error; err != nil || id == 0 {
t.Fatalf("任务未创建: %v", err)
}
for iteration := 0; iteration < 2; iteration++ {
call("POST", "triggerTimedTask", map[string]any{"id": id})
deadline := time.Now().Add(8 * time.Second)
finished := false
for time.Now().Before(deadline) {
logs := call("GET", fmt.Sprintf("getTimedTaskLogList?taskId=%d&page=1&pageSize=10", id), nil)["list"].([]any)
if len(logs) > iteration {
if logs[0].(map[string]any)["status"] != "success" {
t.Fatalf("预警任务失败: %+v", logs)
}
finished = true
break
}
time.Sleep(20 * time.Millisecond)
}
if !finished {
t.Fatal("没有收到预警执行完成日志")
}
}
var rows []struct {
BusinessID, TargetPromoteID uint
Status int
PlatformCode string
}
if err := db.Table("sys_alert_record").Scan(&rows).Error; err != nil {
t.Fatal(err)
}
if len(rows) != 1 || rows[0].BusinessID != 10 || rows[0].TargetPromoteID != 10 || rows[0].PlatformCode != "lx" || rows[0].Status != 1 {
t.Fatalf("重复触发或归属错误: %+v", rows)
}
var enabled int64
db.Table("sys_timed_tasks").Where("enabled=1").Count(&enabled)
if enabled != 0 {
t.Fatal("手动触发不应启用自动计划")
}
}