MQTT Security Fundamentals: Advanced Authentication Mechanisms

mqttsecurityfundamentals_part3

Last week, we explained the basics of authentication and how the MQTT protocol provides a username and password in the CONNECT message for authentication. This post introduces more ways to authenticate a client and shows you how to implement authentication on the MQTT broker.

Authentication with other information

In the last post, we learned that authentication confirms the identity of something or someone. We also saw how a username and password combination can be used for authentication.

In addition to the username and password, MQTT clients provide other information that can be used for authentication:

Client Identifier

Every MQTT client has a unique client identifier. The client provides this unique ID to the broker in the MQTT CONNECT message. The client ID can have a maximum of 65535 characters (the MQTT 3.1.1 specification removed the previous limit of 23 characters). It’s common practice to use the 36 character Universal Unique Identifier (UUID) or other unique client information as the client ID. For example, the MAC address of the network module or the device serial number. In the authentication process, client IDs are often used in combination with the username and password. A common way to confirm if a client can access the MQTT broker is to validate the username/password and the client ID that is correct for that credential combination. It is also possible to ignore the username/password and just authenticate against the client ID; however, this method is not a good security practice. (For some closed systems, this type of authentication may be sufficient).

X.509 Certificate

Another possible authentication method is using the X.509 client certificate. The client presents this certificate to the broker during the TLS handshake (we explain more about transport level security and how SSL/TLS works with MQTT in a later post). After a successful TLS handshake, some brokers such as HiveMQ permit use of certificate information for application layer authentication. This enables the broker to read all of the information in the certificate and use it for authentication purposes as well. If you provision IoT devices, X509 client certificates can be a very good source for authenticating clients on the MQTT broker.

Implementing Authentication with HiveMQ

We’ve seen that there are different types of information available for authentication of an MQTT client. Now, it’s time to wire the MQTT broker and the authentication store, which can be a database, a webservice, a LDAP directory or a simple access control list (ACL). Let’s take a look at how authentication logic can be implemented on the HiveMQ MQTT broker. The HiveMQ broker has an open source plugin system that allows you to hook into different events on the broker. HiveMQ offers various callback interfaces that are very easy to implement in custom plugins. The broker calls the plugin implementations at runtime. HiveMQ provides the OnAuthenticationCallback interface for authentication.

This callback implementation is sufficient for customizing the authentication mechanism to your use case. The callback method has one parameter of type ClientCredentialsData. This parameter contains all data that HiveMQ obtained from the connecting client. You can use this data to verify the client ID, username, password, and the certificate of the client. If the client presents valid information for authentication, this callback returns the value true.

There are two ways to decline authentication:

  • Returning the value false
  • Throwing an Exception

If the callback returns the value false, HiveMQ checks for other installed plugins and requests authentication from them. If one of these plugins returns the value true, HiveMQ authenticates the client. To prevent HiveMQ from checking other plugins and refuse the connection immediately, an exception must be thrown. In case of an exception, it is also possible to modify the CONNACK return code. We have an extensive example using a dummy implementation of username/password authentication on GitHub.

Callbacks must be registered with HiveMQ by adding them to the callback registry. This can be done easily in the main class of a plugin. The main class is required for each plugin and needs to extend the interface PluginEntryPoint. The callback is injected via dependency injection and added to the callback registry. Once the plugin is on the registry, it can be used with the HiveMQ broker.

You can find ready-to use, open-source, HiveMQ plugins for authenticating clients in our plugin directory. For example, the File Authentication Plugin for ACLs.

If you need more information about how to develop, run, and deploy a custom authentication plugin for the HiveMQ broker, see the plugin developer guide.

This brings us to the end of the authentication part of MQTT Security Fundamentals. In the next post, we dive into topic-level authorization with MQTT.

We hope you enjoyed part three of the MQTT Security Fundamentals series. If you want us to notify you as soon as we publish the next post, subscribe to our newsletter or RSS feed. To give us feedback or request more information, feel free to use the comments section. We are always open to questions and suggestions.

7 comments

  1. manunited says:

    hi.
    thank you very much
    but “ClientCredentialsData” and “ClientData” Links are not valid.
    please correct it.
    best regards

    1. Hi there,

      Thank you for pointing this out.
      Fixed it.

      Best regards,
      Florian from The HiveMQ Team.

  2. NuB2Hive says:

    Question on certificate. When you say “it allows you to check client id, username, password and the certificate”, are you assuming the certificate information is being extracted from the TLS level by HiveMQ broker? The client somehow tells it to use that? Or perhaps the plug-in requiring it makes HiveMQ get it (assuming it was used for mutual TLS at transport?) . Thanks.

    1. Hi there,

      the getCertificate() method will return an Optional of the client certificate, if there is a client certificate was used.
      HiveMQ will add this information to the ClientData after the connection was established.
      When there was no client certificate used during the connection, this method will return Optonal.absent().
      Keep in mind that the checks you can do on the plugin at this point, have nothing to do with the TLS validation.
      I hope this answers your question.

      Kind regards,
      Florian from the HiveMQ Team.

  3. NuB2Hive says:

    It does Florian, thanks. Ravi

  4. gmlan says:

    Suppose I have a MQTT client, Pseudo Code:
    MQTTClient client = new xxx();
    client.connect();
    client.subscribe();

    Question: since client send two requests here, how many time that AuthWithUsernamePasswordCallback.checkCredential() are called? and why?

    1. Hi there,

      nice to see your interest in the security aspects of MQTT and HiveMQ.
      Authentication happens during the connection establishment. So in your example the Callback will be called once, as it is called each time a client establishes a connection.

      I hope this helps.
      Kind regards,
      Florian from the HiveMQ Team.

Leave a Reply

Your email address will not be published. Required fields are marked *