Cayenne - missing communication channels in browser

Hello to everyone,

I’m currently working on a biomedical device for measuring heart rate and Galvanic Skin Response(GSR). Because of a sample rate needed for heart rate measurement(50 Hz), message to Cayenne must be send in a time of maximum 20 ms. I checked my device with example code from Arduino library and it worked perfectly. Howewer, I’ve got troubles with getting my test program for to work - channels and values on these channels are absent in my web browser device menu. What could be a cause of such behaviour of Cayenne? I’m new to Cayenne and IoT in general, so I may make some mistakes due to lack of experience/knowledge.

Device is based on ESP32 DevkitC, code for testing communication in my biomedical device looks like this(for now, values from sensors are replaced with random values, just for purpose of testing communication capabilities, comments for file functions are temporary):

#define CAYENNE_DEBUG
#define CAYENNE_PRINT Serial
#include <CayenneMQTTESP32.h>
#include <CayenneArduinoMQTTClient.h>

// WiFi network info.
char ssid[] = "AndroidAP";
char wifiPassword[] = "63c1875d1564";

// Cayenne authentication info. This should be obtained from the Cayenne Dashboard.
char username[] = "";
char password[] = "";
char clientID[] = "";

unsigned long int lastMillis = 0;
unsigned int HeartRateSamples[150];
unsigned long int time_begin;
unsigned int time_of_operation;
unsigned int GSR_Value = 0;
unsigned int GSR_Sample = 0;
unsigned int GSR_Values = 0;
unsigned int Heart_Rate = 0;
unsigned int Voltage = 0;
unsigned int VoltageSample = 1;
unsigned int LoopCounter = 1;
unsigned int VoltageLoopCounter = 1;
bool measure_started = false;


void setup()
{
	  Serial.begin(9600);
          randomSeed(300);
	  Cayenne.begin(username, password, clientID, ssid, wifiPassword);
}

void loop()
{
 
      time_begin = micros();
      HeartRateSamples[LoopCounter] = random(2000, 4000);
    
      if(LoopCounter == 1 && measure_started == true)
      {
          //file.close();
      }

      if(LoopCounter%5 == 0)
      {
          GSR_Sample = random(500, 550);
          GSR_Values += GSR_Sample;
      }

      if(LoopCounter == 149)
      {
          //file.open()
      }

      if(LoopCounter == 150)
      {
          GSR_Value = GSR_Values/30;
          Cayenne.virtualWrite(0, GSR_Value);
          Cayenne.virtualWrite(1, HeartRateSamples[150]);
          LoopCounter = 0;
      }

      if(LoopCounter == 150 && VoltageLoopCounter == 10)
      {
          VoltageSample = random(400, 4000);
          GSR_Value = GSR_Values/30;
          Cayenne.virtualWrite(0, GSR_Value);
          Cayenne.virtualWrite(1, HeartRateSamples[150]);
          Cayenne.virtualWrite(2, VoltageSample);
          LoopCounter = 0;
          VoltageLoopCounter = 0;
      }

      measure_started = true;
      LoopCounter++;
      VoltageLoopCounter++;

      time_of_operation = micros() - time_begin;
      if(time_of_operation<20000)
      {
           delayMicroseconds(20000-time_of_operation);
      }
     
}

Hi @maciek.radz for such critical device operations - it;s highly recommended to computation at the edge and send periodic summaries or averages to the cloud. Cayenne and most IoT cloud have limits on data throughput.

Cayenne’s limit is 60 messages per 1 min or 1 msg / sec.

1 Like

You need to publish data within the rate limit. Sending MQTT messages within rate limits

Thank you for replies.

Actually, troubles with channels visibility were caused by an error in randomSeed() setting - seed was beyond the range of values that could be set in random() function calls.

1 Like

though you have to send the data within rate limit. with your current code, you are sending data at very rapid rate.

I’ ll try to explain how my program works, when it comes to dealing with Cayenne message rate limits.

I’m not planning to send messages in every iteration of the loop - there is a LoopCounter variable, which I use for counting amount of loop iterations. Message will be send only once per 150 iterations. Also, i’m getting information about time of each iteration. At the beginning of the loop iteration, i get information about time:

time_begin = micros();

After all required operations for each iteration of the main loop, i check time of operation and compare if it was shorter than 20 ms. If it was shorter, there is a program delay to wait to guarantee that each loop iteration lasts 20 ms.

time_of_operation = micros() - time_begin;
if(time_of_operation<20000)
{
delayMicroseconds(20000-time_of_operation);
}

Because each loop iteration is set to last at least 20 ms, and messages are once per 150 iterations, that give us a time between sending messages: 150*20 = 3000 ms = 3 seconds.

Each 3 seconds, messages are sent to Channel 0 and 1 - that gives us 40 messages per minute from sensors.

This message rate is set for sending data about heart rate and GSR value, for voltage message rate is divided by 10. In code, there is another counter, called VoltageLoopCounter, which is incremented by 1 each three seconds, when VoltageLoopCounter equals 10, message about battery voltage is sent to Cayenne.

Overall, there are 42 messages per minute and this amount of messages per minute should be within message rate limit of cayenne server.

1 Like