Working With ViewData in Razor Pages

ViewData is a container for data to be passed from the PageModel to the content page. ViewData is a dictionary of objects with a string-based key. You add items to ViewData as follows:

public class IndexModel : PageModel
{

    public void OnGet()
    {
        ViewData["MyNumber"] = 42;
        ViewData["MyString"] = "Hello World";
        ViewData["MyComplexObject"] = new Book { 
                                    Title = "Sum Of All Fears",  
                                    Author = new Author { Name = "Tom Clancy" },
                                    Price = 5.99m
                                    };
    }
}

The ViewData dictionary is automatically made available to the content page. Therefore, in order to reference values stored in it, you just refer to their item by key:

@page
@model IndexModel
@{
}
<h2>@ViewData["MyString"]</h2>
<p>The answer to everything is @ViewData["MyNumber"]</p>

When working with complex values, you need to cast them to their correct type in the content page:

@page
@model IndexModel
@{
    var book = (Book)ViewData["MyComplexObject"];
}

<h2>@book.Title</h2>
<p>@book.Author.Name</p>
<p>@book.Price</p>

ViewData Attribute

The ViewData attribute was introduced in ASP.NET Core 2.1. PageModel properties decorated with this attribute are automatically added as keys to the ViewData dictionary along with any value that has been assigned to them. In the following example, the Message property has been automatically added to ViewData:

public class IndexModel : PageModel
{
    [ViewData]
    public string Message { get; set; }

    public void OnGet()
    {
        Message = "Hello World";
    }
}

Now the Message property can be accessed in the view via the Model property or the ViewData dictionary:

@page
@model IndexModel
@{
    
}

<h2>@Model.Message</h2>
<h2>@ViewData["Message"]</h>

You should prefer to access properties of the Model in a content page because you benefit from strong typing: IntelliSense and compile-time checking. So why should you use the ViewData attribute on model properties? The real benefit of this feature comes when working with layout pages. ViewData is shared with the layout page (and any partial pages called by the content page or the layout), so the attribute makes it easy to pass typed data from the PageModel to the layout page or partials without having to explicitly assign it to the ViewData dictionary.

Building on the previous example, the following snippet is a partial named _HelloWorldPartial:

<p>@ViewData["Message"] from the Hello World partial</p>

This is called from within the layout page using the partial tag helper:

<partial name="_HelloWorldPartial" />

The PageModel Message property was set in the OnGet handler and assigned to ViewData via the attribute, which ensures that it is passed from content page to layout to partial where it is rendered:

ViewData in Razor Pages

Last updated: 05/09/2018 08:35:59

© 2018 - Learn Razor Pages.
All rights reserved.