p.p1 { margin: 0.0px 0.0px 0.0px 0.0px; font: 16.0px “PingFang SC” }
p.p2 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “PingFang SC”; color: #000000; background-color: rgba(0, 0, 0, 0) }
p.p3 { margin: 0.0px 0.0px 0.0px 0.0px; font: 16.0px “PingFang SC”; min-height: 22.0px }
p.p4 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “.PingFang SC”; color: #000000 }
p.p5 { margin: 0.0px 0.0px 0.0px 0.0px; line-height: 18.0px; font: 14.0px “PingFang SC”; color: #000000; background-color: rgba(0, 0, 0, 0) }
p.p6 { margin: 0.0px 0.0px 0.0px 0.0px; line-height: 14.0px; font: 14.0px “PingFang SC”; color: #000000; background-color: rgba(0, 0, 0, 0) }
p.p7 { margin: 0.0px 0.0px 0.0px 0.0px; font: 16.0px “PingFang SC”; color: #000000; background-color: rgba(0, 0, 0, 0); min-height: 22.0px }
p.p8 { margin: 0.0px 0.0px 0.0px 0.0px; font: 16.0px “PingFang SC”; color: #000000; background-color: rgba(0, 0, 0, 0) }
p.p9 { margin: 0.0px 0.0px 0.0px 0.0px; line-height: 14.0px; font: 14.0px “PingFang SC”; color: #000000; background-color: rgba(0, 0, 0, 0); min-height: 20.0px }
p.p10 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “PingFang SC”; color: #000000; background-color: rgba(0, 0, 0, 0); min-height: 20.0px }
p.p11 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “PingFang SC”; color: #3c828b; background-color: rgba(0, 0, 0, 0) }
p.p12 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “PingFang SC”; color: #c81b13; background-color: rgba(0, 0, 0, 0) }
p.p13 { margin: 0.0px 0.0px 0.0px 0.0px; font: 18.0px Menlo; color: #3e1e81; background-color: rgba(0, 0, 0, 0) }
p.p14 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “PingFang SC”; color: #1e9421; background-color: rgba(0, 0, 0, 0) }
p.p15 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “PingFang SC”; color: #31595d; background-color: rgba(0, 0, 0, 0) }
p.p16 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “PingFang SC”; color: #294c50; background-color: rgba(0, 0, 0, 0) }
p.p17 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “PingFang SC”; background-color: rgba(0, 0, 0, 0); min-height: 20.0px }
p.p18 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px “PingFang SC”; color: #3e1e81; background-color: rgba(0, 0, 0, 0) }
span.s1 { }
span.s2 { font: 14.0px “PingFang SC”; background-color: rgba(0, 0, 0, 0) }
span.s3 { font: 14.0px “PingFang SC”; background-color: rgba(0, 0, 0, 0) }
span.s4 { background-color: rgba(0, 0, 0, 0) }
span.s5 { color: #000000 }
span.s6 { color: #3e1e81 }
span.s7 { color: #539aa4 }
span.s8 { color: #c81b13 }
span.s9 { color: #294c50 }
span.s10 { color: #c42275 }
span.s11 { color: #0435ff }
span.s12 { color: #1e9421 }
span.s13 { color: #31595d }
span.s14 { color: #6122ae }
span.s15 { color: #703daa }
span.s16 { color: #3c828b }
一、协议简介:
1、MQTT(Message Queuing Telemetry Transport,消息队列遥测传输)是IBM开发的一个即时通讯协议,有可能成为物联网的重要组成部分。该协议支持所有平台,几乎可以把所有联网物品和外部连接起来,被用来当做传感器和致动器。
二、协议特点:
1、MQTT是为大量计算能力有限,且工作在低带宽、不可靠的网络的远程传感器和嵌入式控制设备通讯而设计的协议,它具有以下主要的几项特性:
1》、使用发布/订阅消息模式,提供一对多的消息发布,解除应用程序耦合;
2》、对负载内容屏蔽的消息传输;
3》、使用 TCP/IP 提供网络连接;
4》、有三种消息QoS发布服务质量;
A、“至多一次”,消息发布完全依赖底层 TCP/IP 网络。会发生消息丢失或重复。这一级别可用于如下情况,环境传感器数据,丢失一次读记录无所谓,因为不久后还会有第二次发送。
B、“至少一次”,确保消息到达,但消息重复可能会发生。
C、“只有一次”,确保消息到达一次。这一级别可用于如下情况,在计费系统中,消息重复或丢失会导致不正确的结果。
5、小型传输,使用很小(固定长度的头部是2字节),协议交换最小化,以降低网络流量;
6、使用 Last Will 和 Testament 特性通知有关各方客户端异常中断的机制。
三、协议应用场景:
1、移动消息、物联网、车联网、智能硬件甚至能源勘探等
2、设计模式支持:1个字节报头、2个字节心跳、消息QoS
四、使用MQTT协议集成iOS客户端步骤:
1、github上搜索资料MQTT并下载,会出现两个(建议使用第二个):
A、MQTTKit:停止更新 下载地址:https://github.com/mobile-web-messaging/MQTTKit
B、MQTTClient:经常更新 下载地址:https://github.com/novastone-media/MQTT-Client-Framework
2、导入MQTT和SocketRocket两个框架到工程,如果遇到编译报错”_utf8_nextCharSafeBody”, referenced from:,记得添加系统依赖库libicucore.tbd
3、创建传输类型
MQTTCFSocketTransport* transport=[[MQTTCFSocketTransport alloc]init];
transport.host=@”192.168.1.1″;
transport.port=[@”8080″ intValue];
4、创建会话任务并设置代理
MQTTSession* session=[[MQTTSession alloc]init];
session.delegate=self;
session.transport=transport;
session.userName=@”peter”;
session.password=@”123456″;
5、订阅主题
BOOL isSucess = [session connectAndWaitTimeout:30];//连接会话, 设置超时时间
if(isSucess){
[session subscribeToTopic:nil atLevel:MQTTQosLevelAtMostOnce subscribeHandler:^(NSError *error, NSArray<NSNumber *> *gQoss) {
if (error) {
NSLog(@”连接失败:%@”,error.localizedDescription);
}else{
NSLog(@”连接成功:%@”,gQoss);
}
}];
}
5、KVO监听状态
[self.session addObserver:self forKeyPath:@”ststus” options:NSKeyValueObservingOptionOld context:nil];
-(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary<NSKeyValueChangeKey,id> *)change context:(void *)context{
//正在断开连接
if (self.session.status==MQTTSessionStatusDisconnecting) {
[self.session connect];//重新连接
}
}
6、发送数据
– (void)sending:(MQTTSession *)session type:(MQTTCommandType)type qos:(MQTTQosLevel)qos retained:(BOOL)retained duped:(BOOL)duped mid:(UInt16)mid data:(NSData *)data{
[session publishAndWaitData:data
onTopic:@”topic”
retain:NO
qos:MQTTQosLevelAtLeastOnce];
}
7、接收数据
-(void)newMessage:(MQTTSession *)session data:(NSData *)data onTopic:(NSString *)topic qos:(MQTTQosLevel)qos retained:(BOOL)retained mid:(unsigned int)mid{
NSDictionary* dict=[NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
self.dataDict=dict;//保存全局属性
if ([topic rangeOfString:@”device_control”].location!=NSNotFound) {
//控制设备
}
}
8、断开服务连接
– (void)connectionClosed:(MQTTSession *)session{
[session disconnect];//断开
[session close];//关闭
}
9、取消订阅服务
– (void)unsubAckReceived:(MQTTSession *)session msgID:(UInt16)msgID{
[session unsubscribeTopic:@”topic” unsubscribeHandler:^(NSError *error) {
}];
}