Search code examples
c#blazorlifecycle

Blazor question- close circuit\connection immediately after making async call


I have a blazor integration and basically, after an indeterminate period of time I see this screen:

enter image description here

Is there no way to prevent this from happening? My concern is that I'm maybe not closing circuits/connections after I have the data I need from the server-side call.

I have this in my ComponentBase class:

  protected override async Task OnInitializedAsync()
    {
         await DoStuff();
    }

which calls to this:

 private async Task DoStuff()
    {

        var results= await httpClient.GetJsonAsync<MyResultsClass>(someResultsUrl);
          ...  
        StateHasChanged();
    }

But I'm wondering if I need something after the fact (maybe need to implement IDisposable, have some kind of a handle to any created circuits, and dispose of it immediately) to make sure that it gets automatically cleaned up? That message should never show, and there is no need to keep any kind of connection open after I get the results I need. I just don't know what sort of handler\object I need that represents the Blazorconnection that is being made.

I found this link but it seems like a lot to accomplish one little thing.

Edit: after trying the proposed solution, I'm seeing slightly different behavior involving a message saying "Attempting to reconnect to server". When that doesn't work, I see "Could not reconnect to the server. Reload the page to restore functionality". Is there no way to automate this, or, at least, prevent it completely by automatically closing the connection\circuit (if it isn't needed)?

Edit 2: it would also be suitable if the reconnection happened automatically, if\where possible - if I leave my blazor page open for a long time, reconnection doesn't seem to work. But, if it were to reconnect at the moment it lost connection, I presume that it could help?

Edit 3: other alternative I'd be happy with is if the page automatically refreshed instead of a reconnection - that would work for me just fine.

Edit 4: (in response to enet's answer) - helps a lot, thanks! And I agree, it's a hack to try to forcibly close the connection. I was just hoping there was a way to gracefully close the connection, knowing that once DoStuff() is done doing what it needs to do, it can release the resources - instead of unnecessarily lingering. If this is a consequence of Blazor that I have to live with, then it's fine. I've found a way to suppress the "Hateful screen" (as you call it) that comes up which is great, but would be nice if I could clean up the "Error: Connection disconnected with error "Error: WebSocket closed with status code: 1006 ().' I've seen a lot of threads about that error, and they mostly lean to the solution of force an automatic refresh. I don't actually care if the error even happens, I just want to make sure that it will eventually free up the resources (and if it happens automatically, then I'm fine with that, too.) - would ideally like to be able to catch\ignore that error message, but if it's something I should be concerned about, then... I don't want to ignore it. Also, this issue is very easy to reproduce and I don't have to recycle my website app pool or anything like that.


Solution

  • I was just hoping there was a way to gracefully close the connection, knowing that once DoStuff() is done doing what it needs to do, it can release the resources - instead of unnecessarily lingering.

    Yes, code as this close the connection (JavaScript, SignalR):

      if (connection) {
        connection.stop();
      }
    

    But why do such a thing?

    This is not windows desktop app, this is a web app running via SignalR, enabling communication through a circuit connection. Please, don't try to code like this. Your connection should close gracefully when the user closes the web page. Understand that closing a connection and then opening a new connection result in lost of the app state and the data created for the page.

    What resources do you want to release after DoStuff() has run ? Do you use external resources that you must release ? And if you do, this can easily be done by implementing the IDisposable interface. And this is mostly done to prevent memory link, as Blazor constantly create and destroy components.

    but would be nice if I could clean up the "Error: Connection disconnected with error "Error: WebSocket closed with status code: 1006 ().'

    I guess this is doable...

    I've seen a lot of threads about that error, and they mostly lean to the solution of force an automatic refresh

    Exactly... because they want an active and live circuit connection. But you want to kill your connection.

    I just want to make sure that it will eventually free up the resources

    Again RESOURCES ??? I'm trying to understand you ? DO YOU MEAN THE RESOURCES USED BY THE SERVER ? Because perhaps of scarcity of resource ? If yes, then my answer is positive. This is from the docs:

    The server can't retain a disconnected circuit forever. The server must release a disconnected circuit after a timeout or when the server is under memory pressure.

    So you can rest assured that resources are going to be released without mercy...