ESP8266 не может подключиться к брокеру MQTT

Я использую плату разработки NodeMCU с ESP8266 WIFI.

Каждый раз, когда я пытаюсь подключиться к своему локальному брокеру, он возвращает эту ошибку:

failed, rc=-2 try again in 5 seconds

Я использую Ubuntu 18.04, мои локальные брокеры — Mosquitto и EQMTT. Я попробовал оба через библиотеку pubsubclient, но они не подключаются. Использование MQTT Box работает при подключении к моим локальным брокерам. Подключение к моему WiFi тоже работает. Когда я подключаюсь к брокеру MQTT с помощью pubsubclient, например mqtt://test.mosquitto.org:1883/, все работает. Похоже, что он просто не работает с локальным брокером. Вот код:

#include <ESP8266WiFi.h>
#include <PubSubClient.h>

// Обновите их значениями, подходящими для вашей сети.

const char* ssid = "mywifi";
const char* password = "password";
const char* mqtt_server = "127.0.0.1";

WiFiClient espClient;
PubSubClient client(espClient);
long lastMsg = 0;
char msg[50];
int value = 0;

void setup() {
  pinMode(D7, OUTPUT);     // Инициализируем вывод BUILTIN_LED как выход
  Serial.begin(9600);
  setup_wifi();
  client.setServer(mqtt_server, 1883);
  client.setCallback(callback);
}

void setup_wifi() {

  delay(10);
  // Начнем с подключения к сети WiFi
  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());
}

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();

  // Включить светодиод, если в качестве первого символа получена 1
  if ((char)payload[0] == '1') {
    digitalWrite(D7, LOW);   // Включаем светодиод (обратите внимание, что LOW — это уровень напряжения
    // но на самом деле светодиод горит; это потому что
    // на ESP-01 активный низкий уровень)
  } else {
    digitalWrite(D7, HIGH);  // Выключаем светодиод, подавая ВЫСОКОЕ напряжение
  }

}

void reconnect() {
  // Цикл продолжается до тех пор, пока мы не восстановим соединение
  while (!client.connected()) {
    Serial.print("Attempting MQTT connection...");
    // Попытка подключения
    if (client.connect("ESP8266Client")) {
      Serial.println("connected");
      // После подключения опубликуйте объявление...
      client.publish("outTopic", "hello world");
      // ... и подпишитесь повторно
      client.subscribe("inTopic");
    } else {
      Serial.print("failed, rc=");
      Serial.print(client.state());
      Serial.println(" try again in 5 seconds");
      // Подождите 5 секунд перед повторной попыткой
      delay(1000);
    }
  }
}
void loop() {

  if (!client.connected()) {
    reconnect();
  }
  client.loop();

  long now = millis();
  if (now - lastMsg > 2000) {
    lastMsg = now;
    ++value;
    snprintf (msg, 75, "hello world #%ld", value);
    Serial.print("Publish message: ");
    Serial.println(msg);
    client.publish("outTopic", msg);
  }
}

Примечание: брокеры работают, я даже могу подключиться к ним через MQTT Box (прикрепленное изображение).

Подключение MQTT Box

, 👍1


1 ответ


Лучший ответ:

2

127.0.0.1 — это не адрес вашего компьютера. Это адрес интерфейса «loopback» — виртуального интерфейса, который позволяет устройству общаться с самим собой.

Это означает, что когда вы используете сам сервер MQTT, вы можете подключиться, потому что это все тот же компьютер. Однако ESP8266 пытается подключиться к себе, а не к серверу MQTT.

Вам необходимо заменить 127.0.0.1 на фактический IP-адрес вашего сервера MQTT.

Самый простой способ узнать IP-адрес вашего компьютера — открыть окно терминала и ввести:

hostname -I
,

Спасибо за ответ. Где я могу узнать реальный IP-адрес моего сервера MQTT?, @Adis

Введите ip address в терминале и найдите интерфейс, к которому вы подключаетесь. Вероятно, это будет 192.168.xxx.xxx., @Majenko

В качестве альтернативы вы можете запустить hostname -I (это заглавная буква i), и она выдаст вам все ваши не-петлевые IP-адреса., @Majenko

Он вернул **192.168.100.3**, я заменил его в своем коде, но он все еще показывает **rc = 2**. Есть идеи? Это только так с использованием локального брокера., @Adis

Какой IP-адрес присвоен вашему ESP8266?, @Majenko

ESP8266 присвоен адрес **192.168.100.12**, @Adis

Попробуйте запустить netstat -an4 | grep 1883 | grep LISTEN и скажите, что она вам скажет, @Majenko

Спасибо. Внезапно заработало, после вашего предложения **hostname -I**., @Adis

Можете ли вы мне снова помочь? Это внезапно перестало работать. Это кажется очень непоследовательным. Я не менял код со вчерашнего дня (последний раз, когда это работало)., @Adis

нетстат -an4 | греп 1883 | grep LISTEN дает мне tcp 0 0 127.0.0.1:11883 0.0.0.0:* СЛУШАТЬ tcp 0 0 0.0.0.0:1883 0.0.0.0:* СЛУШАТЬ, @Adis

Последняя строка этого вывода — mosquitto, слушающий все интерфейсы, так что все в порядке. Если это *работало*, но сейчас не работает, это может быть связано с вашей сетью или компьютером. Это не ваш эскиз, поскольку он не меняется., @Majenko

Как мне правильно это диагностировать? Я использую Ubuntu 18.04 по WiFi-соединению., @Adis

Однако я бы обработал ваше соединение по-другому в вашем эскизе. Подождите, позвольте мне загрузить пример, который я использую вживую прямо сейчас (5- канальный цифровой аудиомикшер, управляемый MQTT)..., @Majenko

Еще одно замечание: я перечислил все устройства, подключенные к моей сети WiFi, я попытался пинговать ВСЕ устройства, которые находятся в сети, по их IP-адресу, но в результате получается From 192.168.100.3 icmp_seq=3 Destination Host Unreachable. Работает только пинг до NodeMCU 64 байта from 192.168.100.12: icmp_seq=3 ttl=255 time=11.9 ms. Может быть, в этом проблема?, @Adis

Ого, действительно странно! Теперь он подключен к MTTQ. Я просто оставил его в покое., @Adis

Вот пример: https://github.com/majenkotech/AmpControl/blob/master/AmpControl.ino — сосредоточьтесь на том, что находится в цикле, остальное не имеет значения., @Majenko

Чтобы дать вам обзор: вам не нужно *ждать* подключения WiFi. Вам просто нужно посмотреть, подключено оно или нет - и если да, то проверить, подключен ли MQTT, и подключить его, если нет, подписавшись, как только соединение будет установлено, @Majenko

Хм, спасибо за помощь, но я не совсем понимаю разницу, в принципе, она линейна с моей логикой. У меня просто проблемы с подключением MQTT, что, как я подозреваю, как-то связано с моим WiFi/хостом., @Adis

Это займет около > 20 из них Попытка подключения MQTT...не удалось, rc=-2, повторите попытку через 5 секунд, пока подключение не будет установлено., @Adis

Я бы предложил избавиться от этой 5-секундной задержки (или значительно сократить ее)., @Majenko