Golang中Websocket连接异常关闭(错误代码1006)的解决方法

Golang中Websocket连接异常关闭(错误代码1006)的解决方法 我一直在尝试学习 WebSockets,但我的 WebSocket 连接似乎工作不正常,客户端可以连接,但会立即因以下错误而断开连接。

websocket: close 1006 (abnormal closure): unexpected EOF

这是我的 main.go

2020-02-05 2020-02-05%20(1)

请帮我解决这个错误。


更多关于Golang中Websocket连接异常关闭(错误代码1006)的解决方法的实战教程也可以访问 https://www.itying.com/category-94-b0.html

2 回复

请不要以截图形式包含代码。请将代码的相关部分以代码形式包含进来。

更多关于Golang中Websocket连接异常关闭(错误代码1006)的解决方法的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


在Golang中,WebSocket连接异常关闭(错误代码1006)通常是由于服务器端未正确处理WebSocket握手或连接保持导致的。以下是基于你提供的代码片段的解决方案:

package main

import (
    "log"
    "net/http"
    "time"

    "github.com/gorilla/websocket"
)

var upgrader = websocket.Upgrader{
    ReadBufferSize:  1024,
    WriteBufferSize: 1024,
    CheckOrigin: func(r *http.Request) bool {
        return true // 生产环境中应验证来源
    },
}

func handleWebSocket(w http.ResponseWriter, r *http.Request) {
    conn, err := upgrader.Upgrade(w, r, nil)
    if err != nil {
        log.Printf("升级到WebSocket失败: %v", err)
        return
    }
    defer conn.Close()

    // 设置读写超时
    conn.SetReadDeadline(time.Now().Add(60 * time.Second))
    conn.SetWriteDeadline(time.Now().Add(60 * time.Second))

    // 设置Pong处理器
    conn.SetPongHandler(func(string) error {
        conn.SetReadDeadline(time.Now().Add(60 * time.Second))
        return nil
    })

    // 启动ping循环
    go func() {
        ticker := time.NewTicker(30 * time.Second)
        defer ticker.Stop()
        
        for {
            select {
            case <-ticker.C:
                if err := conn.WriteControl(websocket.PingMessage, []byte{}, time.Now().Add(10*time.Second)); err != nil {
                    log.Printf("发送ping失败: %v", err)
                    return
                }
            }
        }
    }()

    // 主消息循环
    for {
        messageType, message, err := conn.ReadMessage()
        if err != nil {
            if websocket.IsUnexpectedCloseError(err, websocket.CloseGoingAway, websocket.CloseAbnormalClosure) {
                log.Printf("WebSocket错误: %v", err)
            }
            break
        }

        // 处理消息
        log.Printf("收到消息: %s", message)
        
        // 回显消息
        if err := conn.WriteMessage(messageType, message); err != nil {
            log.Printf("发送消息失败: %v", err)
            break
        }
    }
}

func main() {
    http.HandleFunc("/ws", handleWebSocket)
    log.Println("服务器启动在 :8080")
    log.Fatal(http.ListenAndServe(":8080", nil))
}

关键改进点:

  1. 添加CheckOrigin函数:允许跨域请求,避免握手失败
  2. 设置读写超时:防止连接无限制等待
  3. 实现Ping/Pong机制:保持连接活跃
  4. 正确处理关闭错误:区分正常关闭和异常关闭
  5. 添加错误日志:便于调试

客户端连接示例:

// JavaScript客户端示例
const socket = new WebSocket('ws://localhost:8080/ws');

socket.onopen = function() {
    console.log('连接已建立');
    socket.send('Hello Server');
};

socket.onmessage = function(event) {
    console.log('收到消息:', event.data);
};

socket.onclose = function(event) {
    console.log('连接关闭:', event.code, event.reason);
};

确保已安装gorilla/websocket包:

go get github.com/gorilla/websocket

如果问题仍然存在,检查防火墙设置、代理配置或网络限制,这些也可能导致1006错误。

回到顶部