GO Websocket向所有客户发送消息

要向所有客户端发送消息,您需要在服务器端使用WebSocket连接来管理客户端连接,并使用WebSocket连接实例将消息发送到所有现有客户端。下面是一个简单的示例,它用Go使用Gorilla WebSocket库实现WebSocket服务器和客户端连接。
内存指针转换

            // 创建一个空的 Map
            m := make(map[int64]string)
                ws, err := r.WebSocket()
                if err != nil {
                    glog.Error(ctx, err)
                    r.Exit()
                }

                fmt.Println("original data is", ws)
                // unsafe.Pointer 是内存指针 转换方法
                strPointerHex := fmt.Sprintf("%p", unsafe.Pointer(ws))
                fmt.Println("strPointerHex is", strPointerHex)
                strPointerInt := fmt.Sprintf("%d", unsafe.Pointer(ws))
                fmt.Println("strPointerInt is", strPointerInt)
                // 得到数字用于存储
                int64s, _ := strconv.ParseInt(strPointerInt, 10, 0)
                fmt.Println("int64s is", int64s)
                // var pointer *ghttp.WebSocket
                // pointer = *(**ghttp.WebSocket)(unsafe.Pointer(&int64s))
                // fmt.Println("connection pointer is", pointer)

                // debugMsg := fmt.Sprintf("%p", unsafe.Pointer(pointer))
                // fmt.Println("debugMsg is", debugMsg)
                                m[int64s] = ""
                    for key, value := range m {
                        fmt.Println(key, ":", value)
                        var ws1 *ghttp.WebSocket
                        ws1 = *(**ghttp.WebSocket)(unsafe.Pointer(&key))

                        if err = ws1.WriteMessage(msgType, msg); err != nil {
                            return
                        }
                    }
                                
package main
import (
    "fmt"
    "log"
    "net/http"
    "github.com/gorilla/websocket"
)
// Gorilla WebSocket连接升级器
var upgrader = websocket.Upgrader{
    ReadBufferSize:  1024,
    WriteBufferSize: 1024,
}
// 全局客户端map
var clients = make(map[*websocket.Conn]bool)
// 全局广播消息通道
var broadcast = make(chan []byte)
// WebSocket服务器处理程序
func handleWebSocket(w http.ResponseWriter, r *http.Request) {
    // 升级HTTP连接为WebSocket连接
    conn, err := upgrader.Upgrade(w, r, nil)
    if err != nil {
        log.Println(err)
        return
    }
    // 连接成功时将客户端添加到全局map
    clients[conn] = true
    defer func() {
        // 连接关闭时从全局map删除客户端
        delete(clients, conn)
        conn.Close()
    }()
    for {
        // 读取消息
        _, message, err := conn.ReadMessage()
        if err != nil {
            log.Println(err)
            break
        }
        // 将消息发送到广播通道,以便它可以被广播到所有客户端
        broadcast <- message
    }
}
func main() {
    // 启动WebSocket服务器
    http.HandleFunc("/ws", handleWebSocket)
    go func() {
        err := http.ListenAndServe(":8080", nil)
        if err != nil {
            log.Fatal("ListenAndServe: ", err)
        }
    }()
    //不断处理广播通道上的消息,并向所有客户端发送
    for {
        message := <-broadcast
        for client := range clients {
            err := client.WriteMessage(websocket.TextMessage, message)
            if err != nil {
                log.Println(err)
                client.Close()
                delete(clients, client)
            }
        }
    }
}

这个简单的示例演示了如何使用Go和Gorilla WebSocket库实现WebSocket服务器,处理新的WebSocket连接,将客户端添加到全局map,从客户端读取消息并广播到所有客户端,以及使用它来向所有客户端发送消息。更新广播消息通道以便消息可以在所有连接的客户端之间传播。

goframe框架来做websocket的server

var (
    // Main is the main command.
    Main = gcmd.Command{
        Name:  "main",
        Usage: "main",
        Brief: "start http server of simple goframe demos",
        Func: func(ctx context.Context, parser *gcmd.Parser) (err error) {
            s := g.Server()

            // 创建一个空的 Map
            m := make(map[int64]string)
            // 同时绑定监听 websocket
            s.BindHandler("/ws", func(r *ghttp.Request) {
                ws, err := r.WebSocket()
                if err != nil {
                    glog.Error(ctx, err)
                    r.Exit()
                }
        
                fmt.Println("original data is", ws)
                strPointerHex := fmt.Sprintf("%p", unsafe.Pointer(ws))
                fmt.Println("connection is", strPointerHex)

                strPointerInt := fmt.Sprintf("%d", unsafe.Pointer(ws))
                fmt.Println("connection is", strPointerInt)

                int64s, _ := strconv.ParseInt(strPointerInt, 10, 0)

                // var pointer *ghttp.WebSocket
                // pointer = *(**ghttp.WebSocket)(unsafe.Pointer(&int64s))
                // fmt.Println("connection pointer is", pointer)

                // debugMsg := fmt.Sprintf("%p", unsafe.Pointer(pointer))
                // fmt.Println("debugMsg is", debugMsg)
                m[int64s] = ""
                // 链接参数
                if err = ws.WriteMessage(1, []byte(r.RequestURI)); err != nil {
                    return
                }
                for {
                    msgType, msg, err := ws.ReadMessage()

                    if err != nil {
                        return
                    }
                    m[int64s] = string(msg)
                    for key, value := range m {
                        fmt.Println(key, ":", value)
                        var ws1 *ghttp.WebSocket
                        ws1 = *(**ghttp.WebSocket)(unsafe.Pointer(&key))

                        if err = ws1.WriteMessage(msgType, msg); err != nil {
                            return
                        }
                    }
                    if err = ws.WriteMessage(msgType, []byte("ok")); err != nil {
                        return
                    }
                }
            })
//下面都是http的路由配置 ,如果只需要ws服务 下面可以删除
            s.Use(ghttp.MiddlewareHandlerResponse)
            s.Group("/", func(group *ghttp.RouterGroup) {
                // Group middlewares.
                group.Middleware(
                    service.Middleware().Ctx,
                    ghttp.MiddlewareCORS,
                )
                // 这是 http路由控制器绑定
                group.Bind(
                    user.New(),
                    globaluser.New(),
                )
            })
            s.Run()
            return nil
        },
    }
)
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 219,490评论 6 508
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,581评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 165,830评论 0 356
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,957评论 1 295
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,974评论 6 393
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,754评论 1 307
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,464评论 3 420
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,357评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,847评论 1 317
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,995评论 3 338
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 40,137评论 1 351
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,819评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,482评论 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 32,023评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,149评论 1 272
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,409评论 3 373
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 45,086评论 2 355

推荐阅读更多精彩内容