Debian8にMosquittoMQTTメッセージングブローカーをインストールして保護する方法
序章
MQTT は、マシンツーマシンメッセージングプロトコルであり、「モノのインターネット」デバイスへの軽量のパブリッシュ/サブスクライブ通信を提供するように設計されています。 これは一般的に、車両の地理追跡、ホームオートメーション、環境センサーネットワーク、およびユーティリティ規模のデータ収集に使用されます。
Mosquitto は人気のあるMQTTサーバー(またはMQTT用語ではブローカー)であり、優れたコミュニティサポートを備えており、インストールと構成が簡単です。
このチュートリアルでは、Mosquittoをインストールし、Let’s EncryptからSSL証明書を取得し、SSLを使用してパスワードで保護されたMQTT通信を保護するようにブローカーを設定します。
前提条件
このチュートリアルを開始する前に、次のものが必要です。
- このDebian8サーバーセットアップチュートリアルで詳しく説明されている、root以外のsudo対応ユーザーを持つDebian8サーバー。
- で設定された基本的なファイアウォール
ufw
、 Ubuntu14.04でUFWを使用してファイアウォールを設定する方法で説明されています。 Ubuntu中心のタイトルにもかかわらず、Debianでフォローすることができます。sudo apt-get install ufw
まず、Debianには含まれていないためufw
デフォルトでは。 - DigitalOcean を使用してホスト名を設定する方法に従って、サーバーを指すドメイン名。 このチュートリアルでは、
mqtt.example.com
全体を通して。
ステップ1—Mosquittoのインストール
Debianの mosquitto
パッケージは必要な機能の一部をサポートしていないため、Mosquittoプロジェクトが提供する最新のリポジトリからインストールします。 まず、リポジトリ署名キーをダウンロードします。
- wget http://repo.mosquitto.org/debian/mosquitto-repo.gpg.key
次に、キーをインストールします apt-key
.
- sudo apt-key add mosquitto-repo.gpg.key
これにより、 apt-get
新しいリポジトリからインストールするソフトウェアの整合性を検証します。
今教えて apt-get
リポジトリのURLをファイルに追加してソフトウェアを見つける場所 /etc/apt/sources.list.d/
.
- sudo nano /etc/apt/sources.list.d/mosquitto.list
これにより、新しい空白のファイルが開きます。 次の行をファイルに貼り付けます。
deb http://repo.mosquitto.org/debian jessie main
保存してエディターを閉じてから、で更新します apt-get
新しいパッケージ情報を取得します。
- sudo apt-get update
そして最後に、 mosquitto
パッケージとそのクライアントソフトウェア。
- sudo apt-get install mosquitto mosquitto-clients
デフォルトでは、Debianはインストール後にMosquittoサービスを開始します。 デフォルト設定をテストしてみましょう。 インストールしたばかりのクライアントの1つを使用して、ブローカーのトピックをサブスクライブします。
トピックは、メッセージを公開およびサブスクライブするラベルです。 それらは階層として配置されているので、 sensors/outside/temp
と sensors/outside/humidity
、 例えば。 トピックをどのように配置するかは、あなたとあなたのニーズ次第です。 このチュートリアル全体を通して、簡単なテストトピックを使用して構成の変更をテストします。
サーバーにもう一度ログインすると、2つの端末が並んでいます。 新しいターミナルでは、 mosquitto_sub
テストトピックを購読するには:
- mosquitto_sub -h localhost -t test
The -h
flagは、MQTTサーバーのホスト名を指定します。 -t
トピック名です。 押した後、出力は表示されません ENTER
なぜなら mosquitto_sub
メッセージが到着するのを待っています。 他の端末に戻り、メッセージを公開します。
- mosquitto_pub -h localhost -t test -m "hello world"
のオプション mosquitto_pub
と同じです mosquitto_sub
、今回は追加のを使用しますが -m
メッセージを指定するオプション。 打つ ENTER
、他の端末に helloworldがポップアップ表示されるはずです。 最初のMQTTメッセージを送信しました。
プレス CTRL+C
2番目のターミナルで終了します mosquitto_sub
、ただし、サーバーへの接続は開いたままにします。 ステップ5の別のテストに再び使用します。
次に、新しいLet’sEncryptクライアントであるCertbot を使用して、SSLでインストールを保護します。
ステップ2—Let’sEncrypt証明書用のCertbotのインストール
Let’s Encryptは、自動化されたAPIを介して無料のSSL証明書を提供する新しいサービスです。 APIと通信できるクライアントはたくさんあり、Debianはデフォルトのリポジトリに公式クライアントを含めていますが、少し古く、必要な重要な機能が1つ欠けています。
代わりに、Debianからクライアントをインストールします backports
リポジトリ。 これは、一部のソフトウェアの新しいバージョンを、すでにリリースされているバージョンのDebianで利用できるようにする公式リポジトリです。 前の手順で行ったように、リポジトリをAPTソースリストに追加する必要があります。
まず、で新しいファイルを開きます /etc/apt/sources.list.d/
.
- sudo nano /etc/apt/sources.list.d/backports.list
次の行をファイルに貼り付けます。
deb http://mirrors.digitalocean.com/debian jessie-backports main
ファイルを保存し、エディターを閉じます。 その後、パッケージ情報を更新します。
- sudo apt-get update
そして最後に、Certbotと呼ばれる公式のLet’s Encryptクライアントをインストールし、APTに使用するように指示します。 jessie-backports
そのソースとして:
- sudo apt-get install certbot -t jessie-backports
Certbotがインストールされたので、それを実行して証明書を取得しましょう。
ステップ3—Certbotを実行する
Certbotは、ドメインを制御していることを証明するために、Let’sEncryptAPIによって発行された暗号化の課題に答える必要があります。 ポートを使用します 80
(HTTP)および/または 443
(HTTPS)これを実現します。 ポートのみを使用します 80
、そのため、そのポートでの着信トラフィックを許可します。
- sudo ufw allow http
OutputRule added
Rule added (v6)
これで、Certbotを実行して証明書を取得できます。 を使用します --standalone
CertbotにHTTPチャレンジリクエストを独自に処理するように指示するオプション、および --standalone-supported-challenges http-01
ポートへの通信を制限します 80
. -d
証明書が必要なドメインを指定し、 certonly
他の構成手順を実行せずに証明書を取得するようにCertbotに指示します。
- sudo certbot certonly --standalone --standalone-supported-challenges http-01 -d mqtt.example.com
コマンドを実行すると、電子メールアドレスを入力し、利用規約に同意するように求められます。 そうすると、プロセスが成功したことと、証明書が保存されている場所を示すメッセージが表示されます。
証明書を持っています。 次に、Certbotが期限切れになりそうになったときに自動的に更新するようにする必要があります。
ステップ4—Certbot自動更新の設定
Let’s Encryptの証明書は、90日間のみ有効です。 これは、ユーザーが証明書の更新プロセスを自動化することを奨励するためです。 期限切れの証明書を定期的にチェックして自動的に更新するコマンドを設定する必要があります。
更新チェックを毎日実行するには、定期的なジョブを実行するための標準システムサービスであるcronを使用します。 教えて cron
と呼ばれるファイルを開いて編集することによって何をすべきか crontab
.
- sudo crontab -e
テキストエディタを選択するように求められます。 お気に入りを選択すると、デフォルトが表示されます crontab
ヘルプテキストが含まれています。 ファイルの最後に次の行を貼り付けて、保存して閉じます。
. . .
15 3 * * * certbot renew --noninteractive --post-hook "systemctl restart mosquitto"
The 15 3 * * *
この行の一部は、「毎日午前3時15分に次のコマンドを実行する」ことを意味します。 The renew
Certbotのコマンドは、システムにインストールされているすべての証明書をチェックし、30日以内に期限切れになるように設定されている証明書を更新します。 --noninteractive
ユーザー入力を待たないようにCertbotに指示します。
--post-hook "systemctl restart mosquitto"
Mosquittoを再起動して新しい証明書を取得しますが、証明書が更新された場合に限ります。 これ post-hook
機能は、Let’s Encryptクライアントの古いバージョンに欠けていたものであり、デフォルトのDebianリポジトリではなくバックポートからインストールした理由です。 これがないと、実際に証明書が更新されていなくても、毎日Mosquittoを再起動する必要があります。 MQTTクライアントは自動的に再接続するように構成する必要がありますが、正当な理由がない限り、毎日中断しないようにすることをお勧めします。
証明書の自動更新がすべて設定されたので、Mosquittoのより安全な構成に戻ります。
ステップ5—MQTTパスワードの設定
メッセージを公開できるユーザーを制御できるように、パスワードを使用するようにMosquittoを構成しましょう。 Mosquittoには、と呼ばれる特別なパスワードファイルを生成するユーティリティが含まれています mosquitto_passwd
. このコマンドは、指定されたユーザー名のパスワードを入力するように求め、結果を /etc/mosquitto/passwd
.
- sudo mosquitto_passwd -c /etc/mosquitto/passwd sammy
次に、Mosquittoの新しい構成ファイルを作成し、このパスワードファイルを使用してすべての接続にログインを要求するように指示します。
- sudo nano /etc/mosquitto/conf.d/default.conf
これにより、空のファイルが開きます。 次のように貼り付けます。
allow_anonymous false
password_file /etc/mosquitto/passwd
allow_anonymous false
認証されていないすべての接続を無効にし、 password_file
行は、ユーザーとパスワードの情報を探す場所をMosquittoに指示します。 ファイルを保存して終了します。
次に、Mosquittoを再起動して、変更をテストする必要があります。
- sudo systemctl restart mosquitto
まず、パスワードなしでメッセージを公開してみてください。
- mosquitto_pub -h localhost -t "test" -m "hello world"
メッセージは拒否する必要があります:
OutputConnection Refused: not authorised.
Error: The connection was refused.
パスワードで再試行する前に、2番目のターミナルウィンドウに再度切り替えて、今回はユーザー名とパスワードを使用してtestトピックにサブスクライブします。
- mosquitto_sub -h localhost -t test -u "sammy" -P "password"
接続して座って、メッセージを待つ必要があります。 テストメッセージを定期的に送信するため、チュートリアルの残りの部分では、この端末を開いたまま接続したままにしておくことができます。
次に、ユーザー名とパスワードを使用して、他の端末でメッセージを公開します。
- mosquitto_pub -h localhost -t "test" -m "hello world" -u "sammy" -P "password"
メッセージはステップ1のように通過するはずです。 Mosquittoにパスワード保護を追加しました。 残念ながら、インターネットを介して暗号化されていないパスワードを送信しています。 次に、SSL暗号化をMosquittoに追加して修正します。
ステップ6—MQTTSSLの構成
SSL暗号化を有効にするには、Let’sEncrypt証明書が保存されている場所をMosquittoに通知する必要があります。 以前に開始した構成ファイルを開きます。
- sudo nano /etc/mosquitto/conf.d/default.conf
ファイルの最後に次のように貼り付けて、すでに追加した2行を残します。
. . .
listener 1883 localhost
listener 8883
certfile /etc/letsencrypt/live/mqtt.example.com/cert.pem
cafile /etc/letsencrypt/live/mqtt.example.com/chain.pem
keyfile /etc/letsencrypt/live/mqtt.example.com/privkey.pem
2つ別々に追加します listener
構成へのブロック。 最初、 listener 1883 localhost
、ポートのデフォルトのMQTTリスナーを更新します 1883
、これまで接続してきたものです。 1883
標準の暗号化されていないMQTTポートです。 The localhost
行の一部は、このポートをローカルホストインターフェイスにのみバインドするようにMosquittoに指示しているため、外部からアクセスすることはできません。 とにかく外部リクエストはファイアウォールによってブロックされていたでしょうが、明示的にするのは良いことです。
listener 8883
ポートに暗号化されたリスナーを設定します 8883
. これはMQTT+SSLの標準ポートであり、MQTTSと呼ばれることもあります。 次の3行、 certfile
, cafile
、 と keyfile
、すべてMosquittoが適切なLet’s Encryptファイルをポイントして、暗号化された接続を設定します。
ファイルを保存して終了し、Mosquittoを再起動して設定を更新します。
- sudo systemctl restart mosquitto
ポートへの接続を許可するようにファイアウォールを更新します 8883
.
- sudo ufw allow 8883
OutputRule added
Rule added (v6)
次に、を使用して再度テストします mosquitto_pub
、SSLのいくつかの異なるオプション:
- mosquitto_pub -h mqtt.example.com -t test -m "hello again" -p 8883 --capath /etc/ssl/certs/ -u "sammy" -P "password"
代わりに完全なホスト名を使用していることに注意してください localhost
. SSL証明書が発行されているため mqtt.example.com
、への安全な接続を試みる場合 localhost
ホスト名が証明書のホスト名と一致しないというエラーが表示されます(両方が同じMosquittoサーバーを指している場合でも)。
--capath /etc/ssl/certs/
のSSLを有効にします mosquitto_pub
、およびルート証明書を探す場所を指示します。 これらは通常、オペレーティングシステムによってインストールされるため、macOS、Windowsなどではパスが異なります。 mosquitto_pub
ルート証明書を使用して、Mosquittoサーバーの証明書がLet’sEncrypt認証局によって適切に署名されていることを確認します。 注意することが重要です mosquitto_pub
と mosquitto_sub
このオプション(または同様のオプション)がないとSSL接続を試行しません --cafile
オプション)、標準の安全なポートに接続している場合でも 8883
.
すべてがテストに問題がなければ、こんにちはがもう一方に表示されます。 mosquitto_sub
ターミナル。 これは、サーバーが完全にセットアップされていることを意味します。 MQTTプロトコルを拡張してWebSocketで動作するようにする場合は、最後の手順に従うことができます。
ステップ7— Websocketを介したMQTTの構成(オプション)
Webブラウザ内からJavaScriptを使用してMQTTを話すために、プロトコルは標準のWebSocketで機能するように調整されました。 この機能が必要ない場合は、この手順をスキップできます。
もう1つ追加する必要があります listener
Mosqiutto構成にブロックします。
- sudo nano /etc/mosquitto/conf.d/default.conf
ファイルの最後に、以下を追加します。
. . .
listener 8083
protocol websockets
certfile /etc/letsencrypt/live/mqtt.example.com/cert.pem
cafile /etc/letsencrypt/live/mqtt.example.com/chain.pem
keyfile /etc/letsencrypt/live/mqtt.example.com/privkey.pem
これは、ポート番号と protocol websockets
ライン。 WebSocketを介したMQTTの公式の標準化されたポートはありませんが、 8083
最も一般的です。
ファイルを保存して終了し、Mosquittoを再起動します。
- sudo systemctl restart mosquitto
今、ポートを開きます 8083
ファイアウォールで。
- sudo ufw allow 8083
この機能をテストするために、パブリックなブラウザーベースのMQTTクライアントを使用します。 そこにはいくつかありますが、mqtt-adminはシンプルで簡単です。 ブラウザでmqtt-adminを開きます。 次のように表示されます。
次のように接続情報を入力します。
- プロトコルはwss( w eb s ocket s ecureの略)である必要があります。
- Host は、Mosquittoサーバーのドメインである必要があります。
mqtt.example.com
. - ポートは
8083
. - UserはMosquittoのユーザー名である必要があります。 ここでは、sammyを使用しました。
- Password は、選択したパスワードである必要があります。
- ClientIdはデフォルト値のmqtt-adminのままにしておくことができます。
設定の保存を押した後、 mqtt-admin
Mosquittoサーバーに接続します。 次の画面で、トピックにテストと入力し、ペイロードのメッセージを入力して、公開を押します。 メッセージはに表示されます mosquitto_sub
ターミナル。
結論
Let’s EncryptサービスからのSSL証明書を自動更新することで、パスワードで保護された安全なMQTTサーバーをセットアップしました。 これは、あなたが夢見ているどんなプロジェクトに対しても、堅牢で安全なメッセージングプラットフォームとして機能します。 MQTTプロトコルでうまく機能する一般的なソフトウェアとハードウェアには次のものがあります。
- OwnTracks 、携帯電話にインストールできるオープンソースの地理追跡アプリ。 OwnTracksは定期的に位置情報をMQTTサーバーに報告します。これを保存して地図に表示したり、アラートを作成して場所に基づいてIoTハードウェアをアクティブ化したりできます。
- Node-RED は、モノのインターネットを「一緒に配線」するためのブラウザベースのグラフィカルインターフェイスです。 あるノードの出力を別のノードの入力にドラッグすると、フィルターを介して、さまざまなプロトコル間で、データベースなどに情報をルーティングできます。 MQTTはNode-REDによって非常によくサポートされています。
- ESP8266 は、MQTT機能を備えた安価なwifiマイクロコントローラーです。 温度データをトピックに公開するために1つを接続するか、気圧トピックをサブスクライブして、嵐が来たときにブザーを鳴らすことができます。
これらは、MQTTエコシステムからのいくつかの人気のある例です。 プロトコルを話すハードウェアとソフトウェアはもっとたくさんあります。 お気に入りのハードウェアプラットフォームまたはソフトウェア言語がすでにある場合は、おそらくMQTT機能があります。 あなたの「もの」がお互いに話し合うのを楽しんでください!