In my Blazor application (WebAssembly), I need to load User data in my ApplicationState. Many of my pages needs this User data, so on their OnAfterRenderAsync method, I'm loading User data if it's not loaded :
protected override async Task OnAfterRenderAsync(bool firstRender)
{
    if (firstRender)
    {
        loadingSession = true;
        if (!sessionState.UserDataLoaded)
            await sessionState.LoadUserData();
        loadingSession = false;
    }
    await base.OnAfterRenderAsync(firstRender);
}
But if I go to an other page quickly, the user data won't be loaded yet, and the page will ask a new request.
So I would like to wait if there is already a request, and not to start a new one.
    public async Task LoadUserData()
    {
        try
        {
            if (dataLoading)
            {
                // Need to wait the previous request
            }
            if (dataLoaded)
                return;
            dataLoading = true;
            User = await httpClient.GetFromJsonAsync<User>("users", options);
        }
        catch (Exception e)
        {
            OnException(e);
        }
        finally
        {
            if (User != null)
                dataLoaded = true;
            dataLoading = false;
        }
    }
I tried many things, ManualResetEvent, Thread.Sleep in a Task,... but I don't manage to do it correcly. What would be the best method ?
                        
Moving your code to the
OnInitializedAsyncmethod will load the user data before the control has rendered.Edit: (you want to pass state between components)
Microsoft documentation on State Management
Another example of keeping state in memory and passing it to components via Dependency Injection.
To make use of 'State management' you have to register a 'Service' that can be used for state management.
For example; Create a class named
AppStatewith the values you would like to keep state of.then register this class in your
ServicesasSingleton(see Service Lifetimes):Then in your
Index.razorfile (or wherever you need to call it for the first time) use dependency injection to get access to theAppStateand in theOnInitialzedAsync()call the user data usingHttpContent.This will await the call to the API until it has received a response. If the response was successful ie:
response.IsSuccessStatusCodeis true. extract the data from the response message and store it in theappState.UserDate.In any subsequent component you can get the
AppStateby injecting it using@inject AppState appStateor if it is in a code file[Inject] AppState appState;In the subsequent components you can add a check in the
OnInitializedAsyncmethod :!! This is not how authentication should be handled though !!
If you need authentication look at ASP.NET Core Blazor authentication and authorization as it makes use of AuthenticationStateProvider.
In regards to checking if the call has already been made to the http client, the
awaitshould wait for the response from thehttpClientbefore continuing.If
appState.UserDatahas some value then the call was successfull..