C# Mqtt Client

In this topic I will be sending data from a C# client using a highly volatile protocol to any other client that might be interested in this data. This concept is also called pub/sub or the publish subsrcibe pattern. We need a few components to make this possible:

  • C# client
  • A messaging protocol (used by the client software to either publish or subscribe)
  • A broker (for managing the pub/sub data flows). For more information goto this topic

The C# client

C♯ is one of the programming languages designed for the Common Language Infrastructure. C# is built on the syntax and semantics of C++, allowing C programmers to take advantage of .NET and the common language runtime. For more information: wikipedia.

The protocol

MQTT is a machine-to-machine (M2M)/”Internet of Things” connectivity protocol. It was designed as an extremely lightweight publish/subscribe messaging transport. It is useful for connections with remote locations where a small code footprint is required and/or network bandwidth is at a premium. For more information: http://mqtt.org/.

What is happening?

C# 1

This is sample client based upon the .NET class M2MQTT. It is a simple client that connects to a Mosquitto broker, subscribes to a topic and published a text to the same topic.

C# 2

Connecting to the broker

C# 3

Publishing the text

And hereby the code:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Net;
using System.Windows.Forms;
using uPLibrary.Networking.M2Mqtt;
using uPLibrary.Networking.M2Mqtt.Messages;

namespace MQTTHandler
{
  public partial class MainForm : Form
  {
    MqttClient clientSub;
    delegate void SetTextCallback(string text);

    public MainForm()
    {
      InitializeComponent();
    }

    private void MainForm_Load(object sender, EventArgs e)
    {
      try
      {
        IPAddress HostIP;
        HostIP = IPAddress.Parse(TextBox1.Text);
        clientSub = new MqttClient(HostIP);
        clientSub.MqttMsgPublishReceived += new MqttClient.MqttMsgPublishEventHandler(EventPublished);
      }
        catch (InvalidCastException ex)
        {
        }
      }

      private void EventPublished(Object sender,uPLibrary.Networking.M2Mqtt.Messages.MqttMsgPublishEventArgs e)
      {
        try
        {
          SetText("*** Received Message");
          SetText("*** Topic: " + e.Topic);
          SetText("*** Message: " + System.Text.UTF8Encoding.UTF8.GetString(e.Message));
          SetText("");
        }
        catch (InvalidCastException ex)
        {
        }
      }

      private void SetText(string text)
      {
        if (this.ListBox1.InvokeRequired)
        {
          SetTextCallback d = new SetTextCallback(SetText);
          this.Invoke(d, new object[] { text });
        }
        else
        {
          this.ListBox1.Items.Add(text);
        }
      }

      private void Button1_Click(object sender, EventArgs e)
      {
        try
        {
          clientSub.Connect(TextBox2.Text + "_sub");
          ListBox1.Items.Add("* Client connected");
          clientSub.Subscribe(new string[] { TextBox3.Text }, new byte[] { MqttMsgBase.QOS_LEVEL_EXACTLY_ONCE });
          ListBox1.Items.Add("** Subscribing to: " + TextBox3.Text);
        }
        catch (InvalidCastException ex)
        {
        }
      }

      private void Button2_Click(object sender, EventArgs e)
      {
        try
        {
          clientSub.Publish(TextBox3.Text, Encoding.UTF8.GetBytes(TextBox4.Text), MqttMsgBase.QOS_LEVEL_EXACTLY_ONCE);
          ListBox1.Items.Add("*** Publishing on: " + TextBox3.Text);
        }
        catch (InvalidCastException ex)
        {
        }
      }

      private void Button3_Click(object sender, EventArgs e)
      {
        try
        {
          clientSub.Disconnect();
          ListBox1.Items.Add("* Client disconnected");
        }
        catch (InvalidCastException ex)
        {
        } 
      }
    }
  }
}

There was one small issue: Thread-Safe Calls to Windows Forms Controls. For more information: MSDN. Basically due to subscribing to the topic, the subscription event will try to write to the listbox (used to display the log results) but from a different thread than the Windows form is running on. To solve this I used:

delegate void SetTextCallback(string text);

And this procedure to update the listbox:

private void SetText(string text)
{
  if (this.ListBox1.InvokeRequired)
  {
    SetTextCallback d = new SetTextCallback(SetText);
    this.Invoke(d, new object[] { text });
  }
  else
  {
    this.ListBox1.Items.Add(text);
  }
}

One thought on “C# Mqtt Client

  1. Thank you very much for such a nice tutorial for understanding MQTT Protocol.

Leave a Reply to Android Development Blog Cancel reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s