File indexing completed on 2024-12-15 05:02:05
0001 /* 0002 SPDX-FileCopyrightText: 2019 Ivan Čukić <ivan.cukic(at)kde.org> 0003 0004 SPDX-License-Identifier: LGPL-2.1-only OR LGPL-3.0-only OR LicenseRef-KDE-Accepted-LGPL 0005 */ 0006 0007 #ifndef BLADE_TRANSPORT_H 0008 #define BLADE_TRANSPORT_H 0009 0010 #include "ControllerMessage.h" 0011 0012 #include <sstream> 0013 #include <iostream> 0014 0015 #include <capnp/message.h> 0016 #include <capnp/serialize.h> 0017 #include <capnp/serialize-packed.h> 0018 #include <kj/std/iostream.h> 0019 0020 #include <utils/overloaded.h> 0021 using std_ex::overloaded; 0022 0023 #include "transport/protocol/controller_message.capnp.h" 0024 0025 namespace blade::serialization { 0026 0027 inline 0028 void writeToStdStream(const ControllerMessage &msg, std::ostream& out_) 0029 { 0030 capnp::MallocMessageBuilder builder; 0031 0032 auto cm = builder.initRoot<protocol::ControllerMessage>(); 0033 0034 cm.setHost(msg.host.data()); 0035 cm.setController(msg.controller.data()); 0036 0037 auto message = cm.initMessage(); 0038 0039 std::visit( 0040 overloaded { 0041 [&](const PingMessage &) { message.initPing(); }, 0042 [&](const QueryMessage &msg) { 0043 auto query = message.initQuery(); 0044 query.setId(msg.id); 0045 query.setText(msg.text.toUtf8().data()); 0046 }, 0047 [&](const ErrorMessage &msg) { 0048 auto error = message.initError(); 0049 error.setCode(msg.code); 0050 error.setMessage(msg.message.data()); 0051 }, 0052 }, 0053 msg.message); 0054 0055 kj::std::StdOutputStream out(out_); 0056 capnp::writeMessage(out, builder); 0057 } 0058 0059 void writeToStdStream(const ControllerMessage &msg, std::ostream& out); 0060 0061 inline 0062 std::string asStdString(const ControllerMessage& msg) 0063 { 0064 std::ostringstream result; 0065 writeToStdStream(msg, result); 0066 return result.str(); 0067 } 0068 0069 namespace detail { 0070 auto asByteArray(const capnp::Text::Reader& reader) 0071 { 0072 return QByteArray(reader.cStr(), reader.size()); 0073 } 0074 } // namespace detail 0075 0076 inline 0077 blade::ControllerMessage readControllerMessage(const std::string &data) 0078 { 0079 std::istringstream ss(data); 0080 kj::std::StdInputStream is(ss); 0081 capnp::InputStreamMessageReader reader(is); 0082 0083 auto cm = reader.getRoot<protocol::ControllerMessage>(); 0084 0085 blade::ControllerMessage result; 0086 0087 result.host = detail::asByteArray(cm.getHost()); 0088 result.controller = detail::asByteArray(cm.getController()); 0089 0090 auto message = cm.getMessage(); 0091 0092 if (message.hasQuery()) { 0093 auto query = message.getQuery(); 0094 result.message = blade::QueryMessage{ 0095 query.getId(), 0096 QString::fromUtf8(detail::asByteArray(query.getText())) 0097 }; 0098 0099 } else if (message.hasPing()) { 0100 result.message = blade::PingMessage{}; 0101 0102 } else if (message.hasError()) { 0103 auto error = message.getError(); 0104 result.message = blade::ErrorMessage{ 0105 error.getCode(), 0106 detail::asByteArray(error.getMessage()) 0107 }; 0108 0109 } else { 0110 result.message = blade::ErrorMessage{ 0111 static_cast<std::uint16_t>(-1), 0112 "unknown error" 0113 }; 0114 } 0115 0116 return result; 0117 } 0118 0119 0120 } // namespace blade::serialization 0121 0122 #endif // include guard 0123