How to catch exceptions thrown by the ConnectAsync method of MessageWebSocket?

0

I'm implementing an UWP application for the HoloLens which streams a point cloud over a MessageWebSocket to a companion PC. If I launch the app on the HoloLens while the server on the companion PC is not yet running, calling the ConnectAsync method of MessageWebSocket triggers an exception (because it can't connect to the server) which causes my app to crash. However, I can't figure out how to catch this exception.

Inspired by the example code shown in the official documentation of MessageWebSocket, this is a small sample which reproduces the issue:

void TryConnectToWebsocket()
{
    Windows::Networking::Sockets::MessageWebSocket^ websocket = ref new Windows::Networking::Sockets::MessageWebSocket();
    websocket->Control->MessageType = Windows::Networking::Sockets::SocketMessageType::Utf8;

    try
    {
        ::OutputDebugString(L"Trying to connect...\n");
        auto connectTask = Concurrency::create_task(websocket->ConnectAsync(ref new Windows::Foundation::Uri(L"ws://192.168.0.38:9090")));
        connectTask.then([this, websocket]
        {
            ::OutputDebugString(L"Connected successfully!");
            websocket->Close(1000, "Application caused the connection to close.");
        });
    }
    catch (...)
    {
        ::OutputDebugString(L"Couldn't connect to websocket!");
    }
}

Please note, that the original example code from the docs catches exceptions of type Platform::Exception. I chose to catch exceptions of all types in this code snippet to assert that I don't miss the exception in case it is not a Platform::Exception (or a subtype of it).

If I run this code snippet (without the server being started), I would expect the following console output:

Trying to connect...
Couldn't connect to the websocket!

However, what I get is the following: (Console outputs about loaded and unloaded DLLs have been left out. Some of the messages describing what went wrong were originally in German, so I've translated them.)

Trying to connect...
Exception thrown at 0x76B34592 (KernelBase.dll) in Test.exe: WinRT originate error - 0x80072EFD : 'A connection with the server could not be established.'.
Exception thrown at 0x76B34592 in Test.exe: Microsoft C++ exception: Platform::COMException ^ at memory location 0x0C5AE500. HRESULT:0x80072EFD The message for this error code could not be found.
WinRT information: A connection with the server could not be established.
Stack trace:
 >[External Code]

As you can see, the catch block isn't being executed at all. Furthermore, the very short and unprecise stack trace makes it appear as if the exception is thrown somewhere in a background thread where I don't even have a chance of catching it.

I'd really like to handle this exception instead of having the application crash. Is there any way how I can do this?

c++
websocket
uwp
asked on Stack Overflow Oct 27, 2019 by Fabian B.

1 Answer

1

From the official sample, it doesn't put every operation that might throw within a try…catch block. Instead, it adds a task-based continuation at the end of the chain and handles all errors there. You can try the following code to catch the exception.

create_task(messageWebSocket->ConnectAsync(ref new Windows::Foundation::Uri(L"ws://192.168.0.38:9090")))
        .then([this](task<void> previousTask)
            {
                try
                {
                    previousTask.get();
                    ::OutputDebugString(L"Connected successfully!");
                    websocket->Close(1000, "Application caused the connection to close.");
                }
                catch (Exception^ ex)
                {
                    ::OutputDebugString(L"Couldn't connect to websocket!");
                }

            });
answered on Stack Overflow Oct 30, 2019 by Faywang - MSFT

User contributions licensed under CC BY-SA 3.0