Introduction to ASP.NET Core part 13: the view imports file
February 15, 2017 Leave a comment
Introduction
In the previous post we looked at data annotation to refine our view models. Data annotations are attributes that can be applied to properties of the view models that are injected into the views. These attributes can be put into three groups: validation, display and data type attributes. Validation attributes can help us filter out the most obvious bad entries from the forms. They can make a field required or they can declare that a property must have a certain minimum and/or maximum value. The Display attribute changes the corresponding property label in the view. The data type attributes declare what kind of editor a certain property needs. E.g. the URL data type gives a hint to the view to render an input of type URL. If the browser has built-in validation for the various input types then it offers an extra layer of validation.
In this post we’ll discuss a very specific view file called the view imports file. As usual we’ll be working in our demo web application DotNetCoreBookstore.
The _ViewImports.cshtml file
There are two special types of cshtml file in ASP.NET Core MVC. This post discusses the one called _ViewImports.cshtml. We’ll take up the other one called _ViewStart.cshtml in the next post.
The name _ViewImports.cshtml is important. MVC will look for that file in the various folders that contain our views. We can put common using statements in them that will be automatically injected into the views. There can be one _ViewImports.cshtml file in a single folder.
We’ll start with an example for all the views in the Books folder in our demo application: Create, Details and Index.cshtml. They all require a view model that resides in the DotNetCoreBookstore.Models namespace:
@model DotNetCoreBookstore.Models.InsertBookViewModel @model DotNetCoreBookstore.Models.BookDetailsViewModel @model DotNetCoreBookstore.Models.BookIndexViewModel
Another way of writing these declarations is with a using statement, here’s an example:
@using DotNetCoreBookstore.Models @model BookIndexViewModel
We can factor out the using statements into a single _ViewImports.cshtml file. MVC will look for that file and execute it before running the specific view files.
Right-click on the Views/Books folder and add a file of type MVC View Imports Page:
Add a single using statement to it:
@using DotNetCoreBookstore.Models
We can now simplify the model declarations in the three Book-related views:
@model BookIndexViewModel @model InsertBookViewModel @model BookDetailsViewModel
The web app will continue to work like before.
In the above example the Books folder had its own view imports file which will be applied to all views in the Views/Books folder. Other folders with views in them won’t be affected.
If there are namespaces that should be imported into every single view then we must place the view imports file directly to the Views folder like here:
Imagine that we want to work with files in all our views – or at least in enough of them to warrant a view-wide import of the System.IO namespace. Add the following using statement to the view imports file we’ve just inserted:
@using System.IO
We can now go to any of the views and try to reach an object in the System.IO namespace. Here’s an example:
@File.ReadAllText(@"myfile.txt") @foreach (var bookViewModel in Model.BookViewModels) { <tr> <td>@bookViewModel.Id</td> <td>@bookViewModel.Author</td> <td>@bookViewModel.Title</td> <td>@Html.ActionLink("Details", "Details", "Books", new { id = bookViewModel.Id}, new { @class = "book-details-link"} )</td> </tr> }
There won’t be any compilation error, the File object is available for all views in the web application. If you run the application now it will fail of course since there’s no file called myfile.txt. So make sure you either comment out or delete the call to ReadAllText.
We’ll continue in the next post with the view start file.
View the list of MVC and Web API related posts here.