Scott Weldon
Scott Weldon

Reputation: 10227

Why doesn't ASP.NET TempData work when modifying Web.config?

I have a function in my Global.asax.cs file that applies a couple changes to the Web.config file, if needed. The file is saved with:

config.Save(ConfigurationSaveMode.Modified);

I recently discovered that TempData wasn't working for my app: it appeared to be empty on the next request. My MCVE:

public ActionResult Foo()
{
  TempData["error"] = "testing error passing";
  return RedirectToAction("Bar");
}

public ActionResult Bar()
{
  throw new Exception(TempData["error"] as string);
}

I added that to my HomeController, and visiting /Home/Foo would redirect to /Home/Bar. However, with the above config.Save line active, I get:

Server Error in '/' Application.
Exception of type 'System.Exception' was thrown.

But if I comment out that line, I get:

Server Error in '/' Application.
test error passing

as I was expecting originally.

(I had a couple instances where I got the inverse result, but it was usually on the first request after I commented or un-commented the line, so probably I should blame caching.)

Why does this happen, and how can I fix it?

Upvotes: 0

Views: 1021

Answers (2)

Haitham Shaddad
Haitham Shaddad

Reputation: 4456

TempData stores the values in session and it seems your default session store is InProc which stores the data in server memory which is mainly running under the AppDomain for the Application Pool

By Default, when there is any change in the files under virtual directory, IIS detects that using a File Watcher and recycle the application pool, this will de-allocate all the memory assigned to this web application.

To avoid that, you can change session mode to be either Database or State Server.

But the best thing is to avoid changing the web.config at all, if you have any configuration that is user defined or need to be changed at run time, then you have to store it somewhere else and cache to avoid any performance hits

Upvotes: 1

Tetsuya Yamamoto
Tetsuya Yamamoto

Reputation: 24957

Based from this question:

What happens when I edit web.config?

Imagine each ASP.NET application (as defined in IIS) is a program on the desktop. Saving web.config will do something similar to closing the program and reopening it. - Dan Goldstein

IIS default behavior automatically reset entire session state and recycles existing AppDomain when any changes applied to web.config file at runtime, thus all values stored on TempData array are lost, leaving null values instead.

When config.Save line left uncommented, the line:

throw new Exception(TempData["error"] as string);

will contain null value from TempData["error"]:

throw new Exception(null);

Since as operator returns null if the object doesn't exist, it throws new Exception instance with null string, causing default exception message to show instead of custom one.

If config.Save line commented, the configuration changes doesn't applied into web.config file, thus existing AppDomain remains running and TempData values are still in place.

The default behavior can be changed by these steps:

  1. Open IIS Manager.
  2. Select Application Pools => [your application pool name] => Advanced Settings.
  3. On Recycling area, find Disable Recycling for Configuration Changes (DisallowRotationOnConfigChange) section and set it to True.

Related problem: How to prevent an ASP.NET application restarting when the web.config is modified?

Upvotes: 3

Related Questions