This article will tell you almost everything you need to know about passing data from Controller to View in ASP.NET MVC using TempData. I am writing this article to tell you the basic to advanced foremost concepts about ways to pass data from Controller to View. This article is the fourth one in the series named “Passing Data from Controller to View”. You’ll learn all the ways in each separate article. Stay tuned!
I would strongly recommend reading my previous articles, which will be defining the basic concepts of ASP.NET MVC.
Especially, read my consecutive previous articles in which I have taught the way of passing the data from Controller to View using ViewBag. This is the link to the previous article. Read this article, check the code after downloading, and then feel free to give your feedback.
The topics to be covered are,
- What is TempData?
- Passing the data from Controller to View using TempData
- Differing features of TempData from ViewBag and ViewData
- Maintaining the State of TempData to multiple requests
Introduction and background
As we know Controller is the class that is responsible to handle all the HTTP requests and then to execute the appropriate View. And View gives us the HTML markup that we display to the user. And for displaying anything on the View, there should be some data that is passed from Controller to View. And in this and next articles, you will learn how to pass data from Controller to View.
In this article, you’ll learn how to pass a strongly typed data from Controller to View using TempData. And, you’ll see other ways to pass data, in coming articles. So stay tuned!
What is TempData?
TempData is same as ViewBag and ViewData but also has more functionalities. It is actually a dictionary having a type TempDataDictionary and it is used to store the temporary data. TempData is also one of the properties of “ControllerBase” class so when we create a controller, that controller will automatically inherit the “Controller” abstract class and this “Controller” class inherits “ControllerBase” abstract class, that’s why we can access this TempData property in each controller. You can see in the image below the “Controller” class which inherits the “ControllerBase” class.
And in the “ControllerBase” class, the TempData property is defined, see its syntax below.
- namespace System.Web.Mvc
- {
-
- public abstract class ControllerBase : IController
- {
-
-
-
-
- public TempDataDictionary TempData { get; set; }
- }
- }
TempData is a constrainer in which we maintain the state of consecutive requests. It internally uses session variables. But we not need to clear these variables for TempData, it automatically clears its session variables. It requires typecasting for passing complex data and checking for null values to avoid errors. Let’s look at its main and simple functionality with the help of an example.
Passing the data from Controller to View using TempData
To pass the strongly typed data from Controller to View using TempData, we have to make a model class then populate its properties with some data and then pass that data to TempData as Value and selecting Key’s name is the programmer’s choice. And then in the View, we can access the data of model class by using TempData with the pre-defined keys. Let’s create a project to take a look at an example.
Go to File then New and select “Project” option.
Then create the ASP.NET web application project as depicted below.
Then select “Empty” and tick “MVC” then click OK.
The project is created successfully.
Now create a class named as “Employee” in the Models folder, shown below.
Now add some properties into this class as the code is given below.
- namespace DataCtoV.Models
- {
- public class Employee
- {
- [Display(Name = "Serial No")]
- public byte EmployeeId { get; set; }
-
- [Display(Name = "Name")]
- public string EmployeeName { get; set; }
-
- public string Address { get; set; }
-
- public string Phone { get; set; }
- }
- }
Now, we’ll add a controller from where this data of an employee will pass. Let’s create a Controller, as shown below.
Then, select “MVC 5 Controller– Empty” and click Add.
Then give the name of the Controller and click on Add.
The Controller is created successfully. In this Controller, we’ll make an action method with the name of “GetEmployeeData” in which we’ll make an object of “Employee” model class and populate this object with some data. Then pass this object to the TempData with the help of key named as “employee”. The code of “EmployeeDataController” is given below.
- namespace DataCtoV.Controllers
- {
- public class EmployeeDataController : Controller
- {
-
- public ActionResult GetEmployeeData()
- {
- List<Employee> emp = new List<Employee>
- {
- new Employee
- {
- EmployeeId = 1,
- EmployeeName = "John",
- Address = "12 Fremont St. Clermont, FL 2813",
- Phone = "+1-234-2838421"
- },
- new Employee
- {
- EmployeeId = 2,
- EmployeeName = "Smith",
- Address = "14 Highland Drive Fort Worth, TX 3994",
- Phone = "+1-234-2244521"
- },
- new Employee
- {
- EmployeeId = 3,
- EmployeeName = "Marry",
- Address = "23 Fremont Road Milledgeville, GA 6788",
- Phone = "+1-234-46568421"
- }
- };
-
- TempData["employee"] = emp;
-
- return View();
- }
- }
- }
Because we don’t have any View named as “GetEmployeeData” in the Views folder, let’s create it. For creating a View, right click on “GetEmployeeData” method and select “Add View…” option. The following dialogue box will open, click on “Add”
The View is created successfully. Let’s write the code for it.
- @using DataCtoV.Models
- @model IEnumerable<DataCtoV.Models.Employee>
- @{
- ViewBag.Title = "Employee Data";
- }
-
- <h3>Employee Data</h3>
- <table class="table table-condensed table-hover">
- <thead>
- <tr>
- <th>@Html.DisplayNameFor(e => e.EmployeeId)</th>
- <th>@Html.DisplayNameFor(e => e.EmployeeName)</th>
- <th>@Html.DisplayNameFor(e => e.Address)</th>
- <th>@Html.DisplayNameFor(e => e.Phone)</th>
- </tr>
- </thead>
- <tbody>
- @foreach (var employee in (IEnumerable<Employee>)TempData["employee"])
- {
- <tr>
- <td>@employee.EmployeeId</td>
- <td>@employee.EmployeeName</td>
- <td>@employee.Address</td>
- <td>@employee.Phone</td>
- </tr>
- }
- </tbody>
- </table>
You can see in the code that, we have made a table to represent the strongly typed data of the Employee model class. We have used foreach loop to iterate the data of each employee passed from the Controller.
To iterate the data, here we have used TempData which is calling the data from Controller with the help of key named as “employee”. And you can also see that we must have to cast the TempData to Employee.
Note
We must have to cast the TempData before using it.
Why casting?
As we know, TempData has type TempDataDictionary and this Dictionary has type “object”, and the foreach loop cannot accept variables having type “object”. In the object type, the GetEnumerator method is not defined that’s why we can’t iterate the data of Employee’s collection.
To iterate the data of Employee’s collection properly, we have to cast it to IEnumerable, because there a list/collection of Employees is coming and only in IEnumerable, the GetEnumerator is defined for iterating it properly. Hence we must have to cast it in the foreach loop. See the Error below without casting.
Ways of Casting
One way of casting the TempData is described above, which is at a time casting of TempData in the foreach loop. The code is given below.
Another way of casting the TempData is, cast the TempData in the Multi-Statement Razor Code block for C#, and then use the variable in the foreach loop. You can see code below:
Casting in the code block,
- @{
- ViewBag.Title = "Employee Data";
- var employeeData = (IEnumerable<Employee>)TempData["employee"]; }
Then, use the “employeeData” variable in the foreach loop, as shown below.
- @foreach (var employee in employeeData)
- {
- <tr>
- <td>@employee.EmployeeId</td>
- <td>@employee.EmployeeName</td>
- <td>@employee.Address</td>
- <td>@employee.Phone</td>
- </tr>
- }
All the code of “GetEmployeeData” View is given below for your convenience.
- @using DataCtoV.Models
- @model IEnumerable<DataCtoV.Models.Employee>
- @{
- ViewBag.Title = "Employee Data";
- var employeeData = (IEnumerable<Employee>)TempData["employee"];
- }
-
- <h3>Employee Data</h3>
- <table class="table table-condensed table-hover">
- <thead>
- <tr>
- <th>@Html.DisplayNameFor(e => e.EmployeeId)</th>
- <th>@Html.DisplayNameFor(e => e.EmployeeName)</th>
- <th>@Html.DisplayNameFor(e => e.Address)</th>
- <th>@Html.DisplayNameFor(e => e.Phone)</th>
- </tr>
- </thead>
- <tbody>
- @foreach (var employee in employeeData)
- {
- <tr>
- <td>@employee.EmployeeId</td>
- <td>@employee.EmployeeName</td>
- <td>@employee.Address</td>
- <td>@employee.Phone</td>
- </tr>
- }
- </tbody>
- </table>
You have seen the reason of casting and ways to do casting. Now simply, let’s build and run the application. You should see the following output.
Hence you have seen the practical example of TempData. Now let’s move towards its more features.
Differing features of TempData from ViewBag and ViewData
TempData is a container in which we maintain the state of consecutive requests. It internally uses session variables but we are not needed to clear these variables for TempData, it automatically clears its session variables. TempData stores the information only for an HTTP request mean to say from one page to another. TempData also works with 302 (Found) redirection and 301 (See Other) redirection because it’s in the same HTTP request. TempData helps to maintain the data from controller/action to another controller/action. You may say when you redirect, the TempData helps to maintain data between these redirects. Now, look at a practical example in which the redirection occurs.
For this, first, you have to make some changes in the “GetEmployeeData.cshtml” View. Comment all the code and write the following line of code.
- @{
- ViewBag.Title = "Employee Data";
- }
- <br />
- @Html.ActionLink("Click for Redirection", "SecondMethod", "EmployeeData")
The above line of code makes the redirection from “GetEmployeeData” action method to “SecondMethod” action method to show you that the TempData supports redirection while maintaining the data.
Now, you have to make another action method in the “EmployeeDataController” controller named as “SecondMethod”. The complete code of “EmployeeDataController” after making changes is as follows,
- namespace DataCtoV.Controllers
- {
- public class EmployeeDataController : Controller
- {
-
- public ActionResult GetEmployeeData()
- {
- List<Employee> emp = new List<Employee>
- {
- new Employee
- {
- EmployeeId = 1,
- EmployeeName = "John",
- Address = "12 Fremont St. Clermont, FL 2813",
- Phone = "+1-234-2838421"
- },
- new Employee
- {
- EmployeeId = 2,
- EmployeeName = "Smith",
- Address = "14 Highland Drive Fort Worth, TX 3994",
- Phone = "+1-234-2244521"
- },
- new Employee
- {
- EmployeeId = 3,
- EmployeeName = "Marry",
- Address = "23 Fremont Road Milledgeville, GA 6788",
- Phone = "+1-234-46568421"
- }
- };
-
- TempData["employee"] = emp;
-
-
- TempData.Keep();
-
- return View();
- }
-
- public ActionResult SecondMethod()
- {
-
- ViewBag.emp = TempData["employee"];
- return View();
- }
- }
- }
Now, we have to make the SecondMethod.cshtml view file in the Views folder. After making, the code will be as shown below.
- @model DataCtoV.Models.Employee
- @{
- ViewBag.Title = "Second";
- }
-
- <h2>Second</h2>
-
- <table class="table table-condensed table-hover">
- <thead>
- <tr>
- <th>@Html.DisplayNameFor(e => e.EmployeeId)</th>
- <th>@Html.DisplayNameFor(e => e.EmployeeName)</th>
- <th>@Html.DisplayNameFor(e => e.Address)</th>
- <th>@Html.DisplayNameFor(e => e.Phone)</th>
- </tr>
- </thead>
- <tbody>
- @foreach (var employee in ViewBag.emp)
- {
- <tr>
- <td>@employee.EmployeeId</td>
- <td>@employee.EmployeeName</td>
- <td>@employee.Address</td>
- <td>@employee.Phone</td>
- </tr>
- }
- </tbody>
- </table>
Now, simply build and run the application for this URL - /EmployeeData/GetEmployeeData. You should see the following output.
When you click on the link, you will redirect from the “GetEmployeeData” action method to the “SecondMethod” action method. And the output will be like below.
Hence you have seen the redirection while maintaining data using TempData. This is the feature that makes TempData different from ViewBag and ViewData because this feature is not present in ViewBag and ViewData.
Maintaining the State of TempData to multiple requests
In the previous section, you have maintained the state of data at the first request and made values accessible at second request. Now if you want to maintain the state up to third, fourth, and so on requests, then how can you do it?
This can be done by using a built-in “Keep” function with the TempData variables. Let’s look at its practical example by making some changes into “DataCtoV” project. So we make changes in “SecondMethod” by using the “Keep” function to maintain the state of data.
- public ActionResult SecondMethod()
- {
-
- ViewBag.emp = TempData["employee"];
-
-
- TempData.Keep();
-
- return View();
- }
Then go to its View named as “SecondMethod.cshtml” and add the following line of code to enable the redirection of request.
- @Html.ActionLink("Click for 2nd redirection","ThirdMethod","EmployeeData")
And then, add another action method named as “ThirdMethod” into the “EmployeeDataController”. Code of “ThirdMethod” is as follows,
- public ActionResult ThirdMethod()
- {
-
-
- ViewBag.third = TempData["employee"];
- return View();
- }
Now, create its view and place the following code in it.
- @model DataCtoV.Models.Employee
- @{
- ViewBag.Title = "ThirdMethod";
- }
-
- <h2>ThirdMethod</h2>
-
- <table class="table table-condensed table-hover">
- <thead>
- <tr>
- <th>@Html.DisplayNameFor(e => e.EmployeeId)</th>
- <th>@Html.DisplayNameFor(e => e.EmployeeName)</th>
- <th>@Html.DisplayNameFor(e => e.Address)</th>
- <th>@Html.DisplayNameFor(e => e.Phone)</th>
- </tr>
- </thead>
- <tbody>
- @foreach (var employee in ViewBag.third)
- {
- <tr>
- <td>@employee.EmployeeId</td>
- <td>@employee.EmployeeName</td>
- <td>@employee.Address</td>
- <td>@employee.Phone</td>
- </tr>
- }
- </tbody>
- </table>
Now, I am providing the full code of each file only for your convenience.
The complete code of “Employee” model class is as below.
- namespace DataCtoV.Models
- {
- public class Employee
- {
- [Display(Name = "Serial No")]
- public byte EmployeeId { get; set; }
-
- [Display(Name = "Name")]
- public string EmployeeName { get; set; }
-
- public string Address { get; set; }
-
- public string Phone { get; set; }
- }
- }
The complete code of “EmployeeDataController” is given below.
- namespace DataCtoV.Controllers
- {
- public class EmployeeDataController : Controller
- {
-
- public ActionResult GetEmployeeData()
- {
- List<Employee> emp = new List<Employee>
- {
- new Employee
- {
- EmployeeId = 1,
- EmployeeName = "John",
- Address = "12 Fremont St. Clermont, FL 2813",
- Phone = "+1-234-2838421"
- },
- new Employee
- {
- EmployeeId = 2,
- EmployeeName = "Smith",
- Address = "14 Highland Drive Fort Worth, TX 3994",
- Phone = "+1-234-2244521"
- },
- new Employee
- {
- EmployeeId = 3,
- EmployeeName = "Marry",
- Address = "23 Fremont Road Milledgeville, GA 6788",
- Phone = "+1-234-46568421"
- }
- };
-
- TempData["employee"] = emp;
-
- return View();
- }
-
- public ActionResult SecondMethod()
- {
-
- ViewBag.emp = TempData["employee"];
-
-
- TempData.Keep();
-
- return View();
- }
-
- public ActionResult ThirdMethod()
- {
-
-
- ViewBag.third = TempData["employee"];
- return View();
- }
-
- }
- }
The complete code of “GetEmployeeData.cshtml” view is as below.
- @using DataCtoV.Models
- @model IEnumerable<DataCtoV.Models.Employee>
- @{
- ViewBag.Title = "Employee Data";
- var employeeData = (IEnumerable<Employee>)TempData["employee"];
- }
-
- <h3>Employee Data</h3>
- <br />
- @Html.ActionLink("Click for first Redirection", "SecondMethod", "EmployeeData")
-
- <table class="table table-condensed table-hover">
- <thead>
- <tr>
- <th>@Html.DisplayNameFor(e => e.EmployeeId)</th>
- <th>@Html.DisplayNameFor(e => e.EmployeeName)</th>
- <th>@Html.DisplayNameFor(e => e.Address)</th>
- <th>@Html.DisplayNameFor(e => e.Phone)</th>
- </tr>
- </thead>
- <tbody>
- @foreach (var employee in employeeData)
- {
- <tr>
- <td>@employee.EmployeeId</td>
- <td>@employee.EmployeeName</td>
- <td>@employee.Address</td>
- <td>@employee.Phone</td>
- </tr>
- }
- </tbody>
- </table>
Complete code of “SecondMethod” is follows,
- @model DataCtoV.Models.Employee
- @{
- ViewBag.Title = "Second";
- }
-
- <h2>Second</h2>
-
- @Html.ActionLink("Click for 2nd redirection", "ThirdMethod", "EmployeeData")
-
- <table class="table table-condensed table-hover">
- <thead>
- <tr>
- <th>@Html.DisplayNameFor(e => e.EmployeeId)</th>
- <th>@Html.DisplayNameFor(e => e.EmployeeName)</th>
- <th>@Html.DisplayNameFor(e => e.Address)</th>
- <th>@Html.DisplayNameFor(e => e.Phone)</th>
- </tr>
- </thead>
- <tbody>
- @foreach (var employee in ViewBag.emp)
- {
- <tr>
- <td>@employee.EmployeeId</td>
- <td>@employee.EmployeeName</td>
- <td>@employee.Address</td>
- <td>@employee.Phone</td>
- </tr>
- }
- </tbody>
- </table>
Complete code of “ThirdMethod” is as follows,
- @model DataCtoV.Models.Employee
- @{
- ViewBag.Title = "ThirdMethod";
- }
-
- <h2>ThirdMethod</h2>
-
- <table class="table table-condensed table-hover">
- <thead>
- <tr>
- <th>@Html.DisplayNameFor(e => e.EmployeeId)</th>
- <th>@Html.DisplayNameFor(e => e.EmployeeName)</th>
- <th>@Html.DisplayNameFor(e => e.Address)</th>
- <th>@Html.DisplayNameFor(e => e.Phone)</th>
- </tr>
- </thead>
- <tbody>
- @foreach (var employee in ViewBag.third)
- {
- <tr>
- <td>@employee.EmployeeId</td>
- <td>@employee.EmployeeName</td>
- <td>@employee.Address</td>
- <td>@employee.Phone</td>
- </tr>
- }
- </tbody>
- </table>
Now, simply build and run the application with the URL /EmployeeData/GetEmployeeData to see the output. Output should be as follows,
Just click on the link “Click for first Redirection” then its corresponding HTTP request will execute and give the following output.
Above is the first redirection in which the state of TempData is maintained. And this data will pass to “ThirdMethod” after clicking on the link “Click for 2nd redirection” then the output will be like this.
Hence in this way, you can maintain the state of TempData up to multiple requests.
Summary
In this article, you have learned that how to pass strongly typed data from Controller to View using TempData, in which firstly, you should make a model class then populate its properties with some data then pass that object to the TempData as Value and pass magic Key as a string. Then you have looked the main differing feature of TempData with ViewBag and ViewData. Also, you have learned how to maintain the state of TempData up to multiple requests.
Conclusion
I hope this article has helped you in understanding the concepts about passing strongly typed data from Controller to View using TempData in ASP.NET MVC. Stay tuned for my next articles because this article is the fourth one in the series of “Passing data from Controller to View” and you’ll learn more about passing data in coming articles. If you have any query, please feel free to contact me in the comments section. Also, do provide the feedback whether positive or negative. It will help me to make my articles better and increase my enthusiasm to share my knowledge.