Skip to content

Instantly share code, notes, and snippets.

@YSaxon
Last active July 14, 2023 19:00
Show Gist options
  • Save YSaxon/816c919acc2aacb7873375a3140f178b to your computer and use it in GitHub Desktop.
Save YSaxon/816c919acc2aacb7873375a3140f178b to your computer and use it in GitHub Desktop.

How to export messages from MQTT-Explorer to CSV

(copied from my comment here: thomasnordquist/MQTT-Explorer#632 (comment))

Open DevTools (should be an option in the file menu) Now in the JS Console

const reactRoot = document.querySelector('#app')._reactRootContainer;
const store = reactRoot._internalRoot.current.child.memoizedProps.store;
var tree = store.getState().connection.tree

From there you can access the messages through a somewhat complex object chain. And then you can parse that out into a csv.

window.base64Decode = function(base64) {
    return atob(base64);
}

window.rawToHex = function(raw) {
    var result = "";
    for (var i = 0; i < raw.length; i++) {
        result += raw.charCodeAt(i).toString(16).padStart(2, "0");
    }
    return result;
}


window.makePrintable = function(input) {
    var output = '';
    for (var i = 0; i < input.length; i++) {
        var charCode = input.charCodeAt(i);
        // Replace comma, double quote, backslash, and any non-printable characters
        if (charCode < 32 || charCode > 126 || charCode === 34 || charCode === 44 || charCode === 92) {
            output += '_';  // Or replace with a box icon
        } else {
            output += input.charAt(i);
        }
    }
    return output;
}

var rows = [];

// Function to traverse the tree recursively
window.traverseTree = function(treeNode, topic) {
    if (treeNode.edges) {
        for (var edgeName in treeNode.edges) {
            if (treeNode.edges.hasOwnProperty(edgeName)) {
                traverseTree(treeNode.edges[edgeName].target, topic + '/' + edgeName);
            }
        }
    }
    if (treeNode.messageHistory && treeNode.messageHistory.items) {
        var messageHistory = treeNode.messageHistory.items;
        for (var j = 0; j < messageHistory.length; j++) {
            var item = messageHistory[j];
            var timestamp = item.received;
            var base64Message = item.value.base64Message;
            var rawMessage = base64Decode(base64Message);
            var hexMessage = rawToHex(rawMessage);
            rows.push({
                topic: topic,
                timestamp: timestamp,
                base64Message: base64Message,
                rawMessage: makePrintable(rawMessage),
                hexMessage: hexMessage
            });
        }
    }
}

// Start traversing from root
traverseTree(tree, "");

var csvContent = "topic,timestamp,base64Message,rawMessage,hexMessage\n";
for (var i = 0; i < rows.length; i++) {
    var row = rows[i];
    csvContent += [row.topic, row.timestamp, row.base64Message, row.rawMessage, row.hexMessage].join(",") + "\n";
}

console.log(csvContent);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment