GO 语言websocket编程
生活随笔
收集整理的這篇文章主要介紹了
GO 语言websocket编程
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
GO提供原生的websocket API,使用時go get然后引用即可
golang.org/x/net/websocket
使用起來也很方便,直接上代碼吧。
一個echo server的代碼
package mainimport("golang.org/x/net/websocket""fmt""net/http""flag" )type WSServer struct {ListenAddr string }func (this *WSServer)handler(conn *websocket.Conn){fmt.Printf("a new ws conn: %s->%s\n", conn.RemoteAddr().String(), conn.LocalAddr().String())var err errorfor {var reply stringerr = websocket.Message.Receive(conn, &reply)if err != nil {fmt.Println("receive err:",err.Error())break}fmt.Println("Received from client: " + reply)if err = websocket.Message.Send(conn, reply); err != nil {fmt.Println("send err:", err.Error())break}} } func (this *WSServer)start()(error){http.Handle("/ws", websocket.Handler(this.handler))fmt.Println("begin to listen")err := http.ListenAndServe(this.ListenAddr, nil)if err != nil {fmt.Println("ListenAndServe:", err)return err}fmt.Println("start end")return nil }func main(){addr := flag.String("a", "127.0.1.1:12345", "websocket server listen address")flag.Parse()wsServer := &WSServer{ListenAddr : *addr,}wsServer.start()fmt.Println("------end-------") }上述代碼中,每來一個新的websocket client,server會起一個goroutine執行WSSever的handler函數。
websocket client代碼實例
package mainimport ("flag""fmt""time""golang.org/x/net/websocket" )var addr = flag.String("addr", "127.0.0.1:12345", "http service address")func main() {flag.Parse()url := "ws://"+ *addr + "/ws"origin := "test://1111111/"ws, err := websocket.Dial(url, "", origin)if err != nil {fmt.Println(err)}go timeWriter(ws)for {var msg [512]byte_, err := ws.Read(msg[:])//此處阻塞,等待有數據可讀if err != nil {fmt.Println("read:", err)return}fmt.Printf("received: %s\n", msg)} }func timeWriter(conn *websocket.Conn) {for {time.Sleep(time.Second * 2)websocket.Message.Send(conn, "hello world")} }client的代碼,每隔2秒鐘發送hello world到server,然后阻塞在Read函數。需要注意的是origin必須以“http://1111111/” 這種標準的URI格式,否則報錯“invalid URI for request”。
關閉進程、網絡斷線等異常情況
關閉進程
無論server還是client,關閉進程,對端Read都會立刻收到EOF,對EOF做處理即可。
網絡斷線
- 測試
client和server部署在不同機器上,client每隔2秒中向server發送數據,server收到后回吐給客戶端。這個過程中,拔掉client的網線。 - 測試結果
- 斷網后,client一定時間內寫都能成功返回,但是因為斷網實際沒有發送出去,數據寫到了底層tcp的緩沖區。
- 過一段時間后,1分鐘左右,client Read返回錯誤“read: operation timed out”。Write會返回“write: broken pipe”。這個可能是Go中websocket實現時加了超時機制,也有可能是設置了底層TCP SO_KEEPALIVE,檢測到了網絡不可用。
- 在Read/Write返回錯誤之前,重新連上網絡,可以繼續發送和接受數據。這個可以從TCP的實現上解釋。TCP連接并不是物理連接,本質上就是連接兩端各自系統內核維護的一個四元組。客戶端斷線,在一定時間內并不會導致四元組的釋放。所以當連上網線后此TCP連接可以自動恢復,繼續進行正常的網絡操作。
- 斷線重連到其他網絡,相當于斷網。這個很好解釋,連上其他網絡,IP地址都改變了,之前的四元組不可用。
--------------------- 本文來自 阿冬哥 的CSDN 博客 ,全文地址請點擊:https://blog.csdn.net/c359719435/article/details/78845719?utm_source=copy
總結
以上是生活随笔為你收集整理的GO 语言websocket编程的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 现代环境下的网络分割
- 下一篇: 使用Nomad构建弹性基础架构:重新启动