我們可以看到 gorilla/websocket中的examples中有一個聊天室的demo。
成都創(chuàng)新互聯(lián)公司是專業(yè)的沅江網(wǎng)站建設公司,沅江接單;提供成都網(wǎng)站建設、網(wǎng)站建設,網(wǎng)頁設計,網(wǎng)站設計,建網(wǎng)站,PHP網(wǎng)站建設等專業(yè)做網(wǎng)站服務;采用PHP框架,可快速的進行沅江網(wǎng)站開發(fā)網(wǎng)頁制作和功能擴展;專業(yè)做搜索引擎喜愛的網(wǎng)站,專業(yè)的做網(wǎng)站團隊,希望更多企業(yè)前來合作!
我們進入該項目可以看到里面有這樣的一些內(nèi)容
按照官方的運行方式來運行這個項目
在瀏覽器中打開8080端口,可以看到該項目可以被成功運行了。
就是這樣一個簡單的demo。
然后我們?nèi)タ匆幌滤木唧w實現(xiàn)。
在這個項目中首先定義了一個hub的結(jié)構(gòu)體:
這個結(jié)構(gòu)體中,clients代表所有已經(jīng)注冊的用戶,broadcast管道會存儲客戶端發(fā)送來的信息。 register是一個*Client類型的管道,用于存儲新注冊的用戶,unregister管道反之。
我們打開main.go,main函數(shù)的源碼為:
在這里首先會新開一個goroutine,去跑hub的run方法,run方法中一個死循環(huán),不停地去輪詢hub中的內(nèi)容
如果取到了新用戶,就加入到clients中,如果取到了信息,就循環(huán)所有的client,將信息寫到client.send中。
我們看到在請求路徑為根的時候,它會請求一個函數(shù),而這個函數(shù)就是將home.html發(fā)送到客戶端。
而在請求路徑為“/ws”的時候,他會執(zhí)行一個serveWS的函數(shù)。
每當一個新的用戶進來之后,首先將連接升級為長連接,然后將當前的client寫到register中,由hub.run函數(shù)去做處理。然后開啟兩個goroutine,一個去讀client中發(fā)送來的數(shù)據(jù),一個將數(shù)據(jù)寫入到所有的client中,去發(fā)送給用戶。
這就是整個聊天室的實現(xiàn)原理。
上一節(jié)中,我們?yōu)槊總€連接都創(chuàng)建了一個goroutine來讀取其中的消息,現(xiàn)在我們將這個讀取消息的方法實現(xiàn)一下。
我們在application目錄下新建controllers目錄,并在其中創(chuàng)建一個MessageController.go文件。
首先我們新建一個MessageController的結(jié)構(gòu)體,內(nèi)容如下
這個結(jié)構(gòu)體包括兩個內(nèi)容,一個是我們將連接放在數(shù)組之后,返回的索引,另一個是連接本身.
這個是具體的方法。
我們首先設置了一下讀消息的大小、超時時間以及超時后需要的操作。
超時時間如果設置為0,那么就是永不超時。之前在這里直接寫0,被告知需要傳一個time.Time類型的數(shù)據(jù)。最終谷歌后才得到了這個值time.Time{}為"0001-01-01 00:00:00 +0000 UTC"。
我們將用戶手法消息的內(nèi)容定義為一個結(jié)構(gòu)體,然后將用戶的訂閱信息的json通過json.unmarshal轉(zhuǎn)換成這個結(jié)構(gòu)體。
之后的switch操作與我們在Swoole中的操作基本雷同,在查詢到login之后,調(diào)用service中 的login方法來進行注冊。
下一節(jié)中我們再介紹具體的注冊邏輯。
我們在mian函數(shù)中,首先初始化配置文件,然后新建http連接。
這個連接創(chuàng)建之后,監(jiān)聽服務器的9999端口。如果url的路徑后綴為 "/ws",就轉(zhuǎn)發(fā)到ws/ws.go中的IndexHandler方法中。
這個方法中首先我們創(chuàng)建一個websocket的Upgrader實例,然后我們使用Upgrader的upgrade方法來升級一下我們的連接為長連接。
升級完成之后會返回一個*websocket.Conn的連接,我們之后所有的關于連接的操作,都是基于該conn的。
在該連接完成之后,我們將連接存放到一個名為Client的map中,以便之后管理更為方便。
之后,我們啟動一個goroutine來讀取連接中發(fā)送的信息內(nèi)容,再根據(jù)內(nèi)容進行相應的操作。