ASP.NET Core MVC Anchor Tag Helper

In today’s post in my series on the ASP.NET Core MVC Tag Helpers, I will explore the Anchor tag helper. This tag helper is used generate href attributes to link to a particular controller action or MVC route.

This tag helper is an alternative to using `@Html.ActionLinkor@Url.Action` helper methods. For example, the following code in a Razor view:

@Html.ActionLink("Register", "Register", "Account")

<a href="@Url.Action("Register", "Account")">Register</a>

…would generate 2 identical anchor html tags.

<a href="/Account/Register">Register</a>
<a href="/Account/Register">Register</a>

Using the anchor tag helper, we can generate the same HTML as above by adding the asp-controller and asp-action attributes to an anchor tag as follows:

<a asp-controller="Account" 
asp-action="Register">Register</a>

In simple examples like the one above, there is very little difference between the tag helper approach and the _@Url.Action_ approach. The advantage of tag helpers over the @Html.ActionLink approach is that we can add html attributes or content to the a tag and those will be merged with the generated output. Adding attributes to the a tag was particularly clumsy with the @Html.ActionLink.

Adding Route Parameters

In some cases, you might need to specify additional parameters for the controller action that you are binding to. You can specify values for these parameters by adding attributes with the asp-route- prefix. For example, you might need to specify the id of a product you are linking to, you would add a asp-route-id attribute as follows:

<a asp-controller="Product" 
asp-action="Display"
asp-route-id="@ViewBag.ProductId">

View Details</a>

…would generate the following html when ViewBag.Id = 1:

<a href="/Product/Display/1">View Details</a>

You can specify values for as many parameters as you need using attributes with the asp-route- prefix.

Named Routes

Another option is to specify the controller and action using a named route. For example, if your application had a route named login defined as follows in your MVC route configuration:

routes.MapRoute(
name: "login",
template: "login",
defaults: new { controller = "Account", action = "Login" });

then you can bind an anchor tag to that route as follows:

<a asp-route="login">Login</a>

Protocol, Host and Fragment

The anchor tag helper also has options for specifying the protocol, host and fragment for the generated URL. These are useful if you want to override the defaults to force https or link to a particular portion of a page. To do this using the `@Html.ActionLink` approach, you would need to use the overload that accepts all possible options:

@Html.ActionLink("Register", "Register", "Account",  "https", "aspecificdomain.com", "fragment", null, null)

Notice that you need to specify null for the last 2 parameters (route values and html attributes). This would generate the following HTML:

<a href="https://aspecificdomain.com/Account/Register#fragment">Register</a>

If all you wanted to do was specify https for the current domain, you would need to pass null to 4 parameters:

@Html.ActionLink("Register", "Register", "Account",  "https", null, null, null, null)

With the tag helper approach, you can use any combination of the asp-protocol, _asp-host _and asp-fragment attributes you want. This avoids messing around with method overloads that contain parameters you don’t care about in the current context. The result is a much cleaner syntax that, in my opinion, is easier for the reader to understand:

<a asp-controller="Account" 
asp-action="Register"
asp-protocol="https"
asp-host="asepecificdomain.com"
asp-fragment="fragment">Register</a>


<!--or with the protocol only -->
<a asp-controller="Account"
asp-action="Register"
asp-protocol="https">Register</a>

Conclusion

That wraps up the functionality provided by the anchor tag helper in ASP.NET Core MVC. In the next post in this series we will explore the Cache tag helper.