Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/artcom/hivemq-retained-message-query-plugin
A HiveMQ extension to query retained messages via HTTP
https://github.com/artcom/hivemq-retained-message-query-plugin
Last synced: 3 months ago
JSON representation
A HiveMQ extension to query retained messages via HTTP
- Host: GitHub
- URL: https://github.com/artcom/hivemq-retained-message-query-plugin
- Owner: artcom
- License: apache-2.0
- Created: 2016-09-09T13:05:51.000Z (over 8 years ago)
- Default Branch: master
- Last Pushed: 2023-12-11T14:52:56.000Z (about 1 year ago)
- Last Synced: 2023-12-11T15:29:23.662Z (about 1 year ago)
- Language: Java
- Homepage:
- Size: 1.1 MB
- Stars: 5
- Watchers: 9
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE.txt
Awesome Lists containing this project
README
# HiveMQ Retained Message Query Extension
A HiveMQ extension that allows to query retained messages via HTTP instead of using MQTT subscriptions.
## Development Setup
HiveMQ is needed to run and test the extension. An evaluation version is available [here](http://www.hivemq.com/downloads/).
The extension was developed using IntelliJ IDEA. The repo contains the project file: `hivemq-retained-message-query-extension.iml`.
It can also be built on the command line using Maven:
```bash
$ mvn package
```Maven is configured to use the [HiveMQ Maven Plugin](http://www.hivemq.com/docs/plugins/latest/#maven-plugin-chapter) that will automatically start the plugin when using the `RunWithHiveMQ` profile:
```bash
$ mvn package -PRunWithHiveMQ
```## Tests
There is a test suite in `test/test.js`. Tests are written in JavaScript and run using [mocha](http://mochajs.org/) on Node.js:
```bash
$ npm install # install test dependencies
$ npm test # run tests against localhost
```To run the tests against a different HiveMQ instance, you can set the `BROKER` environment variable:
```bash
BROKER=broker.example.com npm test
```## HTTP API
The extension provides an HTTP API to query retained messages without using the MQTT protocol. The API uses JSON to define the query and represent the results.
## Query
### Endpoint
Retained message payloads can be queried by sending an HTTP POST request to the `/query` endpoint. Using jQuery, you can send a query like this:
```javascript
$.post(httpBrokerUri + "/query", JSON.stringify(query));
```### Query Objects
In the request body we pass a JSON-encoded *query object* containing the details of our query:
```json
{
"topic": "path/of/the/topic",
"depth": 0,
"flatten": false
}
```* `topic` (String) is mandatory. It specifies the path of the topic we want to query.
* `depth` (Number) is optional, defaults to `0`. It specifies how many levels of child topics should be included in the response.
* `flatten` (Boolean) is optional, defaults to `false`. When set to `true`, the query will return an array of result objects instead of a single result objects. The array contains the result object for the queried topic as well as the result objects for all of its children, as far as they are included by the `depth` parameter.### Result Objects
The *result object* that we get back from the broker is also a JSON object:
```json
{
"topic": "path/of/the/topic",
"payload": "23",
"children": [
{
"topic": "path/of/child/topic",
"payload": "\"foo\""
}
]
}
```* `topic` (String) is always present. This is the path of the topic we queried.
* `payload` (String) is optional. It will be included if there is a retained payload for the given topic. The payload is always a string. For topics following our convention to use JSON in payloads, that means we have to `JSON.parse()` the payload on the client side.
* `children` (Array) is optional. It will be included when there are child topics and the `depth` parameter in the query is set to include them, unless the `flatten` parameter is set. The items of the array are *result objects* themselves, including `topic`, an optional `payload` and optional `children`.### Wildcard Queries
The query API has limited support for wildcard queries: The topic in the *query object* may contain one or more `+` wildcards. Instead of a single *result object*, the broker will return an array of *result objects*.
While the `#` wildcard is not supported, a similar result can be achieved using the `depth` parameter.
### Batch Queries
It is also possible to query multiple topics at once. When the request body contains an array of *query objects* instead of a single *query object*, the broker will return an array with a *result object* for each query.
### Examples
Topic | Payload
--------------- | -------
`foo/bar1` | `"hello"`
`foo/bar1/baz1` | `["night", "day"]`
`foo/bar2` | `13`
`foo/bar2/baz1` | `true`
`foo/bar2/baz2` | `false`Let's assume we have the above retained messages published to the broker. We can now issue some queries:
##### Single Query (Depth 0)
```json
// Query
{ "topic": "foo/bar1" }// Result
{ "topic": "foo/bar1", "payload": "\"hello\"" }
```##### Single Query (Depth 1)
```json
// Query
{ "topic": "foo", "depth": 1 }// Result
{
"topic": "foo",
"children": [
{ "topic": "foo/bar1", "payload": "\"hello\"" },
{ "topic": "foo/bar2", "payload": "13" }
]
}
```##### Single Query (Depth 2)
```json
// Query
{ "topic": "foo", "depth": 2 }// Result
{
"topic": "foo",
"children": [
{
"topic": "foo/bar1",
"payload": "\"hello\"",
"children": [
{ "topic": "foo/bar1/baz1", "payload": "[\"night\", \"day\"]" }
]
},
{
"topic": "foo/bar2",
"payload": "13",
"children": [
{ "topic": "foo/bar2/baz1", "payload": "true" },
{ "topic": "foo/bar2/baz2", "payload": "false" }
]
}
]
}
```##### Flattened Single Query (Depth 2)
```json
// Query
{ "topic": "foo", "depth": 2, "flatten": true }// Result
[
{ "topic": "foo" },
{ "topic": "foo/bar1", "payload": "\"hello\"" },
{ "topic": "foo/bar1/baz1", "payload": "[\"night\", \"day\"]" }
{ "topic": "foo/bar2", "payload": "13" },
{ "topic": "foo/bar2/baz1", "payload": "true" },
{ "topic": "foo/bar2/baz2", "payload": "false" }
]
```##### Batch Query
```json
// Query
[{ "topic": "foo/bar1" }, { "topic": "foo/bar2", "depth": 1 }]// Result
[
{
"topic": "foo/bar1",
"payload": "\"hello\""
},
{
"topic": "foo/bar2",
"payload": "13",
"children": [
{ "topic": "foo/bar2/baz1", "payload": "true" },
{ "topic": "foo/bar2/baz2", "payload": "false" }
]
}
]
```##### Wildcard Query
```json
// Query
{ "topic": "foo/+/baz1" }// Result
[
{ "topic": "foo/bar1/baz1", "payload": "[\"night\", \"day\"]" },
{ "topic": "foo/bar2/baz1", "payload": "true" }
]
```## CORS
It can be necessary to send CORS headers along with the response e.g. if there is no upstream server which handles it. The internal HTTP Server can be configured to provide these CORS headers by adding the following section to `conf/config.xml`:
```
true
```
Or by setting the environment variable `QUERY_PLUGIN_CORS` to `true`.
The default is `false` to avoid [duplicate CORS header errors](https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS/Errors/CORSMultipleAllowOriginNotAllowed).
## HTTP API PORT
The default port for the HTTP API is `8080`. It can be changed by setting the environment variable `QUERY_PLUGIN_PORT` to the desired port.
## Disconnect clients on extension initialization
The extension can be configured to disconnect all clients when the extension is initialized. This is needed on startup when the extension is used with the HiveMQ CE broker. The extension will not add a PublishInboundInterceptor to clients connected before the extension is initialized. To disconnect all clients on startup, set the environment variable `QUERY_PLUGIN_DISCONNECT_CLIENTS` to `true`.