前幾天朋友讓我幫忙部署一個mqtt服務器,要支持ssl加密的。初步了解了下mqtt協議是啥,然后選擇了mosquitto搭建mqtt服務器。mqtt協議我就不多介紹了,百度谷歌一下一大堆資料。mosquitto說白了就是mqtt協議的一個服務端實現。
廢話不多說,下面直接上我搭建的過程:
一、 安裝mosquitto 支持mqtt+ws
操作系統:linux。本人用的是centos7。不過centos6.5也試過,也ok。
1. 基礎庫安裝
yum install gcc-c++
yum install cmake
yum install openssl-devel //mosquitto默認支持openssl
官網下載mosquitto
wget http://mosquitto.org/files/source/mosquitto-1.4.4.tar.gz
tar -xzvf mosquitto-1.4.4.tar.gz
cd mosquitto-1.4.4
修改編譯選項
vim config.mk
因為我們需要websocket支持,所以找到WITH_WEBSOCKETS將值設置為yes
4. 別不急着編譯mosquitto,先安裝c-ares
wget http://c-ares.haxx.se/download/c-ares-1.10.0.tar.gz
tar xvf c-ares-1.10.0.tar.gz
cd c-ares-1.10.0
./configure
make
make install
接着安裝lib-uuid
yum install libuuid-devel
安裝libwebcoket
wget https://github.com/warmcat/libwebsockets/archive/v1.3-chrome37-firefox30.tar.gz
tar zxvf v1.3-chrome37-firefox30.tar.gz
cd libwebsockets-1.3-chrome37-firefox30
mkdir build; cd build;
cmake .. -DLIB_SUFFIX=64
make install
最后開始編譯安裝mosquitto
make
make install
最后程序會安裝在 /etc/mosquitto 下面。
8. 添加鏈接庫路徑
由於操作系統版本及架構原因,很容易出現安裝之后的鏈接庫無法被找到,如啟動mosquitto客戶端可能出現找不到
libmosquitto.so.1文件,因此需要添加鏈接庫路徑
//添加路徑
vim /etc/ld.so.conf.d/liblocal.conf
/usr/local/lib64
/usr/local/lib
//刷新
ldconfig
復制配置文件和添加用戶
先添加配置文件
mv /etc/mosquitto/mosquitto.conf.example /etc/mosquitto/mosquitto.conf
mosquitto默認以mosquitto用戶啟動,可以通過配置文件修改啟動用戶為root。
vim /etc/mosquitto/mosquitto.conf
user root
或者 也可以添加mosquitto 用戶啟動程序
groupadd mosquitto
useradd -g mosquitto mosquitto
接下來要開啟websocket支持,我們需要修改配置文件
vim /etc/mosquitto/mosquitto.conf
去掉port注釋,並添加以下內容
port 1883
listener 8080
protocol websockets
接着啟動mosquitto
mosquitto -c /etc/mosquitto/mosquitto.conf -d
這樣,我們就同時開啟了1883端口支持mqtt協議,8080端口支持websocket了。
11. 測試
- mqtt服務讀者可以自行編寫代碼測試連通性。同時mosquitto 提供了 mosquitto_sub 和 mosquitto_pub 測試mqtt服務。
- websocket 也可以編寫js代碼測試。或者去該網站測試 http://www.tongxinmao.com/txm/webmqtt.php
二、加上ssl協議
首先需要去簽一個可信任的證書。目前騰訊雲和阿里雲都提供了免費證書申請。mosquitto配置ssl需要用到3個文件。
root.crt (根證書)
server.crt (我們自己的公鑰根據根證書簽的證書)
server.key (密鑰)
獲得這3個文件后,我們就可以配置mosquitto的ssl了。以下貼出主要的配置
vim /etc/mosquitto/mosquitto.conf
port 1883
listener 8883
cafile /home/yangjb/apache/1_root_bundle.crt
certfile /home/yangjb/apache/2_www.qilv.group.crt
keyfile /home/yangjb/apache/3_www.qilv.group.key
listener 8080
protocol websockets
listener 8081
protocol websockets
cafile /home/yangjb/apache/1_root_bundle.crt
certfile /home/yangjb/apache/2_www.qilv.group.crt
keyfile /home/yangjb/apache/3_www.qilv.group.key
配完重啟mosquitto服務器就生效了
- mqtt 協議走 1883端口
- mqtt+ssl 走8883端口
- websocket 協議走 8080端口
- websocket+ssl 走8081端口
三、 通過 nginx轉發websockt
我這邊測試都通過了,但是朋友的小程序一直連不上websocket。(ws+wss都連不上)
用微信自帶的websocket庫連接是可以的。但是他用的是Patho.Client庫連接,就是死活連不上。
后來網上找了半天,發現一篇文章。說禁用Sec-WebSocket-Protocol頭就可以了。然后我配了下nginx,轉發請求的時候去掉Sec-WebSocket-Protocol頭,竟然真的可以了。也不知道什么原理- -。下面附上部分主要的配置
location /mqtt {
proxy_pass http://127.0.0.1:8080;
proxy_set_header Sec-WebSocket-Protocol mqtt;
# 這行就是去除 Sec-WebSocket-Protocol
more_clear_headers Sec-WebSocket-Protocol;
proxy_http_version 1.1;
proxy_set_header Upgrade websocket;
proxy_set_header Connection "upgrade";
proxy_set_header X-real-ip $remote_addr;
proxy_set_header X-Forwarded-For $remote_addr;
}
上面的配置有個問題,就是我們正常的websockt反而連不上了。然后注解more_clear_headers Sec-WebSocket-Protocol;這行又連上了。但是同時朋友的小程序那邊又連不上了。。。
具體原因現在也沒搞明白,想來可能和那個js庫有關系。
版權聲明:本文為CSDN博主「瘋狂哈丘」的原創文章,遵循CC 4.0 BY-SA版權協議,轉載請附上原文出處鏈接及本聲明。
原文鏈接:https://blog.csdn.net/u013332124/article/details/79480639