0

I'm trying to send data over MQTT from an ESP32 to my computer. I have two distinct sets of data going to two topics, temperature and gravity. For some reason, it will only publish one message, but send it twice to the broker and its whatever message is published first. I'm not sure what I could be doing differently.

Arduino code:

int parseTilt(String DevData) {
  String DevUUID, DevColour, DevTempData, DevGravityData;
  int colourInt;
  float DevTemp, DevGravity;

  // Determine the Colour
  colourInt = DevData.substring(6, 7).toInt();

  switch (colourInt) {
    case 1:
      DevColour = "Red";
      break;
    case 2:
      DevColour = "Green";
      break;
    case 3:
      DevColour = "Black";
      break;
    case 4:
      DevColour = "Purple";
      break;
    case 5:
      DevColour = "Orange";
      break;
    case 6:
      DevColour = "Blue";
      break;
    case 7:
      DevColour = "Yellow";
      break;
    case 8:
      DevColour = "Pink";
      break;
  }

  if (repeatColour != 0 && repeatColour != colourInt) {
    Serial.print(DevColour);
    Serial.println(" Tilt is being ignored.");
    return 0;
  }

  //Generate the UUID
  DevUUID += DevData.substring(0, 8);
  DevUUID += "-";
  DevUUID += DevData.substring(8, 12);
  DevUUID += "-";
  DevUUID += DevData.substring(12, 16);
  DevUUID += "-";
  DevUUID += DevData.substring(16, 20);
  DevUUID += "-";
  DevUUID += DevData.substring(20, 32);


  // Get the temperature
  DevTempData = DevData.substring(32, 36);
  DevTemp = strtol(DevTempData.c_str(), NULL, 16); // Temp in Freedumb units

  // Get the gravity
  DevGravityData = DevData.substring(36, 40);
  DevGravity = strtol(DevGravityData.c_str() , NULL, 16);

  Serial.println("--------------------------------");
  Serial.print("Colour: ");
  Serial.println(DevColour);
  Serial.print("Temp: ");
  if (Celsius) {
     Serial.print((DevTemp-32.0) * (5.0/9.0));
     Serial.println(" C");
  }
  else {
    Serial.print(DevTemp);
    Serial.println(" F");
  }
  Serial.print("Gravity: ");
  float DevGravityFormatted = (DevGravity / 1000);
  Serial.println(DevGravityFormatted);
  Serial.println(DevGravityFormatted, 3);
  Serial.println(DevGravityFormatted);
  Serial.println(DevData);
  Serial.println(DevData.substring(0,32));
  Serial.println(DevUUID);
  Serial.println("--------------------------------");


  client.loop();
  Serial.println(DevGravity, 16);
  char tempGravity[16];
  dtostrf(DevGravity, 16, 3, tempGravity);
  char tempTemp[5];
  dtostrf(DevTemp, 5, 2, tempTemp);
  Serial.println("tempGravity");
  Serial.println(tempGravity);
  Serial.println("tempTemp");
  Serial.println(tempTemp);
  client.publish("fermentation/temperature", tempTemp);
  client.loop();
  delay(500);
  client.publish("fermentation/gravity",tempGravity);
  client.loop();
  Serial.println("published");

  return 2;
}

And the python code on my computer:

MQTT_SERVER = "192.168.1.69"
MQTT_PATH_1 = ('fermentation/gravity')
MQTT_PATH_2 = ('fermentation/temperature')


def on_connect(client, userdata, flags, rc):
    print('conncected, result: ' + str(rc))
    client.subscribe(MQTT_PATH_1)
    print('subscribed gravity')
    client.subscribe(MQTT_PATH_2)
    print('subscribed temperature')

def on_message(client, userdata, msg):
    temp = str(msg.payload).split("'")
    if msg.topic == MQTT_PATH_1:
        print('mqtt 1')
        print(msg.topic + ' ' + str(msg.payload))
    if msg.topic == MQTT_PATH_2:
        print('mqtt 2') 
        print(msg.topic + ' ' + str(msg.payload))
    else:
        print('else')
        print(msg.topic + ' ' + str(msg.payload))
    

client = mqtt.Client()
client.on_connect = on_connect
client.on_message = on_message
client.connect(MQTT_SERVER, 1883, 60)

client.loop_forever()

The output comes out to this: mqtt 2 fermentation/temperature b'75.00' mqtt 2 fermentation/temperature b'75.00'

Not sure what I'm doing wrong. Please excuse the arduino code, I'm a noob. It is adapted from this code: https://github.com/N3MIS15/ESP32-Tilt-Repeater/blob/master/ESP32-Tilt-Repeater.ino

Thanks for the help!

  • So I found a workaround. I moved the lines of code formatting and publishing the gravity earlier in the script, prior to the temperature formatting and publishing. For some reason this works and I now get both messages on my computer. Unclear why this is the case. – broke student May 25 '22 at 20:58
  • 1
    `tempGravity` and `tempTemp` are too small. You call `dtostrf(DevGravity, 16, 3, tempGravity)`, so `tempGravity` should be defined to have at least 22 (16 + 3 + 2 + null terminator) characters. You need to include enough space for all the digits plus the dot and possibly a minus sign, and a C string null terminator. `tempTemp` should be defined to have at least 10. You're clobbering your stack by overwriting them. – romkey May 26 '22 at 00:05
  • @romkey yes this fixed it! Also fixed another issue I was having as well! I didn't realize when creating char objects you had to account for more than what the final result will be. Thank you! – broke student May 27 '22 at 13:22
  • Great, I'm happy you tried it and it worked for you! :) – romkey May 27 '22 at 15:54

0 Answers0