C ++ 20 Coroutines Читать/записать WebSocketC++

Программы на C++. Форум разработчиков
Ответить
Anonymous
 C ++ 20 Coroutines Читать/записать WebSocket

Сообщение Anonymous »

Я хочу сделать WebSocket, работающий на одном потоке, используя Coroutines и Boost :: asio . Один коратика будет нести ответственность за написание (

Код: Выделить всё

async_write
), а другой позаботится о чтении (

Код: Выделить всё

async_read
).
Если какая -либо Coroutine получит исключение (пока я предполагаю, что каждое исключение означает разбитое соединение), я попробую восстановить связь. Клиенты WebSocket будут вызывать Ws.send (data) , и вместо немедленной отправки он останется в буфере до следующего WS.Run () вызов. Если я этого не сделаю, он будет вращаться навсегда, ожидая заполнения буфера. Но я получаю ошибку, пытаясь приостановить его с помощью std :: supardend_always {} :

Код: Выделить всё

error C2665: 'boost::asio::detail::awaitable_frame_base::await_transform': no overloaded function could convert all the argument types
Поэтому я думаю, что я не приостанавливаю сопрограмму с помощью asio::awaitable.
Мне действительно нужен этот прокси-буфер в качестве очереди для моих сообщений. Вероятно, я мог бы использовать что-то еще из boost - возможно, сигналы также предоставляют возможность co_await для них, но я боюсь, что мне придется задать еще 3 вопроса, чтобы понять это.
Вот мой код, сокращенный до минимума:

Код: Выделить всё

#include 
#include 
#include 

#include 
#include 
#include 
#include 

namespace asio = boost::asio;
namespace beast = boost::beast;
namespace websocket = beast::websocket;
using namespace std::chrono_literals;
using namespace asio::experimental::awaitable_operators;

struct CoroWebsocket {

CoroWebsocket(std::string host, std::string port)
: _host(std::move(host))
, _port(std::move(port)) {
asio::co_spawn(_ws.get_executor(), do_run(), asio::detached);
}

void Run() {
_ioc.run_for(50ms);
}

void Write(std::string data) {
// TODO: mutex
_writeBuffer.push_back(std::move(data));
}

std::optional Read(){
// TODO: mutex
if (_readBuffer.empty())
return {};
const auto message = _readBuffer.back();
_readBuffer.pop_back();
return message;
}

private:
const std::string _host, _port;
using tcp = asio::ip::tcp;
std::vector       _writeBuffer; // Will be filled externally.
std::vector       _readBuffer;
boost::asio::io_context        _ioc;
websocket::stream _ws{_ioc};

asio::awaitable do_run() {
while(true) {
try {
co_await do_connect();
co_await asio::co_spawn(_ws.get_executor(), do_write() || do_read(), asio::use_awaitable); // If either ends, it must've been an exception.  Reconnect.
} catch (const boost::system::system_error& se) {
std::cerr 

Подробнее здесь: [url]https://stackoverflow.com/questions/78120525/c20-coroutines-read-write-websocket[/url]
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «C++»