Hello all,
I am working on a project that requires me to talk to my AWS Thing instance from my ESP32. I am using a lilygo board that should have all the hardware I need, and I have a fresh SIM card from Hologram that I have activated and that I can see usage on.
The code should connect to LTE, then connect to AWS, and then publish some data. The project aims to publish GPS data routinely so that it can be plotted on a map. The current issue is that the mqtt_connect() call always returns false, and I can never connect to my topic. I can connect to LTE, but I can't get past AWS. I have created a new Thing and generated new certs which didn't help. Below is my code and the console output:
/**
* @file MqttsBuiltlnAWS.ino
* @author Lewis He (lewishe@outlook.com)
* @license MIT
* @copyright Copyright (c) 2023 Shenzhen Xin Yuan Electronic Technology Co., Ltd
* @date 2023-11-28
* @note
* * * Example is suitable for A7670X/A7608X/SIM7672 series
* * Connect MQTT Broker as https://aws.amazon.com/campaigns/IoT
* * Example uses a forked TinyGSM <https://github.com/lewisxhe/TinyGSM>, which will not compile successfully using the mainline TinyGSM.
* *!!!! When using ESP to connect to AWS, the AWS IOT HUB policy must be set to all devices, otherwise the connection cannot be made.
* *!!!! When using ESP to connect to AWS, the AWS IOT HUB policy must be set to all devices, otherwise the connection cannot be made.
* *!!!! When using ESP to connect to AWS, the AWS IOT HUB policy must be set to all devices, otherwise the connection cannot be made.
* *!!!! When using ESP to connect to AWS, the AWS IOT HUB policy must be set to all devices, otherwise the connection cannot be made.
* *Youtube : https://youtu.be/am-rTDzm4lQ
* */
#define TINY_GSM_RX_BUFFER 1024 // Set RX buffer to 1Kb
#define TINY_GSM_USE_GPRS true
// See all AT commands, if wanted
#define DUMP_AT_COMMANDS
#include "utilities.h"
#include <TinyGsmClient.h>
#include "certs/AWSClientCertificate.h"
#include "certs/AWSClientPrivateKey.h"
#include "certs/AmazonRootCA.h"
#include <PubSubClient.h>
#ifdef DUMP_AT_COMMANDS // if enabled it requires the streamDebugger lib
#include <StreamDebugger.h>
StreamDebugger debugger(SerialAT, Serial);
TinyGsm modem(debugger);
#else
TinyGsm modem(SerialAT);
#endif
// MQTT details
const char *broker = "a3jw4mm4a8k9f8-ats.iot.us-east-2.amazonaws.com";
const uint16_t broker_port = 8883;
const char *clien_id = "iot24_zami_GPSTracker"; // Was "ZaneTest" then proj5
const char *subscribe_topic = "zami_gps/data";
const char *publish_topic = "zami_gps/data";
// Current connection index, range 0~1
const uint8_t mqtt_client_id = 0;
uint32_t check_connect_millis = 0;
void mqtt_callback(const char *topic, const uint8_t *payload, uint32_t len) {
Serial.println();
Serial.println("======mqtt_callback======");
Serial.print("Topic:");
Serial.println(topic);
Serial.println("Payload:");
for (int i = 0; i < len; ++i) {
Serial.print(payload[i], HEX);
Serial.print(",");
}
Serial.println();
Serial.println("=========================");
}
bool mqtt_connect() {
Serial.print("Connecting to ");
Serial.print(broker);
bool ret = modem.mqtt_connect(mqtt_client_id, broker, broker_port, clien_id);
if (!ret) {
Serial.println("Failed!");
return false;
}
Serial.println("successed.");
if (modem.mqtt_connected()) {
Serial.println("MQTT has connected!");
} else {
return false;
}
// Set MQTT processing callback
modem.mqtt_set_callback(mqtt_callback);
// Subscribe to topic
modem.mqtt_subscribe(mqtt_client_id, subscribe_topic);
return true;
}
void setup() {
Serial.begin(115200); // Set console baud rate
Serial.println("Start Sketch");
SerialAT.begin(115200, SERIAL_8N1, MODEM_RX_PIN, MODEM_TX_PIN);
#ifdef BOARD_POWERON_PIN
pinMode(BOARD_POWERON_PIN, OUTPUT);
digitalWrite(BOARD_POWERON_PIN, HIGH);
#endif
// Set modem reset pin ,reset modem
pinMode(MODEM_RESET_PIN, OUTPUT);
digitalWrite(MODEM_RESET_PIN, !MODEM_RESET_LEVEL);
delay(100);
digitalWrite(MODEM_RESET_PIN, MODEM_RESET_LEVEL);
delay(2600);
digitalWrite(MODEM_RESET_PIN, !MODEM_RESET_LEVEL);
pinMode(BOARD_PWRKEY_PIN, OUTPUT);
digitalWrite(BOARD_PWRKEY_PIN, LOW);
delay(100);
digitalWrite(BOARD_PWRKEY_PIN, HIGH);
delay(100);
digitalWrite(BOARD_PWRKEY_PIN, LOW);
// Check if the modem is online
Serial.println("Start modem...");
int retry = 0;
while (!modem.testAT(1000)) {
Serial.println(".");
if (retry++ > 10) {
digitalWrite(BOARD_PWRKEY_PIN, LOW);
delay(100);
digitalWrite(BOARD_PWRKEY_PIN, HIGH);
delay(1000);
digitalWrite(BOARD_PWRKEY_PIN, LOW);
retry = 0;
}
}
Serial.println();
// Check if SIM card is online
SimStatus sim = SIM_ERROR;
while (sim != SIM_READY) {
sim = modem.getSimStatus();
switch (sim) {
case SIM_READY:
Serial.println("SIM card online");
break;
case SIM_LOCKED:
Serial.println("The SIM card is locked. Please unlock the SIM card first.");
// const char *SIMCARD_PIN_CODE = "123456";
// modem.simUnlock(SIMCARD_PIN_CODE);
break;
default:
break;
}
delay(1000);
}
//SIM7672G Can't set network mode
#ifndef TINY_GSM_MODEM_SIM7672
if (!modem.setNetworkMode(MODEM_NETWORK_AUTO)) {
Serial.println("Set network mode failed!");
}
String mode = modem.getNetworkModes();
Serial.print("Current network mode : ");
Serial.println(mode);
#endif
while (!modem.gprsConnect("hologram", "", "")) {
Serial.println("connecting to apn...");
delay(1000);
}
// Check network registration status and network signal status
int16_t sq;
Serial.print("Wait for the modem to register with the network.");
RegStatus status = REG_NO_RESULT;
while (status == REG_NO_RESULT || status == REG_SEARCHING || status == REG_UNREGISTERED) {
status = modem.getRegistrationStatus();
switch (status) {
case REG_UNREGISTERED:
case REG_SEARCHING:
sq = modem.getSignalQuality();
Serial.printf("[%lu] Signal Quality:%d", millis() / 1000, sq);
delay(1000);
break;
case REG_DENIED:
Serial.println("Network registration was rejected, please check if the APN is correct");
return;
case REG_OK_HOME:
Serial.println("Online registration successful");
break;
case REG_OK_ROAMING:
Serial.println("Network registration successful, currently in roaming mode");
break;
default:
Serial.printf("Registration Status:%d\n", status);
delay(1000);
break;
}
}
Serial.println();
Serial.printf("Registration Status:%d\n", status);
delay(1000);
String ueInfo;
if (modem.getSystemInformation(ueInfo)) {
Serial.print("Inquiring UE system information:");
Serial.println(ueInfo);
}
// while (!modem.enableNetwork()) {
// Serial.println("Enable network failed - retrying...");
// delay(1000);
// }
// Serial.println("Network Opened!");
delay(5000);
String ipAddress = modem.getLocalIP();
Serial.print("Network IP:");
Serial.println(ipAddress);
// Initialize MQTT, use SSL
if (modem.mqtt_begin(true))
Serial.println("Began MQTT Client");
// Set Amazon Certificate
modem.mqtt_set_certificate(AmazonRootCA, AWSClientCertificate, AWSClientPrivateKey);
// Connecting to AWS IOT Core
if (!mqtt_connect()) {
return; // Don't run connect() too many times because it sucks up data
}
while (1) {
// Check the connection every ten seconds
if (millis() > check_connect_millis) {
check_connect_millis = millis() + 10000UL;
if (!modem.mqtt_connected()) {
mqtt_connect();
} else {
// If connected, send information once every ten seconds
String payload = "RunTime:" + String(millis() / 1000);
modem.mqtt_publish(0, publish_topic, payload.c_str());
}
}
// MQTT handling
modem.mqtt_handle();
delay(5);
}
}
void loop() {
// Debug AT
if (SerialAT.available()) {
Serial.write(SerialAT.read());
}
if (Serial.available()) {
SerialAT.write(Serial.read());
}
delay(1);
}
And the console output I am reading with AT commands being shown
=~=~=~=~=~=~=~=~=~=~=~= PuTTY log 2024.04.27 18:38:03 =~=~=~=~=~=~=~=~=~=~=~=
ets Jul 29 2019 12:21:46
rst:0x1 (POWERON_RESET),boot:0x12 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:1
load:0x3fff0030,len:1344
load:0x40078000,len:13964
load:0x40080400,len:3600
entry 0x400805f0
Start Sketch
Start modem...
AT
AT
AT
AT
.
AT
AT
AT
AT
.
AT
AT
AT
AT
.
AT
AT
AT
AT
.
AT
AT
AT
AT
.
AT
AT
AT
AT
.
AT
AT
AT
AT
.
AT
AT
AT
AT
.
AT
AT
AT
AT
+CPIN: READY
.
AT
*ATREADY: 1
AT
OK
AT+CPIN?
AT
OK
AT
OK
AT
OK
AT
OK
AT
OK
AT
OK
AT
OK
AT+CPIN?
+CPIN: READY
OK
SIM card online
AT+CNMP=2
SMS DONE
AT+CNMP=2
OK
AT+CNMP?
AT+CNMP?
+CNMP: 2
OK
Current network mode : AUTO
AT+NETCLOSE
AT+NETCLOSE
+NETCLOSE: 2
ERROR
AT+CGDCONT=1,"IP","hologram","0.0.0.0",0,0
AT+CGDCONT=1,"IP","hologram","0.0.0.0",0,0
OK
AT+CIPMODE=0
AT+CIPMODE=0
OK
AT+CIPSENDMODE=0
AT+CIPSENDMODE=0
OK
AT+CIPCCFG=10,0,0,0,1,0,75000
AT+CIPCCFG=10,0,0,0,1,0,75000
OK
AT+CIPTIMEOUT=75000,15000,15000
AT+CIPTIMEOUT=75000,15000,15000
OK
AT+CGACT=1,1
AT+CGACT=1,1
+CME ERROR: unknown error
+CGEV: EPS PDN ACT 1
PB DONE
connecting to apn...
AT+NETCLOSE
AT+NETCLOSE
+NETCLOSE: 2
ERROR
AT+CGDCONT=1,"IP","hologram","0.0.0.0",0,0
AT+CGDCONT=1,"IP","hologram","0.0.0.0",0,0
OK
AT+CIPMODE=0
AT+CIPMODE=0
OK
AT+CIPSENDMODE=0
AT+CIPSENDMODE=0
OK
AT+CIPCCFG=10,0,0,0,1,0,75000
AT+CIPCCFG=10,0,0,0,1,0,75000
OK
AT+CIPTIMEOUT=75000,15000,15000
AT+CIPTIMEOUT=75000,15000,15000
OK
AT+CGACT=1,1
AT+CGACT=1,1
OK
AT+NETOPEN
AT+NETOPEN
OK
+NETOPEN: 0Wait for the modem to register with the network.AT+CGREG?
AT+CGREG?
+CGREG: 0,5
OK
Network registration successful, currently in roaming mode
Registration Status:5
AT+CPSI?
AT+CPSI?
+CPSI: LTE,Online,310-260,0xA181,30298981,372,EUTRAN-BAND4,2350,3,0,15,37,37,4
OK
Inquiring UE system information:LTE,Online,310-260,0xA181,30298981,372,EUTRAN-BAND4,2350,3,0,15,37,37,4
AT+IPADDR
AT+IPADDR
+IPADDR: 100.76.10.133
OK
Network IP:100.76.10.133
AT+CMQTTSTART
AT+CMQTTSTART
OK
+CMQTTSTART: 0
Began MQTT Client
Connecting to a3jw4mm4a8k9f8-ats.iot.us-east-2.amazonaws.comAT+CCERTDOWN="ca_cert.pem",1199
AT+CCERTDOWN="ca_cert.pem",1199
>
-----BEGIN ROOT CERTIFICATE-----
<secret ca_cert>
-----END ROOT CERTIFICATE-----
OK
AT+CSSLCFG="cacert",0,"ca_cert.pem"
AT+CSSLCFG="cacert",0,"ca_cert.pem"
OK
AT+CCERTDOWN="cert.pem",1221
AT+CCERTDOWN="cert.pem",1221
>
-----BEGIN CERTIFICATE-----
<secret cert>
-----END CERTIFICATE-----
OK
AT+CSSLCFG="clientcert",0,"cert.pem"
AT+CSSLCFG="clientcert",0,"cert.pem"
OK
AT+CCERTDOWN="key_cert.pem",1676
AT+CCERTDOWN="key_cert.pem",1676
>
-----BEGIN RSA PRIVATE KEY-----
<secret private key>
-----END RSA PRIVATE KEY-----
OK
AT+CSSLCFG="clientkey",0,"key_cert.pem"
AT+CSSLCFG="clientkey",0,"key_cert.pem"
OK
AT+CSSLCFG="sslversion",0,4
AT+CSSLCFG="sslversion",0,4
OK
AT+CMQTTSSLCFG=0,0
AT+CMQTTSSLCFG=0,0
OK
AT+CSSLCFG="authmode",0,2
AT+CSSLCFG="authmode",0,2
OK
AT+CMQTTREL=0
AT+CMQTTREL=0
+CMQTTREL: 0,20
ERROR
AT+CMQTTACCQ=0,"iot24_zami_GPSTracker",1
AT+CMQTTACCQ=0,"iot24_zami_GPSTracker",1
OK
AT+CMQTTCONNECT=0,"tcp://a3jw4mm4a8k9f8-ats.iot.us-east-2.amazonaws.com:8883",60,1
AT+CMQTTCONNECT=0,"tcp://a3jw4mm4a8k9f8-ats.iot.us-east-2.amazonaws.com:8883",60,1
+CMQTTCONNECT: 0,34
ERROR
Failed!
I am seeking advice for using LTE to communicate with AWS using MQTT. I will be extremely active on this topic, so please don't hesitate to ask questions.