Arduino HTTP Working for One Unit, but not Another

Hello!

I build ESP32-based nixie displays for fun, and recently built two of the same display, one of which I provided to a contact. The code I used for my display is exactly the same as the code they use for theirs, however - mine is able to connect to a specified webpage, whereas there's has not. No amount of troubleshooting preformed has allowed me to figure out how the same code for the same device can work for one system, but not another.

Both units successfully connect to the internet. However, one is successfully able to preform a GET or POST request, while the other fails.

Code:

please post your code using </>

hardcoded address?

could you explain which is server and client?

Sorry about that, will do next time (also posted below).

Yes, hardcoded web address, in the code: https://www.mahdial-husseini.com/jon_dustoff7971_view.php

Arduino is client, server is the webserver, unless you are referring to something else

 /* IoT 7971 Display, 28 APR 2021 ESP32 FEATHER
 * mahdi07@msn.com (404)771-3315 
 * mahdialhusseini.com 
 * 
 * This source code is for an ESP32 and customized B7971 DUSTOFF display, with the corresponding html/php/CSS/SQL code on the back-side
 * 
 * notes:
 * note that Serial is being reserved for wireless transmission to hardware. set diagnosisFlag to true to troubleshoot in Serial Monitor
 * BAUD rate of 9600 critical to interface with PIC direct-drivers firmware
 * If you enter INFINITE SCROLL mode, the only way to exist is by submitting a new request that is NOT INFINITE SCROLL. From then, the default will reengage
 *  */

/* library information ESP32*/
#include <WiFi.h>
#include <HTTPClient.h>
#include <WebServer.h>
#include <WiFiUdp.h>
#include <ESPmDNS.h>
#include <ArduinoOTA.h>
#include <Wire.h>
#include <SPI.h>
#include <SoftwareSerial.h>

/* library information ESP8266*/
/*
#include <ESP8266HTTPClient.h>
#include <WiFiClientSecure.h> 
#include <DNSServer.h>
#include <ESP8266WiFi.h>
*/

// include HTTP and HTTPS options, with redirection automatic
// #include <ESP8266WebServer.h>
// #include <ESP8266WebServerSecure.h>
// const byte DNS_PORT = 53;
// DNSServer dnsServer;

#include <WiFiUdp.h>
#include <ArduinoOTA.h>
#include <Wire.h>
#include <SPI.h>
#include <SoftwareSerial.h>

/* WiFi information*/

/*

/* const char* ssid = "XXXXXX";  // Enter SSID here
const char* password = "XXXXXXX";  //Enter Password here */

/* initializing and defining global variables */
String instance;
String formatted;

#define RXD2 16
#define TXD2 17

bool infiniteScroll = true; 
bool internetFlag = true; 
bool defaultFlag = true;
bool diagnosisFlag = true;

char* submission = "DUSTOFF";
char* style = "static";
char* rate = "fast";
char* uniqueID = "0";
char uniqueRes[] = "0";

// default conditions
char* defaultSubmission = "DUSTOFF";
char* defaultStyle = "static";
char* defaultRate = "fast";

bool WiFiFlag = true;
bool resetFlag = false;

// root certificate specific to mahdial-husseini.com
static const char root_ca[] PROGMEM = R"EOF(
-----BEGIN CERTIFICATE-----
MIIDSjCCAjKgAwIBAgIQRK+wgNajJ7qJMDmGLvhAazANBgkqhkiG9w0BAQUFADA/
MSQwIgYDVQQKExtEaWdpdGFsIFNpZ25hdHVyZSBUcnVzdCBDby4xFzAVBgNVBAMT
DkRTVCBSb290IENBIFgzMB4XDTAwMDkzMDIxMTIxOVoXDTIxMDkzMDE0MDExNVow
PzEkMCIGA1UEChMbRGlnaXRhbCBTaWduYXR1cmUgVHJ1c3QgQ28uMRcwFQYDVQQD
Ew5EU1QgUm9vdCBDQSBYMzCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB
AN+v6ZdQCINXtMxiZfaQguzH0yxrMMpb7NnDfcdAwRgUi+DoM3ZJKuM/IUmTrE4O
rz5Iy2Xu/NMhD2XSKtkyj4zl93ewEnu1lcCJo6m67XMuegwGMoOifooUMM0RoOEq
OLl5CjH9UL2AZd+3UWODyOKIYepLYYHsUmu5ouJLGiifSKOeDNoJjj4XLh7dIN9b
xiqKqy69cK3FCxolkHRyxXtqqzTWMIn/5WgTe1QLyNau7Fqckh49ZLOMxt+/yUFw
7BZy1SbsOFU5Q9D8/RhcQPGX69Wam40dutolucbY38EVAjqr2m7xPi71XAicPNaD
aeQQmxkqtilX4+U9m5/wAl0CAwEAAaNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNV
HQ8BAf8EBAMCAQYwHQYDVR0OBBYEFMSnsaR7LHH62+FLkHX/xBVghYkQMA0GCSqG
SIb3DQEBBQUAA4IBAQCjGiybFwBcqR7uKGY3Or+Dxz9LwwmglSBd49lZRNI+DT69
ikugdB/OEIKcdBodfpga3csTS7MgROSR6cz8faXbauX+5v3gTt23ADq1cEmv8uXr
AvHRAosZy5Q6XkjEGB5YGV8eAlrwDPGxrancWYaLbumR9YbK+rlmM6pZW87ipxZz
R8srzJmwN0jP41ZL9c8PDHIyh8bwRLtTcm1D9SZImlJnt1ir/md2cXjbDaJWFBM5
JDGFoqgCWjBH4d1QB7wCCZAA62RjYJsWvIjJEubSfZGL+T0yjWW06XyxV3bqxbYo
Ob8VZRzI9neWagqNdwvYkQsEjgfbKbYK7p2CNTUQ
-----END CERTIFICATE-----
)EOF";

void connectToNetwork() {
  if (diagnosisFlag) {
    // scanNetworks(); // optional
    Serial.print("Connecting to WiFi..");
  }

  WiFi.begin(ssid, password); 
  // WiFi.mode(WIFI_STA);
  
  while (WiFi.status() != WL_CONNECTED) {
    delay(1000);
    if (diagnosisFlag) {
      Serial.print(".");
    }
  }

  if (diagnosisFlag) {
    Serial.println("Connected to the WiFi network");
  }
}

void setup() {
  Serial.begin(9600);  
  Serial2.begin(9600, SERIAL_8N1, RXD2, TXD2);
  delay(100);
  // Serial.println("Initial Setup");

  /************** 7971 INITIALIZATION **************/
  // {$B7F...}, {$B7E...}, and {$B7S...} are standard configurations for B7971 text display. This can be adjusted as desired; reference the smart_socket guide pdf. 
  Serial2.println("$B7F0000000<cr>");
  Serial2.println("$B7E0000000<cr>");
  Serial2.println("$B7S0000000<cr>");
  // Retain "$B7M" and "<cr>, but replace "MEDEVAC" as desired for start-up display. 
  Serial2.println("$B7MDUSTOFF<cr>");

  /************** WIFI CONNECT **************/
  // Clear out EEPROM
  if (internetFlag == true){ 
    // Serial.println("WiFi delete all config...");
    // delete all existing WiFi stuff in EEPROM
    WiFi.disconnect();

    connectToNetwork();
    Serial.println("");
    Serial.print("Got IP: ");  Serial.println(WiFi.localIP());
  }

  delay(2000);

  establishOTA();
}

void loop() {
  ArduinoOTA.handle();
 
  if ((WiFi.status() == WL_CONNECTED)) {
    if (WiFiFlag == true) {
      Serial.println("WiFi! Connected");
      scroll("WIFI CONNECTED", "slow");
      WiFiFlag = false;
    }
 
    HTTPClient http;
 
    http.begin("https://www.mahdial-husseini.com/jon_dustoff7971_view.php", root_ca); //Specify the URL and certificate
    http.addHeader("Content-Type", "text/plain");             //Specify content-type header
    int httpCode = http.GET();                                                  //Make the request

    if (httpCode > 0) { //Check for the returning code
      String payload = http.getString();

      // parse time
      char * pch;                     // pointer to tokens        
      char copy[300];
      int counter = 0;
      
      payload.toCharArray(copy, 300);
      pch = strtok (copy,"|");         // get first token
      
      while (pch != NULL)
        {
        if (counter == 1) {
          submission = pch;
        }
        else if (counter == 2) {
          style = pch;
        }
        else if (counter == 3) {
          uniqueID = pch;
        }
        else if (counter == 4) {
          rate = pch;
        }
        
        pch = strtok (NULL, "|");     // get next token
        counter++;
       }  

       if (diagnosisFlag) {
          Serial.println();
          Serial.print("submission found: ");
          Serial.println(submission);
          Serial.print("style found: ");
          Serial.println(style);
          Serial.print("ID found: ");
          Serial.println(uniqueID);
          Serial.print("rate found: ");
          Serial.println(rate);
          Serial.print("httpCode: ");
          Serial.println(httpCode);
       }
    }
 
    else {
      if (diagnosisFlag) {
        Serial.println("Error on HTTP request");
        scroll("CANNOT CONNECT TO BACKEND", "slow");
      }
    }
 
    http.end(); //Free the resources
  }

  // if new, original request (as determined by request ID)
  Serial.println(uniqueRes);
  Serial.println(uniqueID);
  
  if(strcmp(uniqueRes, uniqueID) != 0) {
    Serial.println(">> New Original Request Recieved! <<");
    defaultFlag = false;
    textSubmission(submission, style, rate);   
  } else if (infiniteScroll == false and resetFlag == true) {
    defaultFlag = true;
    textSubmission(defaultSubmission, defaultStyle, defaultRate);
  }

  strcpy (uniqueRes, uniqueID); // reset ID for following iterations
  
  if (infiniteScroll == true and defaultFlag == false){
    // infinite scroll not a publicly available option! restrict appropriately
    scroll(submission, rate);
  }

 
  delay(1000);
}

void establishOTA() {
  ArduinoOTA.onStart([]() {
      String type;
      if (ArduinoOTA.getCommand() == U_FLASH)
        type = "sketch";
      else // U_SPIFFS
        type = "filesystem";

      // NOTE: if updating SPIFFS this would be the place to unmount SPIFFS using SPIFFS.end()
      // Serial.println("Start updating " + type);
    });
    
    if (diagnosisFlag) {
      ArduinoOTA.onEnd([]() {
        Serial.println("\nEnd");
      })
      .onProgress([](unsigned int progress, unsigned int total) {
        Serial.printf("Progress: %u%%\r", (progress / (total / 100)));
      })
      .onError([](ota_error_t error) {
        Serial.printf("Error[%u]: ", error);
        if (error == OTA_AUTH_ERROR) Serial.println("Auth Failed");
        else if (error == OTA_BEGIN_ERROR) Serial.println("Begin Failed");
        else if (error == OTA_CONNECT_ERROR) Serial.println("Connect Failed");
        else if (error == OTA_RECEIVE_ERROR) Serial.println("Receive Failed");
        else if (error == OTA_END_ERROR) Serial.println("End Failed");
      }); 
    }

  ArduinoOTA.begin();

  if (diagnosisFlag) {
    Serial.println("OTA Up and Running");
  }
}


void scanNetworks() {
 
  int numberOfNetworks = WiFi.scanNetworks();

  Serial.print("Number of networks found: ");
  Serial.println(numberOfNetworks);
 
  for (int i = 0; i < numberOfNetworks; i++) {
 
    Serial.print("Network name: ");
    Serial.println(WiFi.SSID(i));
 
    Serial.print("Signal strength: ");
    Serial.println(WiFi.RSSI(i));
 
    Serial.print("MAC address: ");
    Serial.println(WiFi.BSSIDstr(i)); 
  }
}

/* takes text parsed from server-side html and submits to 7971s. utilizes String object; don't @ me */
void textSubmission(char* text, char* style, char* rate) {

  // clear out buffer first, initialize formatted, if default flag is false (otherwise consecutive similar requests will blink)
  if (defaultFlag == false) {
    formatted = "$B7M        <cr>";
    Serial2.println(formatted); 
  }
    
  if (strcmp(style, "scroll") == 0) {
    infiniteScroll = false;
    scroll(text, rate);
  }
  else if (strcmp(style, "static") == 0){
    infiniteScroll = false;
    String malleable = text; // conversion to String object for static text

    malleable.toUpperCase();
    formatted = "$B7M" + malleable + "<cr>";
    Serial2.println(formatted);
    if (defaultFlag == false) {
      delay(5000); // allow static requests (not the default) to stick around for at least five seconds
    }
  }
  // if infiniteScroll, don't scroll here
  else if (strcmp(style, "infiniteScroll") == 0){
    infiniteScroll = true;
  }
}

/* Scroll text across 7971s. utilizes String object; don't @ me */
void scroll(char* text, char* rate) {
  // transform data character array to String object for formatting and submission
  String malleable = text;
  // Uppercase the input string
  malleable = "        " + malleable + "        ";
  malleable.toUpperCase();
  
  for (int x = 0; x < malleable.length() - 7; x++) {
    instance = malleable.substring(x, x+8);
    formatted = "$B7M" + instance + "<cr>";
    Serial2.println(formatted); // submit properly formatted request to hardware
    
    // Adjust delay speed for fast or slow scroll
    if (strcmp(rate, "slow") == 0){
      delay(700);
    } 
    else if (strcmp(rate, "fast") == 0){
      delay(500);
    }
    else if (strcmp(rate, "ultrafast") == 0){
      delay(300);
    }
  }
}

is it just unable to connect to that web-page or not able to connect to the internet? (you gotta ask the dumb questions)

It was able to connect to the internet, but could not connect to the web-page in questions. It turns out the root certificate was the issue. It ended up not being necessary for whatever reason, and removing it allowed both units to work (even though one unit worked with it, while the other didn't - still not sure why that was)!