TempData in ASP.NET Core MVC

TempData in ASP.NET Core MVC

In this article, I will discuss ASP.NET Core MVC TempData with Examples. As discussed in our previous articles, we can use ViewData, ViewBag, and Strongly Typed Models to pass data from a controller action method to a view. Now, we will see another approach to sending data from the controller action method to a view, i.e., TempData. As part of this article, we will discuss the following pointers related to MVC TempData.

  1. Why do we need TempData in the ASP.NET Core MVC Application?
  2. What exactly is TempData in ASP.NET Core MVC?
  3. How to use TempData?
  4. How do you Pass and Retrieve data from TempData?
  5. How do you retain TempData values in the Consecutive Request in ASP.NET Core MVC?
  6. How do you Store a Complex Object in TempData in ASP.NET Core MVC?
  7. What are the advantages and disadvantages of TempData in ASP.NET Core MVC?
  8. When should you use TempData in ASP.NET Core MVC?
Why do we need TempData in the ASP.NET Core MVC Application?

The limitation of both ViewData and ViewBag is they are limited to one HTTP request only. So, if redirection occurs, their values become null, meaning they will lose the data they hold. In many real-time applications, we may need to pass the data from one HTTP Request to the next subsequent HTTP Request. For example, we may need to pass the data from one controller to another, from one action method to another action method within the same controller, or to a different controller. Then, in such situations like this, we need to use TempData in the ASP.NET Core MVC Application.

What is TempData in ASP.NET Core MVC?

TempData in ASP.NET Core MVC Application is one of the mechanisms for passing a small amount of temporary data from a controller action method to a view and from a controller action method to another action method within the same controller or to a different controller. It is useful when passing data from one controller action to another, especially in scenarios like redirecting after form submissions.

The TempData value will become null by default once the subsequent request is completed. But you can also change this default behavior, and we will explain how to do this. Now, if you look at the definition of the Controller class, you will find the following signature of the TempData property.

What is TempData in ASP.NET Core MVC?

As you can see in the above image, the data type of the TempData is ITempDataDictionary. Let us see the definition of the ITempDataDictionary class.

Why do we need TempData in the ASP.NET Core MVC Application?

As you can see, the ITempDataDictionary class implements the IDictionary interface. So, we can say that TempData in ASP.NET Core MVC is a dictionary object. As a dictionary object, it stores data in the form of key-value pairs, where each key must be a string. The value we pass to the dictionary will be stored as an object type. Here, you can also see that to manage the TempData value in ASP.NET Core MVC, it provides 5 methods. The use of these methods is as follows:

Load:

The framework uses the Load method internally to load TempData from the underlying TempData provider when an HTTP request begins. You typically won’t need to use this method directly in your applications. It’s more of a system-level function that ensures TempData is available for your actions during an HTTP request.

Save:

Similar to Load, the Save method is also used internally by ASP.NET Core. It saves the current state of TempData back to the underlying TempData provider at the end of an HTTP request. This method maintains TempData across redirects because it ensures that any changes you’ve made during the request are persisted correctly.

Keep:

The Keep method marks all items in TempData to be retained for the next request. This method is useful when you want to ensure that TempData is not removed at the end of the current request, allowing it to be available for another subsequent request.

Keep(string key):

This overloaded version of the Keep method works like the general Keep method but allows you to specify a single key to retain in TempData. Only the TempData entry with this specified key will be preserved for the next request, while others will be discarded (unless they, too, are explicitly kept). This method is useful when you need to retain specific information.

Peek(string key)

The Peek method retrieves the value associated with the specified key without marking it for deletion when TempData is read. This is useful when you need to read a TempData value to display on a page but also need it to persist for another subsequent request. Unlike reading TempData using the String Indexer, which marks the item for deletion, Peek allows the data to be read and still remain in TempData for further requests.

How do you Pass and Retrieve data from TempData in ASP.NET Core MVC?

The most important point you need to remember is that it stores the data as an object, so while retrieving the data from TempData, type casting is required. If you are accessing string values from TempData, typecast is not required. However, it is mandatory to typecast explicitly to the actual type if you are accessing data other than the string type from the TempData.

Example to Understand TempData in ASP.NET Core MVC Application

We will use the same application we worked on in our previous article. Modify the HomeController to use TempData, as shown below. As you can see, we have created three action methods here. In the Index action method, we have set the Name and Age values using TempData, and in the other two action methods, we are not doing anything.

using Microsoft.AspNetCore.Mvc;
namespace FirstCoreMVCWebApplication.Controllers
{
    public class HomeController : Controller
    {
        public ActionResult Index()
        {
            TempData["Name"] = "Pranaya";
            TempData["Age"] = 30;
            return View();
        }
        public ActionResult Privacy()
        {
            return View();
        }
        public ActionResult About()
        {
            return View();
        }
    }
}

Next, modify the Index, Privacy and add the About Views within the Home Folder, which is inside the Views folder as follows:

Index.cshtml
@{
    ViewData["Title"] = "Index Page";
}

<div class="text-left">
    <b>Name:</b> @TempData["Name"]
    <br />
    <b>Age:</b> @TempData["Age"]
</div>
Privacy.cshtml
@{
    ViewData["Title"] = "Privacy Policy";
}

<div class="text-left">
    <b>Name:</b> @TempData["Name"]
    <br />
    <b>Age:</b> @TempData["Age"]
</div>
About.cshtml
@{
    ViewData["Title"] = "About Page";
}

<div class="text-left">
    <b>Name:</b> @TempData["Name"]
    <br />
    <b>Age:</b> @TempData["Age"]
</div>

The implementation of all three methods is the same. From each view, we access the TempData values using the String Indexer, i.e., using the string key name. Now, run the application and visit the Index Page, and you will get the data as expected, as shown in the image below.

How to Pass and Retrieve Data From TempData in ASP.NET Core MVC?

Now, if you visit Privacy and About, you will not get the data as expected, as shown in the image below.

Example to Understand TempData in ASP.NET Core MVC Application

Why are we not getting the TempData value in the next subsequent Request?

The reason is that once we read the value from TempData using the String Indexer, it will mark the item for deletion from the TempData dictionary collection. And this is the default behavior of TempData. In our example, we are reading the TempData within the Index View. Hence, after reading the Age and Name keys from TempData, these two keys will be deleted from the TempData dictionary collection.

How Do We Retain the TempData value in the next Sub Sequent Request in ASP.NET Core MVC?

We can retain the TempData values for the next subsequent request in many ways. Let us discuss them one by one.

Method 1: Don’t Fetch the Data from TempData

Suppose we don’t fetch the data from the TempData either from the Index Action Method or the Index View. In that case, the TempData will be preserved in the TempData dictionary collection and can be accessed from the next subsequent request. To do so, let us modify the Index.cshtml view as follows. As you can see, we are only fetching the Age key from TempData, not the Name key, which means the Name key will be preserved in the TempData dictionary collection for the next request.

@{
    ViewData["Title"] = "Index Page";
}

<div class="text-left">
    <b>Name:</b>
    <br />
    <b>Age:</b> @TempData["Age"]
</div>

Now, run the application, visit the Index page, and then visit either the Privacy or About Page, as shown in the image below. You can see that the age value is on the index page, and the name value is on the privacy page.

Why are we not getting the TempData value in the next subsequent Request?

Now, if you visit the About page, you will not see the data shown in the image below.

How to Retain the TempData value in the next Sub Sequent Request in ASP.NET Core MVC?

Method 2: Use the Keep Method to Preserve the Data in TempData

If we want to preserve the TempData for the next request, we can use the TempData Keep or Keep(string) Method. In this case, no matter whether you access the data or not from the TempData, it will preserve the TempData value for the next request. The Keep() method will Mark all keys in the dictionary for retention. On the other hand, the Keep(string key) method marks the specified key in the dictionary for retention.

To better understand, please modify the Home Controller as follows. Here, you can see inside the Index Action method we call the Keep method.

using Microsoft.AspNetCore.Mvc;
namespace FirstCoreMVCWebApplication.Controllers
{
    public class HomeController : Controller
    {
        public ActionResult Index()
        {
            TempData["Name"] = "Pranaya";
            TempData["Age"] = 30;

            //Retention of All keys of TempData for the next request
            //TempData.Keep();

            //Retention of Individual keys of TempData for the next request
            TempData.Keep("Name");
            TempData.Keep("Age");

            return View();
        }
        public ActionResult Privacy()
        {
            return View();
        }
        public ActionResult About()
        {
            return View();
        }
    }
}

Next, modify the Index.cshtml view as follows. As you can see, we are fetching both keys from the TempData Dictionary Collection.

@{
    ViewData["Title"] = "Index Page";
}

<div class="text-left">
    <b>Name:</b> @TempData["Name"]
    <br />
    <b>Age:</b> @TempData["Age"]
</div>

Now, run the application, visit the Index page, and then visit either the Privacy or About Page, as shown in the image below. Both the Index Page and Privacy Page show the Name and Age values.

Use the Keep Method to Preserve the Data in TempData in ASP.NET Core MVC

If you visit the About page, you will not see the data shown in the image below.

How to Preserve the TempData for the About Page?

How Do We Preserve the TempData for the About Page?

In that case, we need to call the Keep method inside the Privacy Action method. So, modify the Home Controller as follows:

using Microsoft.AspNetCore.Mvc;
namespace FirstCoreMVCWebApplication.Controllers
{
    public class HomeController : Controller
    {
        public ActionResult Index()
        {
            TempData["Name"] = "Pranaya";
            TempData["Age"] = 30;

            //Retention of All keys of TempData for the next request
            //TempData.Keep();

            //Retention of Individual keys of TempData for the next request
            TempData.Keep("Name");
            TempData.Keep("Age");

            return View();
        }
        public ActionResult Privacy()
        {
            //Retention of Individual keys of TempData for the next request
            TempData.Keep("Name");
            TempData.Keep("Age");
            return View();
        }
        public ActionResult About()
        {
            //Retention of Individual keys of TempData for the next request
            //TempData.Keep("Name");
            //TempData.Keep("Age");
            return View();
        }
    }
}

Method 3: Using TempData Peek Method

If we read the data using the string Indexer, the key will be deleted from the TempData Dictionary Collection by default once we read the value. So, instead of reading the values using the string Indexer, we can also read the data from TempData using the Peek method. To do this, we need to pass the key name to the Keep method. In this case, it will read the data but will preserve the key for the next subsequent request.

To Understand this concept, please modify the Home Controller class as follows. Inside the Index Action method, we store the data in TempData and redirect the request to the Privacy Action Method. As the Index View is not executed, we are not fetching the data from the TempData. So, these TempData keys are available for the next request, which is, in this case, the Privacy Action method. We are fetching the data from the Privacy action method using the Peek method, which will return the data and keep the keys alive for the next request. And inside the About Page, we can access the value.

using Microsoft.AspNetCore.Mvc;
namespace FirstCoreMVCWebApplication.Controllers
{
    public class HomeController : Controller
    {
        public ActionResult Index()
        {
            TempData["Name"] = "Pranaya";
            TempData["Age"] = 30;

            //We are redirecting the request to Privacy Action Method from here
            //In this case, Index View is not going to be executed
            //Means we are not reading the TempData keys and hence they available
            //in the Privacy Action method

            //return RedirectToAction("Privacy", "Home");
            return RedirectToAction("Privacy");
            
        }
        public ActionResult Privacy()
        {
            //Retention of Individual keys of TempData for the next request
            if(TempData.ContainsKey("Name"))
            {
                //Peek Method will read the data and preserve the key for next request
                ViewData["Name"] = TempData.Peek("Name");
            }

            if (TempData.ContainsKey("Age"))
            {
                //Peek Method will read the data and preserve the key for next request
                ViewData["Age"] = TempData.Peek("Age");
            }

            return View();
        }
        public ActionResult About()
        {
            return View();
        }
    }
}
Modifying Privacy.cshtml view:

Inside the Privacy.cshtml View, we need to use ViewData instead of Tempdata as follows:

@{
    ViewData["Title"] = "Privacy Policy";
}

<div class="text-left">
    <b>Name:</b> @ViewData["Name"]
    <br />
    <b>Age:</b> @ViewData["Age"]
</div>

With the above changes, run the application and see if everything works as expected. So, when you run the application, the Index action method will be redirected to the Privacy Action method. Then, if you visit the About action method, you will also get the data as expected, as shown in the image below.

Using TempData Peek Method

How Do We Store a Complex Object in TempData in ASP.NET Core MVC?

To retain a complex object in TempData in ASP.NET Core MVC, you need to serialize the object to a string format, typically JSON, and then deserialize it back when retrieving it. 

Serialize the Object to JSON

Before storing the complex object in TempData, you must convert it to a JSON string. This is because TempData can only store primitive types by default. You can use System.Text.Json.JsonSerializer or Newtonsoft.Json (aka JSON.NET) for serialization. The following is the syntax.

var myObject = new MyComplexObject();
string json = JsonSerializer.Serialize(myObject);
TempData["MyObject"] = json;
Retrieve and Deserialize the Object

When retrieving the object, get the JSON string from TempData and deserialize it to the original object type. The following is the syntax.

if (TempData["MyObject"] is string json)
{
    var myObject = JsonSerializer.Deserialize<MyComplexObject>(json);
    // Use myObject as needed
}
Handling TempData Persistence

If you need the data to persist for another request, you must read it and keep it again. The syntax is as follows.

string json = TempData["MyObject"] as string;
TempData.Keep("MyObject"); // This line keeps the data for another request
Creating the Model:

First, create the following Student class within the Models folder.

namespace FirstCoreMVCWebApplication.Models
{
    public class Student
    {
        public int StudentId { get; set; }
        public string? Name { get; set; }
        public string? Branch { get; set; }
        public string? Section { get; set; }
        public string? Gender { get; set; }
    }
}
Modifying the Home Controller:
using FirstCoreMVCWebApplication.Models;
using Microsoft.AspNetCore.Mvc;
using System.Text.Json;
namespace FirstCoreMVCWebApplication.Controllers
{
    public class HomeController : Controller
    {
        public ActionResult Index()
        {
            //Create the Complex Object
            var student = new Student()
            {
                StudentId = 1,
                Name = "Pranaya",
                Gender = "Male",
                Branch = "CSE",
                Section = "A"
            };

            //Convert the Complex Object to Json
            string jsonStudent = JsonSerializer.Serialize(student);

            //Store the JSON Objec into the TempData
            TempData["StudentObject"] = jsonStudent;

            //return RedirectToAction("Privacy", "Home");
            return RedirectToAction("Privacy");
        }
        public JsonResult Privacy()
        {
            Student? student = new Student();
            if (TempData["StudentObject"] is string jsonStudent)
            {
                //Deserialize the Json Object to Actual Student Object
                student = JsonSerializer.Deserialize<Student>(jsonStudent);
                //You can use the Student
                // The following line keeps the data for another request
              
                TempData.Keep("StudentObject"); 
            }
            return Json(student);
        }

        public JsonResult About()
        {
            Student? std = new Student();
            if (TempData["StudentObject"] is string jsonStudent)
            {
                //Deserialize the Json Object to Actual Student Object
                std = JsonSerializer.Deserialize<Student>(jsonStudent);
            }
            return Json(std);
        }
    }
}

Now, run the application and test it, and it should work as expected.

How TempData Works in ASP.NET Core MVC?

TempData is stored in short-lived session cookies and is cleared out after it has been read in a subsequent request. This makes it ideal for passing error messages, status messages, or other one-time-use data between actions. ASP.NET Core provides several storage providers for TempData:

  • SessionStateTempDataProvider: This is the default provider. It stores TempData using the session state. To use session-based TempData, you must enable the session state in your application.
  • CookieTempDataProvider: This provider stores TempData in cookies. It’s useful when you want to avoid using server memory for session state. However, be aware of the size limitations of cookies.

In the next article, I will discuss the Post-Redirect-Get (PRG) Pattern Example in the ASP.NET Core MVC Application with Examples. In this article, I try to explain TempData in the ASP.NET Core MVC Application with examples. I hope you enjoy this article on ASP.NET Core MVC TempData with Examples.

Leave a Reply

Your email address will not be published. Required fields are marked *