C#应用:MQTT分析——CONNECT为例子
源代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Net.Sockets;
namespace ConsoleApp1
{
class Program
{
static void Main(string[] args)
{
Connect();
}
/// <summary>
/// 向服务器端发送请求,使用socket连接请求
/// </summary>
static void Connect()
{
Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
socket.Connect("127.0.0.1", 1883);//TCP三次握手
//发送MQTT的登录请求
//固定报头
//第一个字节8个位,(消息类型4个位,DUP位1个位,Qos2个位,Retain1个位)
//请求,根据固定报文控制类型,第一个请求为 00010000,表示从客户端到服务器
List<byte> list = new List<byte>();
list.Add(0x10);
//===========可变报头+载荷部分==============
List<byte> list2 = new List<byte>();
//可变报头由以下组成:协议名(MQTT)+协议级别+连接标志+保持连接
string protocolName = "MQTT";
byte[] probyet = Encoding.UTF8.GetBytes(protocolName);//MQTT对应的ascii码的十六进制
//协议长度
list2.Add((byte)(probyet.Length / 256 % 256));
list2.Add((byte)(probyet.Length % 256));
list2.AddRange(probyet);//协议名称
list2.Add(0x04);//协议级别,只能是0x04
//连接标志 一个字节(8位)
//11000010
byte flag = 0; //0000 0000
flag |= 128; //1000 0000
//flag |=128 ==> 1000 0000或运算
flag |= 64; //0100 0000
//flag |=64 ==>//1100 0000或运算
flag |= 2; //0000 0010
//flag |=2 ==>//1100 0010
list2.Add(flag);
//keep alive保持连接
int second = 100; //保持100秒,持续到150秒
list2.Add((byte)(second / 256 % 256));
list2.Add((byte)(second % 256));
//有效载荷(客户端标识符,遗嘱主题,遗嘱消息,用户名,密码)
string clientStr = "JTVL";
byte[] idBytes = Encoding.UTF8.GetBytes(clientStr); //ID的字节数组
int idBytesLen = idBytes.Length; //ID字节数组的长度
list2.Add((byte)(idBytes.Length / 256 % 256));
list2.Add((byte)(idBytesLen % 256));
list2.AddRange(idBytes); //添加ID字节数组
//UserName
string userName = "JT";
byte[] nameByte = Encoding.UTF8.GetBytes(userName);
list2.Add((byte)(nameByte.Length / 256 % 256));
list2.Add((byte)(nameByte.Length % 256));
list2.AddRange(nameByte);
//Password
string passWord = "123";
byte[] passByte = Encoding.UTF8.GetBytes(passWord);
list2.Add((byte)(passByte.Length / 256 % 256));
list2.Add((byte)(passByte.Length % 256));
list2.AddRange(passByte);
//把可变报头+载荷部分加到固定报头的后面
//添加固定报头的第二个字节
list.Add((byte)(list2.Count));
//添加
list.AddRange(list2);
//发送连接请求报文
socket.Send(list.ToArray());
}
}
}
一、知识基础
1、C#的byte类型
在C#中,byte类型表示一个8位无符号整数(也称为字节)。由于它是无符号的,它的值范围是0到255,即 1111 1111
2、BitConverter.GetBytes
BitConverter.GetBytes(int) 的返回值为 byte数组 ,但是创建的数组容量为4个,如果不够会依次增加4个,返回的顺序是顺序。即:如果是 256 ,则为 1 0000 0000 ,也就是第二个数组的值为1,第一个数组为0 ,而第三和第四为0;如果是 1 ,则为 0000 0001 ,第二第三第四值为0。<