Overview
Examples
Screenshots
Comparisons
Applications
Download
Documentation
Tutorials
UppHub
Status & Roadmap
FAQ
Authors & License
Forums
Funding U++
Search on this site











SourceForge.net Logo

SourceForge.net Logo

GitHub Logo

Discord Logo

AsyncWebSocket

 

Demonstrates asynchronous WebSocket server

 

 

AsyncWebSocket.cpp

 

#include <Core/Core.h>

 

using namespace Upp;

 

struct Worker {

    WebSocket ws;

    

    void Do();

    

    Worker();

};

 

void Worker::Do()

{

    String s = ws.Receive();

    if(s.GetCount()) {

        LOG("Received request " << s);

        ws.SendText(AsString(sqrt(atof(s))));

    }

}

 

Worker::Worker()

{

    ws.NonBlocking();

}

 

void ClientEmulation();

 

CONSOLE_APP_MAIN

{

    StdLogSetup(LOG_COUT|LOG_FILE);

    

    WebSocket::Trace();

 

    TcpSocket server;

    server.Timeout(0);

 

    if(!server.Listen(12321, 5, false, true)) {

        LOG("Cannot open server socket for listening!");

        Exit(1);

    }

 

    ClientEmulation();

 

    Array<Worker> worker;

 

    LOG("Starting to listen");

    for(;;) {

        if(server.IsError()) {

            LOG("Server error: " << server.GetErrorDesc());

            server.ClearError();

        }

        SocketWaitEvent sel;

        sel.Add(server, WAIT_READ);

        for(auto& w : worker)

            w.ws.AddTo(sel);

        sel.Wait(1000);

        LOG("Waiting ended at " << GetSysTime());

        for(int i = worker.GetCount() - 1; i >= 0; i--)

            if(sel[i + 1]) {

                LOG("Event at worker " << i);

                Worker& w = worker[i];

                w.Do();

                if(w.ws.IsClosed() || w.ws.IsError()) {

                    worker.Remove(i);

                    LOG("WebSocket closed, current count: " << worker.GetCount());

                }

            }

        if(sel[0]) {

            if(!worker.Add().ws.NonBlocking().Accept(server))

                worker.Drop();

            else

                LOG("WebSocket accepted, current count: " << worker.GetCount());

        }

    }

}

 

 

 

Client.cpp

 

#include <Core/Core.h>

 

using namespace Upp;

 

// Clients are run in blocking mode

 

void ClientEmulation()

{

    Thread::Start([] {

    #if 0 // change to 1 to do single request

        Sleep(500);

        WebSocket ws;

        ws.Connect("ws://127.0.0.1:12321");

        if(ws.IsError()) {

            LOG("Failed to connect");

            return;

        }

        LOG("Client Request");

        ws.SendText(AsString(Random()));

        LOG("Response: " << ws.Receive());

        ws.Close();

    #else

        for(;;) {

            Sleep(Random(2000));

            Thread::Start([] {

                LOG("Started a new client");

                WebSocket ws;

                ws.Connect("ws://127.0.0.1:12321");

                if(ws.IsError()) {

                    LOG("Failed to connect");

                    return;

                }

                LOG("WebSocket connected to the server");

                while(Random(20) && ws.IsOpen()) {

                    String request = AsString(Random());

                    LOG("Sending request " << request);

                    ws.SendText(request);

                    String reply = ws.Receive();

                    LOG(request << " -> " << reply);

                    Sleep(Random(2000));

                }

                ws.Close();

            });

        }

    #endif

    });

}

 

 

 

Do you want to contribute?