Setting TempData on IExceptionFilter with SessionStateTempDataProvider
- Dominant language
- C#
- Stars
- 38.4k
- Forks
- 10.9k
- Avg merge
- 2d 6h
- Merged PRs (30d)
- 290
Description
### Is there an existing issue for this?
- [x] I have searched the existing issues
### Describe the bug
I have implemented a `IExceptionFilter `that sets some data on `TempData `to be read on the redirect action, however since I have enabled `SessionStateTempDataProvider `when the pipeline reaches the response.OnStarting it will try to access Session that at that time has been closed on the `SessionMiddleware`. I know that I can pass the data as query string for example, but this is a legacy application migration that we are migrating slowly so the redirect endpoint is not to be migrated yet and it reads the data from the `TempData`.
### Expected Behavior
To not give exception.
### Steps To Reproduce
Example:
```
var builder = WebApplication.CreateBuilder();
builder.Services.AddSession();
builder.Services.AddScoped();
builder.Services
.AddControllersWithViews()
.AddSessionStateTempDataProvider();
var app = builder.Build();
app.UseRouting();
app.UseSession();
app.MapControllers();
app.Run();
```
```
public sealed class BaseControllerExceptionFilter : IExceptionFilter
{
private readonly ITempDataDictionaryFactory _tempDataFactory;
public BaseControllerExceptionFilter(ITempDataDictionaryFactory tempDataFactory)
{
_tempDataFactory = tempDataFactory;
}
public void OnException(ExceptionContext context)
{
var tempData = _tempDataFactory.GetTempData(context.HttpContext);
tempData["example"] = context.Exception.Message;
context.Result = new RedirectToActionResult(null, "WeatherForecast", null);
context.ExceptionHandled = true;
}
}
```
```
[ApiController]
[Route("[controller]")]
[ServiceFilter(typeof(BaseControllerExceptionFilter))]
public class WeatherForecastController : Controller
{
private static readonly string[] Summaries = new[]
{
"Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
};
private readonly ILogger _logger;
public WeatherForecastController(ILogger logger)
{
_logger = logger;
}
[HttpGet(Name = "GetWeatherForecast")]
public IEnumerable Get()
{
var example = TempData["example"];
if(example == null)
{
throw new Exception("123 = 123");
}
return Enumerable.Range(1, 5).Select(index => new WeatherForecast
{
Date = DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
TemperatureC = Random.Shared.Next(-20, 55),
Summary = Summaries[Random.Shared.Next(Summaries.Length)]
})
.ToArray();
}
}
```
### Exceptions (if any)
System.InvalidOperationException: Session has not been configured for this application or request.
at Microsoft.AspNetCore.Http.DefaultHttpContext.get_Session()
at Microsoft.AspNetCore.Mvc.ViewFeatures.SessionStateTempDataProvider.SaveTempData(HttpContext context, IDictionary`2 values)
at Microsoft.AspNetCore.Mvc.ViewFeatures.TempDataDictionary.Save()
at Microsoft.AspNetCore.Mvc.ViewFeatures.Filters.SaveTempDataFilter.OnStarting(HttpContext httpContext)
at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpProtocol.g__ProcessEvents|241_0(HttpProtocol protocol, Stack`1 events)
### .NET Version
net8.0
### Anything else?
_No response_
Contributor guide
Assessment
This issue has not been assessed yet.