Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

The ParameterView instance can no longer be read because it has expired. ParameterView can only be read synchronously and must not be stored for

When overriding SetParametersAsync, if I call any asynchronous method then I get the "Unhandled exception rendering component: The ParameterView instance can no longer be read because it has expired. ParameterView can only be read synchronously and must not be stored for later use."

public override async Task SetParametersAsync(ParameterView parameters)
{
    await Task.Delay(1000);

    await base.SetParametersAsync(parameters);
}

How can we safely call an async method in SetParamatersAsync?

like image 854
Mister Cook Avatar asked Mar 02 '23 16:03

Mister Cook


1 Answers

I believe the coding patterns you're looking for are shown below. The error message is generated by the Renderer. It's passing in the ParameterView, tracks it, and expects it to be consumed immediately (synchronously). The parameters within the object could be very stale in a second.

In the pattern we consume parameters immediately, applying it to the component instance properties. We can then call base at our leisure, passing an empty ParameterView as we've already set them.

        public async override Task SetParametersAsync(ParameterView parameters)
        {
            parameters.SetParameterProperties(this);
            await Task.Delay(100);
            await base.SetParametersAsync(ParameterView.Empty);
        }
        public override Task SetParametersAsync(ParameterView parameters)
        {
            parameters.SetParameterProperties(this);
              ... Do things
            return base.SetParametersAsync(ParameterView.Empty);
        }

This is the pattern the ASPNetCore team seem to use. You can see it here in the code for InputBase - line 190 onwards.

like image 123
MrC aka Shaun Curtis Avatar answered May 06 '23 03:05

MrC aka Shaun Curtis