Sign inSign up

iotechsys/sparkplug-client

By iotechsys

•Updated 6 months ago

Sparkplug client functionality (publisher and subscriber)

Image
Developer tools
0

8.2K

iotechsys/sparkplug-client repository overview

⁠Sparkplug Client

⁠Overview

This is a utilty for debugging Sparkplug⁠ messages that are encoded using GPB (Google Protocol Buffers)⁠.

The docker container has two modes: 'pub'(publish) and 'sub'(subscribe).

When in subscribe mode, the docker container subscribes to a given MQTT⁠ topic, attempting to decode any messages it receives on this topic before printing them to the console (or a file see usage⁠).

When in publish mode, the docker container will parse the given message (see usage⁠) before encoding it and publishing it on the given topic.

For both encoding and decoding, all messages are expected to follow the Sparkplug B specification which can be found in section 6.4 in the this document⁠.

⁠Getting Started

⁠Prerequisites

An MQTT Broker is required to use this image.

⁠Usage

This code is intended to be used as a docker container which can be pulled using:

docker pull iotechsys/sparkplug-client
⁠Publish mode

The container can be used to publish an encoded message with:

docker run --rm --network host iotechsys/sparkplug-client pub -h <YourMQTTHostIP> -t <YourTopic> -m <YourMessageToBeEncoded>

Where

  • YourMQTTHostIP is the IP address of the MQTT broker, usually "localhost"
  • *YourTopic is the MQTT topic you wish to publish to
  • YourMessageToBeEncoded is a json representation of the message, for example: '{ "metrics":[ { "name": "Node Control/LogLevel", "datatype": 7, "value": 5 } ] }'

There are a variety of flags available for use in publish mode. These can be found in section Flags⁠.

⁠Subscribe Mode

The container can be used to subscribe to a topic and decode the messages with:

docker run --rm --network host iotechsys/sparkplug-client sub -h <YourMQTTHostIP> -t <YourTopic> 

Where

  • YourMQTTHostIP is the IP address of the MQTT broker, usually the same as the host PC
  • YourTopic is the MQTT topic you wish to subscribe to, this supports wildcards

Outputting to a file is also supported.

This is controlled via the -f flag, which should be supplied along with a path to the file.

In order to output the decoded messages a volume has to be mounted to share the files generated within the container with the host environment.

This can be done as follows:

mkdir volume
docker run --rm --network host -v ${PWD}/volume:/volume iotechsys/sparkplug-client sub -f /volume/output_file.json -t spBv1.0/# -v --indent

This will instruct the container to write all received messages to _/volume/output_file.json.

There are a variety of flags available for use in subscribe mode. These can be found in section Flags⁠.

⁠Web UI Mode

The Sparkplug Client includes a built-in Web UI for visualising MQTT messages in real-time through a browser interface. To enable the Web UI, use the --webui flag in subscribe mode:

docker run --rm --network host iotechsys/sparkplug-client sub --webui -h <YourMQTTHostIP> -t <YourTopic>

This starts the Web UI server on port 8080 by default. Access the interface at http://localhost:8080⁠

To use a different port, add the --webui-port flag:

docker run --rm --network host iotechsys/sparkplug-client sub --webui --webui-port 9090 -h localhost -t "spBv1.0/#"

The Web UI provides real-time visualisation of decoded Sparkplug messages and runs alongside console output (unless --quiet is used).

⁠Usage without datatypes

This client has some limitations when handling messages that are missing datatypes such as DDATA and NDATA messages.

This is due to the Sparkplug specification utilising generic Protobuf types for several Sparkplug datatypes.

This means that types such as Int8 (1) and Int32 (3) are encoded over the wire as uint32s and the client is unaware as to their original datatypes of the metric.

For these ambiguous metrics, the client will print them using their Protobuf Value Names, for example the following message: { "metrics": [ { "name": "Int8 Metric (Datatype 1)", "value": -4 }, { "name": "UInt64 Metric (Datatype 8)", "value": 4 }, { "name": "String Metric (Datatype 12)", "value": "Test String" }, { "name": "UInt8 Array (Datatype 26)", "value": [3, 4] } ] }

would be printed as: { "metrics": [ { "name": "Int8 Metric (Datatype 1)", "int_value": 4294967292 }, { "name": "UInt64 Metric (Datatype 8)", "long_value": 4 }, { "name": "String Metric (Datatype 12)", "value": "Test String" } { "name": "UInt8 Array (Datatype 26)", "bytes_value":"AwQ=" } ] }

Notice that the String Metric is a non-ambiguous type and as such will not use Protobuf naming despite having no datatype.

Please find below a reference for all ambiguous types and their value names:

Sparkplug DatatypeProtobuf Value StringProtobuf Datatype
Int8 (1)int_valueuint32
Int16 (2)int_valueuint32
Int32 (3)int_valueuint32
Int64 (4)long_valueuint64
UInt8 (5)int_valueuint32
UInt16 (6)int_valueuint32
UInt32 (7)int_valueuint32
UInt64 (8)long_valueuint64
Bytes (17)bytes_valuebytes
File (18)bytes_valuebytes
Int8Array (22)bytes_valuebytes
Int16Array (23)bytes_valuebytes
Int32Array (24)bytes_valuebytes
Int64Array (25)bytes_valuebytes
UInt8Array (26)bytes_valuebytes
UInt16Array (27)bytes_valuebytes
UInt32Array (28)bytes_valuebytes
UInt46Array (29)bytes_valuebytes
FloatArray (30)bytes_valuebytes
DoubleArray (31)bytes_valuebytes
BooleanArray (32)bytes_valuebytes
StringArray (33)bytes_valuebytes

For more detail on the array types, please refer to the Sparkplug B Specification that outlines how these are encoded on the wire.

⁠Flags

There are many flags which can be configured for your needs.

These can be viewed using:

docker run --rm --network host iotechsys/sparkplug-client --help

You can set as many of these flags as you wish in any order, for example:

docker run --rm --network host iotechsys/sparkplug-client sub -P user1password -u user1 -t another/topic/# -p 8883

Below you will find all flags that can be configured for this client

⁠File [Pub and Sub Mode]

The file flag can be used to specify a file to send in the case of pub mode, or to specify a file to write received messages to in the case of sub mode.

In order to share the file a volume has to be mounted to allow the container to access the file on the host machine.

This can be done as follows for pub mode:

docker run --rm --network host -v ${PWD}/volume:/volume iotechsys/sparkplug-client pub -f /volume/message.txt   

Where ${PWD}/volume/message.txt contains the json representation of the desired message.

And in sub mode:

docker run --rm --network host -v ${PWD}/volume:/volume iotechsys/sparkplug-client sub -f /volume/messages.txt   

Where all messages received will be written to ${PWD}/volume/messages.txt

⁠Repeated publishing [Pub Mode Only]

The client can also repeatedly publish the same message

The basic --repeat flag can be used to specify the number of times the message is sent, with --repeat-delay specifying the time in milliseconds between repeats

So the following would send the message 3 times, with 1000ms between each repeat:

docker run --rm --network host iotechsys/sparkplug-client pub -m '{"metrics":[{"datatype":6,"name":"Current","value":6}]}' --repeat 3 --repeat-delay 1000

The --repeat flag can also be combined with --auto-increment-initial and --auto-increment-value in order to send a changing value with each repeat where --auto-increment-initial specifies the value to start on, and --auto-increment-value specifies the incremental value.

The string "AUTO_INCREMENT" (including quotes) needs then be placed in the message where the value should be substituted.

For example:

docker run --rm --network host iotechsys/sparkplug-client pub -m '{"metrics":[{"datatype":6,"name":"Current","value":"AUTO_INCREMENT"}]}' --repeat 3 --repeat-delay 1000 --auto-increment-initial 15 --auto-increment-value 3

Would send:

{"metrics":[{"datatype":6,"name":"Current","value":15}]}
{"metrics":[{"datatype":6,"name":"Current","value":18}]}
{"metrics":[{"datatype":6,"name":"Current","value":21}]}
⁠Excluding Topics [Sub Mode Only]

Exclusion of messages published on certain topics is another feature available when in subscribe mode.

This is controlled with the -et flag

For example:

docker run --rm --network host iotechsys/sparkplug-client sub -t "spBv1.0/#" -et "DBIRTH"

Would exclude any message received from a topic that included "DBIRTH", all other messages would be printed as normal.

⁠Full Flag List
FlagDefaultModeDescription
-h"127.0.0.1"[pub or sub]MQTT Broker Host Address
-p"1883"[pub or sub]MQTT Broker Port
-t"spBv1.0/#"[pub or sub]MQTT topic, default not applicable in pub mode (# can be used as wild card in sub mode)
-f""[pub or sub]File containing message in json to encode and publish, or file in which to write received messages
-u""[pub or sub]MQTT Broker username
-P""[pub or sub]MQTT Broker password
-q0[pub or sub]Quality of Service level to use (0 to 3)
-repeat1[pub]Client will send the given message this many times
-repeat-delay0[pub]If using --repeat, client will wait this many milliseconds between publishes
-msg-count0[sub]Client will disconnect after receiving this many messages (0 means receive messages indefinitely)
-vfalse[sub]Prints the topic the message was received on as well as the message
-et""[sub]Rejects messages from topics that are published on topics that contain the passed in string
-quietfalse[sub]Messages will not be printed
-print-timingsfalse[sub]If using --msg-count, print the time of receipt of the first message and the time of program termination
-m""[pub]Message in json to encode and publish, must follow Sparkplug Specification
-auto-increment-initial0.0[pub]If using --repeat, string "AUTO_INCREMENT" in message will be replaced with a value that is incremented by auto-increment-value (defaults to 1) each repeat starting at the given value
-auto-increment-value1.0[pub]If using --repeat and --auto-increment-initial, the "AUTO_INCREMENT" value will be incremented by this value
-connection-retry-interval100[pub or sub]Sets the connection retry interval in milliseconds if the client is unable to connect to the broker
-indentfalse[sub]Prints the message as indented json
-webuifalse[pub or sub]Enable web UI (Default port 8080)
-webui-port8080[pub or sub]Run the web UI on a different port
⁠Object Type Support

The Sparkplug Specification does not presently have any support for objects. Because of this IOTech Systems Edge Connect enables sending of objects as JSON strings under the Text Datatype (Represented by value 14)

An example message that the client could send is should below: { "metrics": [ { "datatype": 14, "name": "Object Metric", "value": { "number": 4, "object": { "number2": 1, "string": "Example String" } } } ] }

which would then be received and printed as shown: { "metrics": [ { "datatype": 14, "name": "Object Metric", "value": "{"number":4,"object":{"number2":1,"string":"Example String"}}" } ] }

Worth noting, is that this object support does not prevent sending of regular strings in datatype 14, this will be handled as expected.

⁠Known Issues

This client does not currently support certain datatypes. These are:

  • Datasets (16)
  • Templates (19)
  • Datetime Array (34)

This client also does not currently support the publishing of messages that do not contain all datatypes.

Tag summary

Content type

Image

Digest

sha256:ce1b0e794…

Size

8.9 MB

Last updated

over 2 years ago

docker pull iotechsys/sparkplug-client