技术标签: 数字孪生 c语言 websocket linux 物联网 云计算
Mosquitto是一款轻量级的Mqtt消息代理软件,提供了C语言的动态库接口,用于运行C或C++编写的软件的场合,但是官方提供的默认编译版本是没有集成websockets功能的,如果需要Mosquitto代理软件能够支持websockets功能,则需要使用者自己去进行编译。本文即是介绍在Linux的环境下对Mosquitto软件和其C语言动态库如何进行编译的方法。
本文以CentOS 7.6环境为例进行说明,mosquitto采用2.0.9版本。
利用mosquitto的C语言客户端进行编程,通过cJSON或protobuff对消息内容进行格式化传输,并与前端JavaScript进行完全交互系列文章:
第一篇:Mosquitto打开Websockets模块并在Linux下的编译及安装使用
第二篇:cJSON模块在Mqtt代理mosquitto中的使用
mosquitto [-c config file] [ -d | --daemon ] [-p port number] [-v]
-c 后面跟的是启动mosquitto可以调整的参数,比如是否开启基本认证,端口是什么,SSL单向和双向的认证配置等等。
-d 表示MQTT mosquitto将在后台运行。
-p 代表当前的mosquitto服务实例启动以后,其监听端口号,这个配置的覆盖[-c config file] 指定的配置文件中的端口
-v 代码调试模式(verbose)可以输出更多的信息
要进行mosquitto的编译,需要提前准备好以下三个方面的动态库:
cmake3
yum install -y cmake3.x86_64
openssl
yum install -y openssl.x86_64 openssl-devel.x86_64 openssl-libs.x86_64 cmake3.x86_64
libwebsockets
git clone https://codechina.csdn.net/mirrors/warmcat/libwebsockets.git
mosquitto
git clone https://hub.fastgit.org/eclipse/mosquitto.git
cd libwebsockets/
mkdir build
cd build
cmake3 ..
make
make install
启用websockets,mosquitto需要开启websockets模块,需要更改以下两个地方的设置:
cd mosquitto-2.0.9/
mkdir build
cd build
cmake3 ..
make
make install
仅展示订阅端关键逻辑步骤代码。如果需要进行消息的发布需要使用消息发送函数mosquitto_publish。
#include <mosquitto.h>
bool session = true;
struct mosquitto *mosq = NULL;
void on_connect(struct mosquitto *mosq, void *obj, int reason_code)
{
int rc;
printf("##############on_connect: %s\n", mosquitto_connack_string(reason_code));
if(reason_code != 0){
mosquitto_disconnect(mosq);
}
//订阅主题
rc = mosquitto_subscribe(mosq, NULL, "test/control/#", 0);
printf("##################subscribing test/control/#..\n");
if(rc != MOSQ_ERR_SUCCESS){
fprintf(stderr, "Error subscribing: %s\n", mosquitto_strerror(rc));
mosquitto_disconnect(mosq);
}
}
void on_subscribe(struct mosquitto *mosq, void *obj, int mid, int qos_count, const int *granted_qos)
{
int i;
bool have_subscription = false;
printf("###############on_subscribe: qos_count=%d \n", qos_count);
for(i=0; i<qos_count; i++){
printf("###########on_subscribe: %d:granted qos = %d\n", i, granted_qos[i]);
if(granted_qos[i] <= 2){
have_subscription = true;
}
}
if(have_subscription == false){
fprintf(stderr, "Error: All subscriptions rejected.\n");
mosquitto_disconnect(mosq);
}
}
void on_message(struct mosquitto *mosq, void *obj, const struct mosquitto_message *msg)
{
if(msg->payloadlen){
//parse json here
char * data=new char[msg->payloadlen+1];
sprintf(data,(char *)msg->payload);
printf("######## %s %d payload=%s data=%s \n", msg->topic, msg->qos, (char *)msg->payload,data);
}
// 当断开连接时调用回调该函数
void on_disconnect(struct mosquitto *mosq, void *obj, int rc)
{
printf("###############Call the function: my_disconnect_callback\n");
//exitflag = TRUE;
}
void my_log_callback(struct mosquitto *mosq, void *userdata, int level, const char *str)
{
printf("%s\n", str);
}
int main(int argc,char *argv[])
{
//libmosquitto 库初始化
mosquitto_lib_init();
//创建mosquitto客户端
mosq = mosquitto_new(NULL,session,NULL);
if(!mosq){
printf("create client failed..\n");
mosquitto_lib_cleanup();
return 1;
}
mosquitto_log_callback_set(m_mosq, my_log_callback);
mosquitto_connect_callback_set(m_mosq, on_connect);
mosquitto_subscribe_callback_set(m_mosq, on_subscribe);
mosquitto_message_callback_set(m_mosq, on_message);
mosquitto_disconnect_callback_set(m_mosq, on_disconnect);
//连接服务器
if(mosquitto_connect_async(m_mosq, (char *)host_addra, port, keep_alive)!= MOSQ_ERR_SUCCESS){
fprintf(stderr, "Unable to connect.\n");
mosquitto_destroy(m_mosq);
mosquitto_lib_cleanup();
return 1;
}
//开启一个线程,在线程里不停的调用 mosquitto_loop() 来处理网络信息
int loop = mosquitto_loop_start(m_mosq);
if(loop != MOSQ_ERR_SUCCESS)
{
printf("mosquitto loop error\n");
mosquitto_destroy(m_mosq);
mosquitto_lib_cleanup();
return 1;
}
//销毁mosquitto环境
mosquitto_destroy(mosq);
mosquitto_lib_cleanup();
}
mosquitto如果需要启用websockets,则在配置文件中需要增加websockets监听端口,配置如下:
vi /usr/local/etc/mosquitto/mosquitto.conf
找到listeners节点,设置或修改如下(端口号可根据需要自定义):
listener 1883
protocol mqtt
listener 1884
protocol websockets
如果需要匿名登录进行消息的发送或接收,则设置如下:
allow_anonymous true
启动:
mosquitto -c /etc/mosquitto/mosquitto.conf -d -v
消息订阅和发布测试
//主题消息订阅
mosquitto_sub -t 'test/topic' -v
//主题消息发布
mosquitto_pub -t 'test/topic' -m 'hello world'
本文仅仅介绍了mosquitto要启用websockets模块时,如何在Linux环境下进行源代码的编译的过程,以及如何进行配置的过程,其中代码部分展示了在利用mosquitto提供的动态库时编写Mqtt客户端的主要逻辑。
下一篇介绍后端C语言中利用cJSON库进行MQTT中JSON格式内容消息的接收和发送。
如果您对物联网相关方面技术感兴趣,可进群交流,QQ群:541826239
前言阿里巴巴,作为国内互联网公司的Top,算是业界的标杆,有阿里背景的程序员,也更具有权威性。作为程序员,都清楚阿里对于员工要求有多高,技术人员掌握的技术水平更是望尘莫及。所以,大厂程序员的很多经验也都值得我们借鉴和学习,在一定程度上确实能够帮助我们“走捷径”。今天,我们要分享的是,Alibaba技术官丢出来的SpringCloud微服务实战笔记,这份笔记让人看了不得不爱,目前在GitHub的热度已经标星81.6k了,由此可见同行们对这份文档的认可程度,这也意味着对我们的学习和技术提升有很大的帮助。_字节高级java
工作中遇到的问题以前在jsp中引入一个静态页面用include<div id="div"> <c:if test="${item.guaranteeSlipId!=null}"> //判断值是否存在 <jsp:include page="../insuranceCardKind/riderList.jsp"> //路径 <
还是上图:_zookeeper分析调用链
随碟附送_撒打发手动阀打发
课件下载 : 方式1:本节课件下载地址:链接: https://pan.baidu.com/s/1DhCDxiPRSQw2vjowgjWSRQ 密码: x6pe方式2:或点击此处下载效果图:代码示例:1. 在sheet1中选择通用下拉列表中的WorkSheet 右侧选择BeforeSave,写入下列代码: 注意:确..._vba 备份第一个工作表数据
_config.xml这里首先要知道在 Hexo 中有两份主要的配置文件,其名称都是 _config.yml,它们均是用于站点配置使用的。其中,一份位于站点根目录下(比如我的:D:\h2pl.github.io_config.yml),主要包含 Hexo 本身整站的配置;另一份位于主题目录(D:\hexo\themes\icaurs_config.yml)下,这份配置由主题作者提供,主要用于配置...
MakeItTalk: Speaker-Aware Talking-Head Animation_现场演讲肖像:实时逼真的说话头动画 (yuanxunlu.github.io)
-- 查询数据表结构SELECTCONCAT(‘"e.‘,SUBSTRING(COLUMN_NAME,1),‘,"+‘),COLUMN_NAME,‘,‘,COLUMN_TYPE,column_commentFROMINFORMATION_SCHEMA.COLUMNSWHERE table_schema = ‘xcb‘and table_name = ‘t_product‘;-- 生成Java实体类..._mysql 查询生成实体
% 本程序主要用来计算根据灰色理论建立的模型的预测值。% 应用的数学模型是GM(1,1)。% 原始数据的处理方法是一次累加法。y=input('请输入数据');%输入数据请用如例所示形式:[48.7 57.17 68.76 92.15] n=length(y); yy=ones(n,1); yy(1)=y(1); for i=2:n yy(i)=yy(i-1)+y(i); end B..._灰度预测 gm(1,1) c语言
银行账目管理系统mysql数据库创建语句银行账目管理系统oracle数据库创建语句银行账目管理系统sqlserver数据库创建语句银行账目管理系统spring+springMVC+hibernate框架对象(javaBean,pojo)设计银行账目管理系统spring+springMVC+mybatis框架对象(javaBean,pojo)设计银行账目管理系统登录注册界面银行账目管理系..._做一个有注册页面的银行系统设计
Python 通过numpy库 求序列均值、标准差、中位数、分位数#导入包numpyimport numpy as np#序列例子aa = np.array([1,2,3,4,5,6,7])#求均值 np.mean:print(np.mean(aa))#求标准差 np.std:print(np.std(aa))#求中位数:print(np.percentile(aa,50))..._numpy 十分位数
单行文本截断.text-clip { width: 200px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }多行文本截断_css text clip