package main import ( "context" "encoding/json" "fmt" "os" "os/exec" "time" "bet24.com/log" "bet24.com/servers/micros/common" "bet24.com/utils" "github.com/smallnest/rpcx/client" ) var consulAddr = common.Default_Consul_Addr func getClient(servcieName string) client.XClient { return common.GetClientPool().GetClient(servcieName, consulAddr) } type serviceInfo struct { Name string Exe string FailCount int } func (si *serviceInfo) getExecuteFile() string { if si.Exe == "" { return si.Name } return si.Exe } var services []serviceInfo const max_failed_count = 2 func waitInput() { for { var endInput string fmt.Scanln(&endInput) switch endInput { case "list": dumpServices() default: log.Release("unknown command") } } } func dumpServices() { log.Release("listing services") for _, v := range services { log.Release(" %s:[%s][%d]", v.Name, v.Exe, v.FailCount) } log.Release("") } func tryRestart(exe string) { cmd := exec.Command("cmd.exe", "/c", fmt.Sprintf("start cmd.exe /k %v", exe)) cmd.Start() } func loadServices() { data, err := os.ReadFile("serviceconf/monitor.json") if err != nil { log.Debug("read config failed %v", err) time.AfterFunc(time.Second*10, loadServices) return } err = json.Unmarshal(data, &services) if err != nil { log.Debug("Unmarshal config failed err:%v", err) time.AfterFunc(time.Second*10, loadServices) return } time.AfterFunc(time.Second*600, loadServices) } type Request struct { Name string } type Response struct { Data string } func sayHelloToService(si *serviceInfo) { xclient := getClient(si.Name) args := &Request{ Name: si.Name, } reply := &Response{} err := xclient.Call(context.Background(), "SayHello", args, reply) if err != nil { log.Debug("failed to call service[%s]: %v", si.Name, err) common.GetClientPool().RemoveClient(si.Name) // 重启服务 //exe := addFailCount(serviceName) si.FailCount++ if si.FailCount >= max_failed_count { log.Release("service[%s] dead,try to restart", si.Name) si.FailCount = 0 tryRestart(si.getExecuteFile()) } } else { si.FailCount = 0 } } func checkAllServices() { time.AfterFunc(time.Second*10, checkAllServices) for k := range services { sayHelloToService(&services[k]) } } func main() { defer waitInput() // 读取配置 loadServices() utils.SetConsoleTitle(fmt.Sprintf("MicroMonitor0 %d services", len(services))) checkAllServices() }