package main import ( "Dynamic_environmental_detection/business" "Dynamic_environmental_detection/connect" "Dynamic_environmental_detection/logger" "encoding/json" "flag" "log" "os" "os/signal" "strconv" "syscall" "time" ) func main() { // 解析命令行参数 debugMode := flag.Bool("debug", false, "Enable debug mode") slaveID := flag.String("slave", "2", "Slave address (debug mode only)") sensorType := flag.String("type", "1", "Sensor type 1-Temperature/Humidity, 2-Water Leak, 3-Smoke (debug mode only)") rawCommand := flag.String("cmd", "", "Raw Modbus command (hexadecimal, debug mode only)") flag.Parse() // 初始化日志 if err := logger.InitLogger(); err != nil { log.Fatal("Failed to initialize logger:", err) } defer logger.Close() // 调试模式 if *debugMode { runDebugMode(*slaveID, *sensorType, *rawCommand) return } // 正常模式 runNormalMode() } // runDebugMode 运行调试模式 func runDebugMode(slaveID, sensorType, rawCommand string) { logger.Logger.Printf("=== Environmental Detection System Debug Mode ===") debugHandler := business.NewDebugHandler() if rawCommand != "" { // 原始命令模式 if err := debugHandler.TestRawCommand(rawCommand); err != nil { logger.Logger.Printf("Debug failed: %v", err) os.Exit(1) } } else { // 设备测试模式 if err := debugHandler.TestDevice(slaveID, sensorType); err != nil { logger.Logger.Printf("Debug failed: %v", err) os.Exit(1) } } } // setupGracefulShutdown 设置优雅关闭 func setupGracefulShutdown() { sigChan := make(chan os.Signal, 1) signal.Notify(sigChan, syscall.SIGINT, syscall.SIGTERM) go func() { sig := <-sigChan logger.Logger.Printf("Received signal: %v, starting shutdown", sig) // 关闭 WebSocket 连接 connect.Close() logger.Logger.Printf("WebSocket connection closed") logger.Logger.Printf("=== System exited ===") os.Exit(0) }() } // runNormalMode 运行正常模式 func runNormalMode() { logger.Logger.Printf("=== Environmental Detection System Starting ===") // 原有的正常模式代码... // 2. 初始化 WebSocket 连接 logger.Logger.Printf("Initializing WebSocket connection...") if err := connect.InitWSChannel(); err != nil { log.Fatal("WebSocket connection initialization failed:", err) } // 3. 解析配置文件 logger.Logger.Printf("Parsing sensor configuration file...") configs, err := business.ParseServiceConfig("/usr/local/etc/service.conf") if err != nil { log.Fatal("Configuration parsing failed:", err) } // 4. 验证配置 if err := business.ValidateConfig(configs); err != nil { log.Fatal("Configuration validation failed:", err) } // 5. 注册服务 logger.Logger.Printf("Registering service to server...") serviceID := connect.GenerateServiceID() metaData := map[string]interface{}{ "version": "1.0", "type": "environment_detection", "sensor_count": len(configs), "description": "Environmental Detection Service", } if err := connect.RegisterService(serviceID, metaData, "environment-detection-container"); err != nil { log.Fatal("Service registration failed:", err) } // 6. 创建业务管理器 logger.Logger.Printf("Creating business manager...") businessManager, err := business.NewBusinessManager(configs) if err != nil { log.Fatal("Failed to create business manager:", err) } defer businessManager.Close() // 7. 订阅主题处理服务器消息 logger.Logger.Printf("Subscribing to device updates topic...") if err := connect.SubscribeTopic("device_updates", handleDeviceUpdates); err != nil { log.Fatal("Topic subscription failed:", err) } logger.Logger.Printf("Subscribing to alert topic (/dthjjc/alert) for buzzer...") if err := connect.SubscribeTopic("/dthjjc/alert", handleAlertMessage); err != nil { logger.Logger.Printf("Failed to subscribe alert topic: %v (continue anyway)", err) } else { logger.Logger.Printf("Successfully subscribed to /dthjjc/alert → buzzer ready!") } // 8. 启动数据采集循环 logger.Logger.Printf("Starting data collection loop...") go startDataCollectionLoop(businessManager) // 9. 设置优雅关闭 setupGracefulShutdown() logger.Logger.Printf("=== System startup completed, beginning operation ===") // 永久运行 select {} } // handleDeviceUpdates 处理设备更新消息 func handleDeviceUpdates(params *connect.PublishParams) { logger.Logger.Printf("Received device update message, topic: %s", params.Topic) var updateData map[string]interface{} if err := json.Unmarshal(params.Data, &updateData); err != nil { logger.Logger.Printf("Failed to parse device update message: %v", err) return } logger.Logger.Printf("Device update content: %+v", updateData) } // startDataCollectionLoop 启动数据采集循环 func startDataCollectionLoop(businessManager *business.BusinessManager) { collectionInterval := 20 * time.Second ticker := time.NewTicker(collectionInterval) defer ticker.Stop() logger.Logger.Printf("Data collection loop started, interval: %v", collectionInterval) for { select { case <-ticker.C: if err := businessManager.StartDataCollection(); err != nil { logger.Logger.Printf("Data collection failed: %v", err) } } } } func handleAlertMessage(params *connect.PublishParams) { payload := params.Content if len(payload) == 0 { payload = params.Data } if len(payload) == 0 { logger.Logger.Printf("平台告警空包 → 强制响 3 秒") business.TriggerBuzzer(3) return } raw := string(payload) logger.Logger.Printf("收到告警原始内容 → %s", raw) type Cmd struct { Type int `json:"type"` BuzzerDuration json.RawMessage `json:"buzzer_duration"` // 万能类型! } var cmd Cmd var outer string if json.Unmarshal(payload, &outer) == nil { logger.Logger.Printf("检测到外层是字符串 → %s", outer) raw = outer } if err := json.Unmarshal([]byte(raw), &cmd); err != nil { logger.Logger.Printf("最终解析失败: %v → 暴力识别", err) } else if cmd.Type == 1 { dur := 3 var temp interface{} if json.Unmarshal(cmd.BuzzerDuration, &temp) == nil { switch v := temp.(type) { case string: if n, err := strconv.Atoi(v); err == nil { dur = n } case float64: dur = int(v) case int: dur = v } } if dur <= 0 { dur = 3 } logger.Logger.Printf("平台告警解析成功 → 蜂鸣器响 %d 秒!!!", dur) business.TriggerBuzzer(dur) return } // 终极兜底:只要包含 type 和 1 就响 //if strings.Contains(raw, "type") && strings.Contains(raw, "1") { // logger.Logger.Printf("暴力识别告警指令 → 强制响 3 秒") // business.TriggerBuzzer(3) //} }