All checks were successful
Build docker and publish / build (20.15.1) (push) Successful in 7m39s
修复绑定相同邮箱时的错误提示问题,允许重复绑定相同邮箱 重构设备绑定逻辑,增加详细注释和日志记录 移除无用的WebSocket测试端点 更新测试脚本中的默认配置和测试用例
90 lines
2.3 KiB
Go
90 lines
2.3 KiB
Go
package main
|
||
|
||
import (
|
||
"fmt"
|
||
"log"
|
||
"net/http"
|
||
"os"
|
||
"os/signal"
|
||
"time"
|
||
|
||
"github.com/gorilla/websocket"
|
||
)
|
||
|
||
func main() {
|
||
// 默认配置,可用环境变量覆盖
|
||
baseURL := getenvDefault("SERVER_URL", "wss://api.hifast.biz")
|
||
userID := getenvDefault("USER_ID", "23")
|
||
deviceID := getenvDefault("DEVICE_ID", "c76463cff8512722")
|
||
auth := "dkjw6TCQTBlgreyhjN8u32gP0A6RrQ/V50vf8wjNFwFL9hgKJrOOv+ziS03GCQ/8E0fWUzjc4aCoMcVMzUN8vR7CwqR45HbtogoT9iNoElW9rgzpQNbwQ4BHK/Q25WvcgdrhfRzE19nPqUTOcN+4iY6NmeiwHEMLBTzDEeu8wGn/yjVLRMCyh5QJuQizllbrDR5LuTiNEcdSdBSx9cFZYtnJIIyi1b60BZYo4lIyRADCH6smTsLDhoZG0nJvJw3C0XCGvf0jC/4d4u40IvbzKOm1TBSK0lgOzNjvkSfS/DJibAi4l7qNTYmFlQ1wp+iW1MNllqd+OtSavZYoajoZGA=="
|
||
|
||
// 拼接完整 WS 地址
|
||
wsURL := fmt.Sprintf("%s/v1/app/ws/%s/%s", baseURL, userID, deviceID)
|
||
|
||
// 自定义 header(包含 Authorization)
|
||
header := http.Header{}
|
||
header.Set("Authorization", auth)
|
||
|
||
// 建立连接
|
||
dialer := websocket.Dialer{
|
||
HandshakeTimeout: 10 * time.Second,
|
||
}
|
||
conn, _, err := dialer.Dial(wsURL, header)
|
||
if err != nil {
|
||
log.Fatalf("dial error: %v", err)
|
||
}
|
||
defer conn.Close()
|
||
log.Println("connected to", wsURL)
|
||
|
||
// 优雅退出
|
||
interrupt := make(chan os.Signal, 1)
|
||
signal.Notify(interrupt, os.Interrupt)
|
||
|
||
// 心跳:定时发送 "ping"
|
||
ticker := time.NewTicker(25 * time.Second)
|
||
defer ticker.Stop()
|
||
|
||
// 读协程
|
||
done := make(chan struct{})
|
||
go func() {
|
||
defer close(done)
|
||
for {
|
||
mt, msg, err := conn.ReadMessage()
|
||
if err != nil {
|
||
log.Printf("read error: %v", err)
|
||
return
|
||
}
|
||
log.Printf("recv [%d]: %s", mt, string(msg))
|
||
}
|
||
}()
|
||
|
||
// 连接成功后先发一个 "ping"
|
||
if err := conn.WriteMessage(websocket.TextMessage, []byte("ping")); err != nil {
|
||
log.Printf("write ping error: %v", err)
|
||
}
|
||
|
||
for {
|
||
select {
|
||
case <-done:
|
||
return
|
||
case <-ticker.C:
|
||
if err := conn.WriteMessage(websocket.TextMessage, []byte("ping")); err != nil {
|
||
log.Printf("write heartbeat error: %v", err)
|
||
return
|
||
}
|
||
log.Printf("sent heartbeat ping")
|
||
case <-interrupt:
|
||
log.Println("interrupt, closing...")
|
||
_ = conn.WriteMessage(websocket.CloseMessage, websocket.FormatCloseMessage(websocket.CloseNormalClosure, ""))
|
||
return
|
||
}
|
||
}
|
||
}
|
||
|
||
func getenvDefault(key, def string) string {
|
||
if v := os.Getenv(key); v != "" {
|
||
return v
|
||
}
|
||
return def
|
||
}
|