У меня есть raspberry pi 3 с raspbian stretch в качестве операционной системы. Я установил и полностью настроил брокер MQTT на raspberry pi, следуя этому руководству: https://www.digitalocean.com/community/tutorials/how-to-install-and-secure-the-mosquitto-mqtt-messaging-broker-on-ubuntu-16-04 На стороне брокера все работает нормально. Сертификаты обновляются через 60 дней, и вы можете подключиться к порту 1883 только через localhost, а другие порты (8883 и 8083) открыты, но доступны только с использованием TLS версии 1.2, а для последнего также с использованием веб-сокетов. Ниже вы можете найти код моей конфигурации mosquitto (/etc/mosquitto/conf.d/default.conf).
allow_anonymous false
password_file /etc/mosquitto/passwd
listener 1883 localhost
listener 8883
certfile /etc/letsencrypt/live/home.kamidesigns.be/cert.pem
cafile /etc/letsencrypt/live/home.kamidesigns.be/chain.pem
keyfile /etc/letsencrypt/live/home.kamidesigns.be/privkey.pem
tls_version tlsv1.2
listener 8083
protocol websockets
certfile /etc/letsencrypt/live/home.kamidesigns.be/cert.pem
cafile /etc/letsencrypt/live/home.kamidesigns.be/chain.pem
keyfile /etc/letsencrypt/live/home.kamidesigns.be/privkey.pem
tls_version tlsv1.2
Я также купил ESP8266 Wemos D1 Mini для безопасного подключения к этому брокеру. Я использовал библиотеку pubsubclient по этой ссылке: https: //github.com/knolleary/pubsubclient для моего MQTT-клиента. Я использую главную ветку этой ссылки: https://github.com/esp8266/Arduino для моего безопасное соединение SSL. Ниже вы видите код, который я использовал для программирования своего Wemos D1 Mini.
#include <ESP8266WiFi.h>
#include <PubSubClient.h>
#include <time.h>
void callback(char* topic, byte* payload, unsigned int length) {
Serial.print("Message arrived [");
Serial.print(topic);
Serial.print("] ");
for (int i = 0; i < length; i++) {
Serial.print((char)payload[i]);
}
Serial.println();
}
const char* ssid = "ssid";
const char* password = "wifipassword";
const char* host = "home.kamidesigns.be";
const int port = 8883;
WiFiClientSecure espClient;
PubSubClient client(host, port, callback, espClient);
long lastMsg = 0;
char msg[50];
int value = 0;
void setup() {
Serial.begin(115200);
Serial.println();
Serial.print("connecting to ");
Serial.println(ssid);
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
delay(500);
Serial.print(".");
}
Serial.println("");
Serial.println("WiFi connected");
Serial.println("IP address: ");
Serial.println(WiFi.localIP());
// Synchronize time useing SNTP. This is necessary to verify that
// the TLS certificates offered by the server are currently valid.
Serial.print("Setting time using SNTP");
configTime(8 * 3600, 0, "pool.ntp.org", "time.nist.gov");
time_t now = time(nullptr);
while (now < 1000) {
delay(500);
Serial.print(".");
now = time(nullptr);
}
Serial.println("");
struct tm timeinfo;
gmtime_r(&now, &timeinfo);
Serial.print("Current time: ");
Serial.print(asctime(&timeinfo));
}
void reconnect() {
// Loop until we're reconnected
while (!client.connected()) {
Serial.print("Attempting MQTT connection...");
// Attempt to connect
if (client.connect("ESP8266LightController","username","password")) {
Serial.println("connected");
// Once connected, publish an announcement...
client.publish("outTopic", "hello world");
// ... and resubscribe
client.subscribe("inTopic");
} else {
Serial.print("failed, rc=");
Serial.print(client.state());
Serial.println(" try again in 5 seconds");
// Wait 5 seconds before retrying
delay(5000);
}
}
}
Когда я запускаю свой Wemos D1, серийный монитор говорит: подключение к ssid .. Подключенный IP-адрес WiFi: 192.168.0.213 Установка времени с помощью SNTP. Текущее время: 14 окт, суббота, 02:26:25 2017 Попытка подключения MQTT ... подключено
Это хорошо, и это именно то, что я хотел, но меня смущает, как мой Wemos D1 может подключаться к порту 8883 без проверки цепочки сертификатов сервера? Помните, что я никогда не загружал сертификат в Wemos D1 и не внедрял сертификат в код, но он все равно может подключиться.