// // MessagesClient.cpp // libraries/networking/src // // Created by Brad hefta-Gaub on 11/16/2015. // Copyright 2015 High Fidelity, Inc. // // Distributed under the Apache License, Version 2.0. // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // #include "MessagesClient.h" #include #include #include #include "NetworkLogging.h" #include "NodeList.h" #include "PacketReceiver.h" MessagesClient::MessagesClient() { setCustomDeleter([](Dependency* dependency){ static_cast(dependency)->deleteLater(); }); auto nodeList = DependencyManager::get(); auto& packetReceiver = nodeList->getPacketReceiver(); packetReceiver.registerMessageListener(PacketType::MessagesData, this, "handleMessagesPacket"); connect(nodeList.data(), &LimitedNodeList::nodeActivated, this, &MessagesClient::handleNodeActivated); } void MessagesClient::init() { if (QThread::currentThread() != thread()) { QMetaObject::invokeMethod(this, "init", Qt::BlockingQueuedConnection); } } void MessagesClient::handleMessagesPacket(QSharedPointer packetList, SharedNodePointer senderNode) { QByteArray packetData = packetList->getMessage(); QBuffer packet{ &packetData }; packet.open(QIODevice::ReadOnly); quint16 channelLength; packet.read(reinterpret_cast(&channelLength), sizeof(channelLength)); auto channelData = packet.read(channelLength); QString channel = QString::fromUtf8(channelData); quint16 messageLength; packet.read(reinterpret_cast(&messageLength), sizeof(messageLength)); auto messageData = packet.read(messageLength); QString message = QString::fromUtf8(messageData); emit messageReceived(channel, message, senderNode->getUUID()); } void MessagesClient::sendMessage(const QString& channel, const QString& message) { auto nodeList = DependencyManager::get(); SharedNodePointer messagesMixer = nodeList->soloNodeOfType(NodeType::MessagesMixer); if (messagesMixer) { auto packetList = NLPacketList::create(PacketType::MessagesData, QByteArray(), true, true); auto channelUtf8 = channel.toUtf8(); quint16 channelLength = channelUtf8.length(); packetList->writePrimitive(channelLength); packetList->write(channelUtf8); auto messageUtf8 = message.toUtf8(); quint16 messageLength = messageUtf8.length(); packetList->writePrimitive(messageLength); packetList->write(messageUtf8); nodeList->sendPacketList(std::move(packetList), *messagesMixer); } } void MessagesClient::subscribe(const QString& channel) { _subscribedChannels << channel; auto nodeList = DependencyManager::get(); SharedNodePointer messagesMixer = nodeList->soloNodeOfType(NodeType::MessagesMixer); if (messagesMixer) { auto packetList = NLPacketList::create(PacketType::MessagesSubscribe, QByteArray(), true, true); packetList->write(channel.toUtf8()); nodeList->sendPacketList(std::move(packetList), *messagesMixer); } } void MessagesClient::unsubscribe(const QString& channel) { _subscribedChannels.remove(channel); auto nodeList = DependencyManager::get(); SharedNodePointer messagesMixer = nodeList->soloNodeOfType(NodeType::MessagesMixer); if (messagesMixer) { auto packetList = NLPacketList::create(PacketType::MessagesUnsubscribe, QByteArray(), true, true); packetList->write(channel.toUtf8()); nodeList->sendPacketList(std::move(packetList), *messagesMixer); } } void MessagesClient::handleNodeActivated(SharedNodePointer node) { if (node->getType() == NodeType::MessagesMixer) { for (const auto& channel : _subscribedChannels) { subscribe(channel); } } }