STM32-ESP8266-MQTT通信
2025/12/12大约 2 分钟
STM32-ESP8266-MQTT通信
OLED用来显示调试信息
代码详情
串口格式化打印
void uart_print(UART_HandleTypeDef *huart,char* format,...) {
char buf[128]={0};
va_list ap;
va_start(ap,format);
vsprintf(buf,format,ap);
va_end(ap);
HAL_UART_Transmit(huart,(uint8_t*)buf,strlen(buf),HAL_MAX_DELAY);
}中断不定长接收
// 初始化串口接收
HAL_UART_Receive_IT(&huart2,uart_buffer,1);
// 中断接收函数
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart){
if(huart==&huart2){
uart_time = uwTick;
uart_index++;
HAL_UART_Receive_IT(&huart2,(uint8_t *)&uart_buffer[uart_index],1);
}
}
void uart_process(void){
if(uart_index==0)return;
if(uwTick>uart_time+100){
memset(&uart_buffer,0,uart_index);
uart_index=0;
huart2.pRxBuffPtr = uart_buffer;
}
}MQTT消息解析
mqtt接收消息形式如下:
AT+MQTTPUB=0,"aaa","Hello from ESP8266",0,0
OK
+MQTTSUBRECV:0,"aaa",18,Hello from ESP8266+MQTTSUBRECV:0,"aaa",18,Hello from ESP8266即为我们要解析的数据
根据该数据的特点,aaa由双引号包裹,数据长度为第2个和第3个逗号之间,数据在第3个逗号后进行针对性解析
void extract_mqtt_info(const char *str, char *info1, char *info_b) {
const char *p1 = strchr(str, '"'); // 第一个引号
if (!p1) return;
const char *p2 = strchr(p1 + 1, '"'); // 第二个引号
if (!p2) return;
// 提取 info1
size_t len1 = p2 - p1 - 1;
strncpy(info1, p1 + 1, len1);
info1[len1] = '\0';
// 向后找逗号,找到数字部分
const char *p_comma = strchr(p2 + 1, ',');
if (!p_comma) return;
int length = atoi(p_comma + 1); // 提取长度数值
// 再找一个逗号,找到消息体开始处
const char *msg_start = strchr(p_comma + 1, ',');
if (!msg_start) return;
msg_start++; // 跳过逗号
// 提取信息b
strncpy(info_b, msg_start, length);
info_b[length] = '\0';
}MQTT连接
uart_print(&huart2,"AT+MQTTCLEAN=0\r\n");
uart_print(&huart2,"AT+CWJAP=\"aaa\",\"aaaaaaaa\"\r\n");
uart_print(&huart2,"AT+MQTTUSERCFG=0,1,\"fs\",\"111111\",\"272935657\",0,0,\"\"\r\n");
uart_print(&huart2,"AT+MQTTCONN=0,\"47.113.191.144\",1883,1\r\n");
uart_print(&huart2,"AT+MQTTSUB=0,\"topic1\",1\r\n");MQTT发送信息
uart_print(&huart2,"AT+MQTTPUB=0,\"topic1\",\"Ha\",0,0\r\n");主要思路
- 先初始化,连接MQTT服务器
- 完成串口不定长接收
- 接收消息后解析并打印
