一步一步教你用WebSocket進行消息推送(iOS版本)

? 寫作原因:公司這個月的項目計劃是優化推送;目前我們推送用的個推(不是不好,項目限制),然后服務器那邊人員忙(本人菜雞iOS程序員),所以我就自己來做咯,如果有錯誤的地方下面留言我們一起交流哈,要源碼的記得回復留下地址哦

? 大家都知道用APNS(個推那些都是基于這個的)只能推送一些不重要的消息(比如公告,推薦你買啥啥啥),但是我們項目有加圈子/發任務/會議等等非常重要的操作,這種是不能用APNS來做的,那么我們應該用什么呢?我們應該用聊天那種來推送;當然說起聊天我們技術就多了,你可以使用最裸奔的socket(https://github.com/robbiehanson/CocoaAsyncSocket)自己做協議,也可以使用封裝了一下的websocket(https://github.com/facebook/SocketRocket)等等,甚至封裝更深的socket.io(https://github.com/pkyeck/socket.IO-objc)等等;當然你也知道答案了,websocket最適合來做推送。我們先來看看最終效果吧,如果你覺得感興趣,可以繼續往下看:

我們在我們的服務器上輸入一個內容,點擊按鈕
模擬器上就會收到消息

? 那么現在開始說下準備工作,1:你要會點H5,2:你要知道websocket是啥東西,3:你要有一個heroku賬號(有免費的nodejs環境服務器),4:你要會點終端(包括解決神秘代碼和常用命令);好的現在解釋下為什么要用nodejs來做服務器,因為他天生就適合websocket;那么為什么要用heroku呢,因為我之前用新浪云,新浪云也有nodejs環境,但是要收費(土豪忽略),于是找了一個大家都拍手稱快的heroku;那么我們開始做咯。

第一步:本地先弄個簡單的websocket服務器

我們使用npm管理器來創建,首先自己在盡量沒有中文路徑的地方創建一個文件夾(名字就叫做hellowebsocket),然后我們用終端進入文件夾:

進入文件夾

創建一個基礎項目:

創建基礎項目

創建一個server.js(websocket服務器文件):

創建服務器文件

配置package.json文件,覆蓋或者修改成這樣:

修改配置文件

其中的scripts我們定義一個start為node server.js操作,也就是說你輸入npm start相當于是執行node server.js,

我們來安裝一些工具,express(用來搭建http協議的網頁,我們不是要做一個網頁嗎?這個網頁是http協議的,我們肯定要搭建咯),ws(websocket的node封裝),在命令行依次輸入以下命令:1:npm install --save --save-exact express,2:npm install --save --save-exact ws bufferutil utf-8-validate,

我們來創建一個網頁,取名index.html,內容先簡單點,點擊按鈕顯示輸入框的內容,還沒有連接websocket服務器(server.js,以后不再注釋):

彈出文本框內容

現在我們來編輯weboscket服務器咯,先簡單點,搭建一個http協議讓index.html可以本地瀏覽器輸入localhost:3000/index.html訪問,還沒有創建websocket監聽,等一下來:

搭建http環境

然后在終端中輸入npm start,這時候你在瀏覽器中輸入localhost:3000/index.html,就可以看到下面的效果了:

HTTP搭建好了

接下面我們修改一下index.html和server.js,讓index.html連接websocket服務器,weboscket服務器收到連接后發送回調消息"device your connect!",然后index.html收到回調消息后彈窗,內容如下:

server.js內容
index.html內容

這時候我們終端輸入npm start,瀏覽器中輸入localhost:3000/index.html就會彈出來回調消息了:

頁面彈出連接成功的回調消息

通過以上的幾步,大家應該大致知道推送原理了把,就是通過websocket連接得到的標示符進行發送消息和接收消息

第二步:網頁輸入內容點擊按鈕,websocket服務器響應并回調相同的內容,網頁收到后彈窗

?通過第一步,大家可以暫定自己想一下這個怎么做,是這樣的:我們index.html連接成功后我們通過標識符發送消息到websocket服務器,websocket服務器收到后得到內容并發送到index.html就可以了;那么同樣的,我們修改一下內容:

server.js內容
index.html內容

同樣的,執行npm start,瀏覽器中輸入localhost:3000/index.html,然后輸入框輸入內容點擊按鈕就可以看到效果了:

效果圖

現在我們越來越得心應手了,發現這么簡單啊(好吧,下一篇我們才要開始做我們真正的目的呢,高興啥)

第三步:我們用iOS連接websocket服務器把發送的和收到的消息展示到表格視圖

經過以上的兩步,我們終于揭開了神秘的websocket服務器面紗,我們決定要是一步一步實現iOS應用的推送,廢話不對說,我們新建一個iOS工程并導入SRWebSocket庫(這里沒有教程,自己弄),然后寫一個表格視圖和數組,我們把發送消息和接收消息存到數組中用表格視圖展示出來,重點代碼如下:

連接websocket服務器

發送消息

接收消息

發送心跳,頻率可設

還是不要忘記了,我們執行npm start,然后我們用模擬器打開點擊右上角的“+”號發送消息就能看到以下的效果了:

效果圖

好的,離目標又近了,現在我們來點有意思的

第四步:iOS端和index.html都連接到websocket服務器,index.html點擊按鈕發送輸入內容到websocket服務器,web socket服務器發送消息到iOS端,iOS端收到消息并顯示到表格視圖

大家應該猜到怎么做了,主要難點是遍歷所有的websocket連接,依次發送消息,我們暫時去掉index.html收到消息彈窗的代碼,iOS端代碼不用修改,主要內容如下:

index.html

server.js

然后依然,執行nam start,iOS啟動模擬器,然后瀏覽器中輸入localhost:3000/index.html,輸入內容點擊按鈕,我們就可以看到下面的效果:

發送消息

模擬器收到消息

大家發現是不是和我們的最終效果有點像呢?其實還差得遠呢,我們下一篇開始好好寫一下細節部分

第五步:我們讓每個連接的websocket有一個對應的標識符,以便單獨的向某一個人發送消息

細心的小伙伴發現了,我們用index.html連接websocket服務器時后面帶了一個userId參數,好吧暴露了其實我們連接的時候url后面是可以加參數的,我們暫且就先用這個來和websocket連接做一個映射吧,我們這一步不使用index.html,我們用iOS端連接并帶上參數userId,然后在終端打印出來userId參數的值;有人問了,userId我在iOS請求時加上,那么在websocket服務器那邊怎么收到呢?這個問題問的很好,我們來做一下實驗,首先我們先改造一下iOS連接的代碼,如下:

iOS連接websocket帶上參數

然后我們在websocket服務器收到連接后把socket連接打印出來,代碼如下:

websocket打印連接實例

依然,npm start,iOS端啟動,這時候終端會輸出一大片東西(這就是實例咯),然后你會在中間位置看到這樣的東西:

參數位置

沒錯,我們就是要取出來這個東西,然后和websocket綁定,我們先在weboscket服務器文件上建立一個字典,然后連接的地方取出userId然后dic[userId]=websocket就可以了,為了看到效果,我們就把userId打印到終端顯示吧,代碼如下:

server.js內容

老話題,npm start,然后啟動iOS端,就會終端打印出來了:

效果圖

轉入正題,我們既然都知道誰的連接是哪個了,那么我們接下來要做的就是在websocket服務器中接收消息(我們用index.html發消息,充當"業務服務器");然后websocket服務器判斷消息是要發給誰的,然后在字典中找到那個socket連接,調用send函數即可(當然還有其他很多的方法,可能我這個不標準),我們修改server.js為以下代碼:

給指定的userid發消息

然后我們修改一下index.html文件,給指定的userId為10001的人發送消息,消息格式在websocket服務器中定義好了,所有我們index.html給websocet發消息時要遵從消息格式加上分隔符"^"等,代碼如下:

讓web socket服務器給userId=10001的人發消息

我們讓iOS端的userId設置成10001,然后npm start,瀏覽器中輸入localhost:3000/index.html,啟動模擬器,瀏覽器中輸入內容點擊按鈕,這時候會看到如下效果:

發送消息

iOSuserId=10001的用戶收到消息

當然了,你可以多建幾個工程,設置連接不同的userId,然后 index.html也可以設置不限userId和限制多個userId發消息,你可以多測試一下效果。那么接下來的系列我們將把本地服務器部署到heroku上成為全局的,然后各地的個小伙伴都可以訪問到了,你可以先自己折騰下,我先給個網址給你們https://devcenter.heroku.com/articles/node-websockets

第六步:把websocket服務器部署到heroku服務器變為全局訪問

有的人有個好東西就想分(xuan)享(yao)(就是我),其實websocket服務器成為全局訪問后,你發你女朋友這個網址(前面的index.html文件),讓她在里面里輸東西,點一下按鈕;你就能施展"神通"知道她寫的是什么,是不是很完(zhuang)美(bi)呢?那么現在就開始吧。上一步我最后留了一個網址,里面的內容是不是還是看不懂啊(反正我最開始沒看懂,不然不會折騰這么幾天),那么用我的方式來講講吧。

首先,你要有個heroku的賬號,然后安裝heroku-toolbelt.pkg工具(我們假設完全終端里操作,不在heroku官網操作),地址在這里https://devcenter.heroku.com/articles/heroku-command-line,然后安裝,然后終端進入我們的目錄中(一直都是hellowebsocket文件夾哦),執行heroku login(輸入密碼時是沒有回顯的),然后初始化一個git工程,執行git init,創建一個heroku項目,執行heroku create hellowebsocket(后面的名字自己看著辦,如果有錯誤回提示你的,重新想一個就是了)然后你會看到兩個地址(前面的就是你的全局地址咯,現在還訪問不了,慢慢來,后面的是你的git地址),這時候我們執行git remote add hellowebsocket https://git.heroku.com/hellowebsocket.git(第5個參數是你的git地址,用你自己的),

其次,還有重要的東西,還記得我們之前安裝了一些工具類嗎?就是node_modules文件夾里面的東西,這些東西不用提交到git項目上去,所以我們建立一個.gitignore文件忽略掉,里面就寫上node_modules就可以了;還有,我們本地服務器可以npm start執行nodejs環境,那heroku怎么去執行呢?我們應該建立一個Procfile文件,里面寫上web: node server.js,這樣目錄里面就有這些內容了:

hellowebsocket目錄

好了,現在可以提交了,git add .,git commit -m 'init',git push hellowebsocket master,然后等待部署吧,你會看到如下的信息表示成功部署:

部署成功

部署成功后heroku那邊會自動啟動nodejs環境服務器(相當于我們本地的npm start),然后我們在瀏覽器中輸入上圖黑色箭頭的地址就會看到如下結果:

地址可全局訪問了

第七步:實現最終效果,目標達成

把我們的iOS端的websocket連接地址換掉,代碼如下:

iOS連接全局 websocket服務器

然后我們啟動iOS端,瀏覽器中輸入地址hellowebsocket.herokuapp.com/index.html,文本框中輸入內容,iOS端就會顯示了,效果如下:

輸入推送內容

iOS收到推送消息

好了,這里面還有一個小問題留給你們,我們那個html文件沒有發送心跳哦,你們去加上,還有就是可以設置心跳的頻率,你們也可以研究研究;當然了,推送不僅僅是這樣,我們的業務服務器(目前來說我們的index.html有點像)要考慮用戶不在線的情況要把消息存起來同時發個APNS提醒用戶,然后等用戶上線后再取出消息發送出去,這部分的話我沒有實現,交給你們啦;還有就是業務服務器和websocket服務器分工要明確,目前我的可能都是錯誤的(因為我的判斷邏輯在websocket服務器,websocket服務器應該只負責發送,邏輯應該寫在業務服務器),慢慢學習吧!

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 230,321評論 6 543
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 99,559評論 3 429
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 178,442評論 0 383
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,835評論 1 317
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 72,581評論 6 412
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 55,922評論 1 328
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,931評論 3 447
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 43,096評論 0 290
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 49,639評論 1 336
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 41,374評論 3 358
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 43,591評論 1 374
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 39,104評論 5 364
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,789評論 3 349
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 35,196評論 0 28
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 36,524評論 1 295
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 52,322評論 3 400
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 48,554評論 2 379

推薦閱讀更多精彩內容

  • WebSocket-Swift Starscream的使用 WebSocket 是 HTML5 一種新的協議。它實...
    香橙柚子閱讀 24,022評論 8 183
  • 發現 關注 消息 iOS 第三方庫、插件、知名博客總結 作者大灰狼的小綿羊哥哥關注 2017.06.26 09:4...
    肇東周閱讀 12,173評論 4 61
  • Dear:剛醒來,睜眼之初意識到今天是2017年的第一天,我心里泛起喜悅,“dear,happy new year...
    田心遠閱讀 184評論 9 3
  • 今天羅胖在得到的直播里,請到了一個人。此前他也提到過,說他練三個月書法就出字帖了,分別練三個月吉他、鋼琴,就出教程...
    薛定餓著貓閱讀 179評論 0 0
  • 在一切宣布結束,在事情真的無能為力之時,到底要怎樣,才會讓自己的心有一絲絲寬慰? 我不想說什么,真的有一種哽咽。或...
    公皙瓊羽閱讀 154評論 0 0