在《MQTT服务器Mosquitto 2.x编译安装配置》
https://zhuanlan.zhihu.com/p/365103802
https://blog.csdn.net/chentuo2000/article/details/115731687
一文中我们下载了最新的mosquitto源码进行了编译安装。
在下载的源码中有几个C语言的例子可以参考:
这些例子在github上也可以找到:
https://github.com/eclipse/mosquitto/tree/master/examples
下面我们看例子subscribe。
2. 查看例子subscribe
- 查看temperature_conversion目录
ls -l mosquitto-2.0.9/examples/subscribe/
- 查看C源文件basic-1.c
cat mosquitto-2.0.9/examples/subscribe/basic-1.c
下面对注释进行了翻译。
-
/_
-
_ This example shows how to write a client that subscribes to a topic and does
-
_ not do anything other than handle the messages that are received.
-
这个例子示范了怎样写一个客户端订阅一个主题,对收到的消息不做任何其他处理。
-
_/
-
-
-
-
-
-
-
-
-
/_ Callback called when the client receives a CONNACK message from the broker. _/
-
/_ 当客户端从代理接收到CONNACK消息时调用回调。 _/
-
void on_connect(struct mosquitto _mosq, void _obj, int reason_code)
-
{
-
int rc;
-
/_ Print out the connection result. mosquitto_connack_string() produces an
-
_ appropriate string for MQTT v3.x clients, the equivalent for MQTT v5.0
-
_ clients is mosquitto_reason_string().
-
打印连接结果。mosquitto_connack_string()为mqttv3.x客户端生成适当的字符串,与
-
mqttv5.0客户端等效的是mosquitto_reason_string()。
-
_/
-
printf(“on_connect: %s\n”, mosquitto_connack_string(reason_code));
-
if(reason_code != 0){
-
/_ If the connection fails for any reason, we don’t want to keep on
-
_ retrying in this example, so disconnect. Without this, the client
-
_ will attempt to reconnect.
-
如果由于任何原因连接失败,在本例中我们不想继续重试,所以断开连接。否则,客户端将尝
-
试重新连接。
-
_/
-
mosquitto_disconnect(mosq);
-
}
-
-
/_ Making subscriptions in the on_connect() callback means that if the
-
_ connection drops and is automatically resumed by the client, then the
-
_ subscriptions will be recreated when the client reconnects.
-
在on_connect()回调中进行订阅意味着如果连接断开并由客户端自动恢复,则在客户端重新连接时将重
-
新创建订阅。
-
_/
-
rc = mosquitto_subscribe(mosq, NULL, “example/temperature”, 1);
-
if(rc != MOSQ_ERR_SUCCESS){
-
fprintf(stderr, “Error subscribing: %s\n”, mosquitto_strerror(rc));
-
/_ We might as well disconnect if we were unable to subscribe _/
-
/_ 如果无法订阅,我们应该断开连接。 _/
-
mosquitto_disconnect(mosq);
-
}
-
}
-
-
-
/_ Callback called when the broker sends a SUBACK in response to a SUBSCRIBE. _/
-
/_ 当代理在响应订阅发送SUBACK时调用回调。 _/
-
void on_subscribe(struct mosquitto _mosq, void _obj, int mid, int qos_count, const int _granted_qos)
-
{
-
int i;
-
bool have_subscription = false;
-
-
/_ In this example we only subscribe to a single topic at once, but a
-
_ SUBSCRIBE can contain many topics at once, so this is one way to check
-
_ them all.
-
在本例中,我们一次只订阅一个主题,但是订阅可以一次包含多个主题,因此这是检查所有主题的一种方
-
法。
-
_/
-
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){
-
/_ The broker rejected all of our subscriptions, we know we only sent
-
_ the one SUBSCRIBE, so there is no point remaining connected.
-
代理拒绝了我们所有的订阅,我们知道我们只发送了一个订阅,所以没有保持连接的点。
-
_/
-
fprintf(stderr, “Error: All subscriptions rejected.\n”);
-
mosquitto_disconnect(mosq);
-
}
-
}
-
-
-
/_ Callback called when the client receives a message. _/
-
/_ 当客户端收到消息时调用回调。 _/
-
void on_message(struct mosquitto _mosq, void _obj, const struct mosquitto_message _msg)
-
{
-
/_ This blindly prints the payload, but the payload can be anything so take care.
-
这会盲目地打印有效负载,但是有效负载可以是任何东西,所以请小心。
-
_/
-
printf(“%s %d %s\n”, msg->topic, msg->qos, (char _)msg->payload);
-
}
-
-
-
int main(int argc, char *argv[])
-
{
-
struct <span class=”hljs-title class_“>mosquitto _mosq;
-
int rc;
-
-
/_ Required before calling other mosquitto functions _/
-
/_ 调用其他mosquitto函数之前需要初始化 _/
-
mosquitto_lib_init();
-
-
/_ Create a new client instance.
-
_ id = NULL -> ask the broker to generate a client id for us
-
_ clean session = true -> the broker should remove old sessions when we connect
-
_ obj = NULL -> we aren’t passing any of our private data for callbacks
-
-
创建新的客户端实例。
-
id = NULL -> ask 代理为我们生成一个客户id
-
clean session = true -> 当我们连接时,代理将删除旧会话
-
obj = NULL -> 我们没有为回调传递任何私有数据
-
_/
-
mosq = mosquitto_new(NULL, true, NULL);
-
if(mosq == NULL){
-
fprintf(stderr, “Error: Out of memory.\n”);
-
return 1;
-
}
-
-
/_ Configure callbacks. This should be done before connecting ideally. _/
-
/_ 配置回调,这应该在连接之前完成。 _/
-
mosquitto_connect_callback_set(mosq, on_connect);
-
mosquitto_subscribe_callback_set(mosq, on_subscribe);
-
mosquitto_message_callback_set(mosq, on_message);
-
-
/_ Connect to test.mosquitto.org on port 1883, with a keepalive of 60 seconds.
-
_ This call makes the socket connection only, it does not complete the MQTT
-
_ CONNECT/CONNACK flow, you should use mosquitto_loop_start() or
-
_ mosquitto_loop_forever() for processing net traffic.
-
将端口1883连接test.mosquitto.org,心跳时间间隔60秒。
-
此调用仅使套接字连接,它不完成MQTT CONNECT/CONNACK流,应该使用
-
mosquitto_loop_star()或mosquitto_loop_forever()来处理网络流量。
-
_/
-
rc = mosquitto_connect(mosq, “test.mosquitto.org”, 1883, 60);
-
if(rc != MOSQ_ERR_SUCCESS){
-
mosquitto_destroy(mosq);
-
fprintf(stderr, “Error: %s\n”, mosquitto_strerror(rc));
-
return 1;
-
}
-
-
/_ Run the network loop in a blocking call. The only thing we do in this
-
_ example is to print incoming messages, so a blocking call here is fine.
-
_
-
_ This call will continue forever, carrying automatic reconnections if
-
_ necessary, until the user calls mosquitto_disconnect().
-
在阻塞调用中运行网络循环。在这个例子中,我们所做的唯一一件事就是打印传入的消息,所以这里的阻
-
塞调用是可以的。
-
如果需要此调用将一直持续,直到用户调用mosquitto\u disconnect()。
-
*/
-
mosquitto_loop_forever(mosq, -1, 1);
-
-
mosquitto_lib_cleanup();
-
return 0;
-
}
说明:
这个例子示范了怎样写一个客户端订阅一个主题,对收到的消息不做任何其他处理。
3. 编译例子subscribe
3.1 头文件和库文件
- 头文件
ls -l /usr/local/include/mosquitto.h
- 库文件
ls -l /usr/local/lib/libmosquitto.so.1
有关API的详细说明见:
https://mosquitto.org/api/files/mosquitto-h.html#mosquitto_connect
3.2 修改例子
- 设置Username和password
在rc = mosquitto_connect(mosq, “test.mosquitto.org”, 1883, 60);
前面添加一句,用来设置Username和password:
mosquitto_username_pw_set(mosq, “ct”, “1qaz2wsx”);
- 设置我的服务器
将rc = mosquitto_connect(mosq, “test.mosquitto.org”, 1883, 60);
中的test.mosquitto.org改成raspberrypi。
- 编辑basic-1.c
进入例子目录:
cd mosquitto-2.0.9/examples/subscribe/
nano basic-1.c
3.3 编译
- 编译
gcc -o basic-1 basic-1.c -lmosquitto
3.4 测试
- 运行basic-1
./basic-1
从rc = mosquitto_subscribe(mosq, NULL, “example/temperature”, 1);可知,订阅的消息主题为example/temperature。
- 再开一个窗口发布消息
mosquitto_pub -p 1883 -u ct -P xxxxxxxx -t example/temperature -m “26.6”
- 订阅测试窗口收到消息
- 用MQTT.fx远程测试
详细说明见《树莓派MQTT服务远程测试MQTT.fx》
https://zhuanlan.zhihu.com/p/363373024
https://blog.csdn.net/chentuo2000/article/details/115539377
点击Publish:
订阅测试窗口收到消息
评论(0)
您还未登录,请登录后发表或查看评论