Introduction
This library provides advanced asynchronous I/O and networking capabilities using coroutine-based APIs and poller-driven execution. It supports high-performance operations for both network sockets and file handles.
Key Features
The library's core functionality is exposed through a few high-level classes:
In addition to these, the library supports multiple polling mechanisms for asynchronous operations:
- TSelect - Poller using the select() system call.
 
- TPoll - Poller using the poll() system call.
 
- TEPoll - Linux-specific poller using epoll.
 
- TKqueue - Poller for macOS/FreeBSD using kqueue.
 
- TIOCp - Poller for Windows using IOCP.
 
- TUring - Linux-specific poller using io_uring.
 
Example: Echo Client
The following example demonstrates a simple echo client. The client reads lines from standard input, sends them to an echo server, and then prints the response.
template<bool debug, typename TPoller>
TFuture<void> client(TPoller& poller, TAddress addr)
{
    static constexpr int maxLineSize = 4096;
    using TSocket = typename TPoller::TSocket;
    using TFileHandle = typename TPoller::TFileHandle;
    std::vector<char> in(maxLineSize);
 
    try {
        TFileHandle input{0, poller}; 
        TSocket socket{poller, addr.Domain()};
        TLineReader lineReader(input, maxLineSize);
        TByteWriter byteWriter(socket);
        TByteReader byteReader(socket);
 
        co_await socket.Connect(addr, TClock::now() + std::chrono::milliseconds(1000));
        while (auto line = co_await lineReader.Read()) {
            co_await byteWriter.Write(line);
            co_await byteReader.Read(in.data(), line.Size());
            if constexpr (debug) {
                std::cout << "Received: " << std::string_view(in.data(), line.Size()) << "\n";
            }
        }
    } catch (const std::exception& ex) {
        std::cout << "Exception: " << ex.what() << "\n";
    }
 
    co_return;
}
Example: Simple Actor
The following example demonstrates basic actor usage for message processing:
struct TCounterMessage {
    static constexpr TMessageId MessageId = 1;
    int value;
};
 
class TCounterActor : public IActor {
private:
    int counter = 0;
 
public:
    void Receive(TMessageId messageId, TBlob blob, TActorContext::TPtr ctx) override {
        if (messageId == TCounterMessage::MessageId) {
            auto message = DeserializeNear<TCounterMessage>(blob);
            counter += message.value;
            std::cout << "Counter: " << counter << "\n";
        }
    }
};
 
template<typename TPoller>
TFuture<void> actorExample(TPoller& poller) {
    TActorSystem actorSystem;
    auto actorId = actorSystem.Register(std::make_unique<TCounterActor>());
    
    actorSystem.Send(actorId, TCounterMessage{5});
    actorSystem.Send(actorId, TCounterMessage{10});
    actorSystem.Send(actorId, TCounterMessage{-3});
    
    co_return;
}
Further Information
For more details on each component, please refer to the following classes:
For the available pollers, see: