Developing Web Applications In
Developing Web Applications In
Abstract: There are many approaches available for developing a web application in .NET. In this article, I will give an overview of frameworks that you can
choose for your .NET projects.
Models are a representation of the application state. They encapsulate the business logic necessary to retrieve the state from and persist it back to the data
store (often a relational database), as well as to perform the operations modifying the state.
Controllers respond to all user requests. Their main role is to map the request to the underlying models which implement the business logic, select the
correct view for presenting the requested data to the user, and pass it the model with that data.
Views are responsible for rendering the resulting web page to the user. They read all the necessary data from the model passed to them. To avoid too
much logic in a view, the controller can instead pass a specialized view model which serves as a wrapper or data transfer object (DTO) for the model data.
The pattern prescribes how the different building blocks can interact. A controller interacts with both models and views, a view only interacts with models, and a
model interacts neither with controllers nor with views.
Figure 1: Interaction between the model, the view and the controller
The MVC architectural pattern is often used in web development frameworks for a reason. It works well with the stateless model of the HTTP protocol:
The HTTP request received by the web server is routed to the controller with all the required information to perform the requested action.
The controller interacts with the model and finally invokes the view with the required data.
The output generated by the view is sent back by the web server as the HTTP response.
Figure 2: HTTP request handling with the MVC pattern
The MVC application architecture is most suitable for development of web applications that benefit from being fully rendered on the server, i.e. those that need to
be easily indexable by search engines and don’t require a lot of quick user interaction. Examples of such applications are publicly accessible web portals and
dynamic web sites.
Are you a .NET, C#, Cloud or Web Developer looking for a resource covering New Technologies,
in-depth Tutorials and Best Practices?
Well, you are in luck! We at DotNetCurry release a FREE digital magazine once every few months
aimed at Developers, Architects and Technical Managers. This magazine covers ASP.NET Core,
Xamarin, C#, Patterns and Practices, .NET Core, ASP.NET MVC, Azure, DevOps, ALM,
TypeScript, Angular, React, Vuejs and much more.
Subscribe to this magazine for FREE and receive the current and upcoming editions, right in
your Inbox. No Spam Policy.
Click here to Download the Latest Edition For Free
ASP.NET Core
Of the two MVC frameworks for .NET, ASP.NET Core is the modern one. It was released as part of.NET Core which means that it can run on Windows as well
as on Linux and macOS. It is the recommended framework for development of new web applications following the MVC architectural pattern.
In Visual Studio 2019, a new project can be created using the ASP.NET Core Web Application template. The recommended choice in the second step of the
project creation wizard is Web Application (Model-View-Controller) which will generate a simple sample app. If you’re using Visual Studio Code, you can create
an equivalent new project from the command line with the following command:
dotnet new mvc
Each building block type has its own folder in the project structure.
- Controller classes are placed in the Controllers folder. They derive from the Controller base class. Their methods are called action methods and serve
as entry points handling the requests:
public class HomeController : Controller
{
public IActionResult Error()
{
return View(new ErrorViewModel { RequestId = Activity.Current?.Id ??
HttpContext.TraceIdentifier });
}
}
- The Views folder contains views. By convention, they are placed in a subfolder matching the name of the controller which will be using them. Their name
matches the action methods they will be used in. Hence, the Views/Home/Index.cshtml file would contain the default view for
the HomeController.Index action method. The .cshtml extension indicates that the views are using Razor syntax which combines regular HTML with
additional Razor markup which starts with the @ symbol:
@model ErrorViewModel
@{
ViewData["Title"] = "Error";
}
<h1 class="text-danger">Error.</h1>
<h2 class="text-danger">An error occurred while processing your request.</h2>
@if (Model.ShowRequestId)
{
<p>
<strong>Request ID:</strong> <code>@Model.RequestId</code>
</p>
}
- The classes in the Models folder fit the definition of view models. They are typically instantiated in action methods and are usually wrappers or data transfer
objects with minimal business logic.
public class ErrorViewModel
{
public string RequestId { get; set; }
ASP.NET MVC
ASP.NET MVC is the predecessor of ASP.NET Core.
It runs on top of the .NET framework (with no support for .NET Core) and is not actively developed anymore. Applications written in ASP.NET MVC must be
hosted in IIS on Windows. ASP.NET MVC should usually not be used for creating new web applications anymore. ASP.NET Core should be used instead (on top
of .NET Core if possible, or .NET framework if necessary).
On the surface, ASP.NET MVC appears similar to ASP.NET Core. The project structure contains the same three core folders:
Controllers folder with controller classes derived from the Controller base class which implement action methods.
Views folder with views which use Razor syntax.
Models folder with model (or view model) classes.
However, there is only limited built-in support for dependency injection with no implementation provided out-of-the-box. To inject services with business logic into
a controller, a third-party dependency injection library implementing the provided interfaces must be added to the project and properly configured.
Although the default routing of requests to action methods in controllers follows the same convention as in ASP.NET Core projects, it is configured elsewhere
and with slightly different code which you can find in the RegisterRoutes method of the RouteConfig class:
routes.MapRoute(
name: "Default",
url: "{controller}/{action}/{id}",
defaults: new
{
controller = "Home",
action = "Index",
id = UrlParameter.Optional
}
);
There is also no customizable request pipeline. To hook into a request, several different approaches can be used, depending on what needs to be achieved:
HTTP handlers are used for extension-based request processing. ASP.NET MVC itself is implemented as an HTTP handler which executes action methods
in controllers.
HTTP modules are used to hook into the processing of every HTTP request (ASP.NET MVC or not) and are typically used for authentication, logging etc.
Action filters are a part of ASP.NET MVC and can be invoked before or after the action method call, but always after the ASP.NET MVC HTTP handler has
already taken over the processing.
From the three approaches above, only action filters are still available in ASP.NET Core. The other two must be converted to middleware. This can make it
difficult to port an existing ASP.NET MVC application to ASP.NET Core unless it is very simple. Usually it makes sense to keep maintaining it in ASP.NET MVC,
especially if there isn’t a lot of new development being done and the application is not required to run on other operating systems than Windows.
Using attributes, such requests can be routed to the appropriate action methods:
// POST api/values
[HttpPost]
public void Post([FromBody] string value)
{
}
// PUT api/values/5
[HttpPut("{id}")]
public void Put(int id, [FromBody] string value)
{
}
// DELETE api/values/5
[HttpDelete("{id}")]
public void Delete(int id)
{
}
The .NET framework predecessor of ASP.NET Core for building REST services is ASP.NET Web API. It’s architecturally similar to ASP.NET MVC.
For the same reasons as ASP.NET MVC, it’s not a recommended choice for new projects, but it makes sense for existing projects to keep using it.
JavaScript frameworks
There’s an abundance of client-side JavaScript frameworks for single-page applications to choose from. Currently, the most popular ones are Angular, React,
and Vue.js.
Although there are a lot of differences between them, they consist of the same basic building blocks:
Templates for the HTML pages to be displayed with support for binding values from variables and for handling events such as clicks.
JavaScript (or TypeScript) code that reacts to those events by changing the bound values or switching the HTML template which is currently displayed.
Command line tooling for building the application, for running it locally during development and for other common operations.
@Component({
selector: 'app-fetch-data',
templateUrl: './fetch-data.component.html'
})
export class FetchDataComponent {
public forecasts: WeatherForecast[];
You can decide for yourself how you want to build and host each one. To simplify this, there are ASP.NET Core templates available for Angular and React which
join both parts into a single project:
In Visual Studio 2019, you can choose these templates in the second step of the ASP.NET Core Web Application template. They are named: Angular,
React.js, and React.js and Redux.
When using the dotnet new command, the template names are: angular, react and reactredux.
Editorial Note: For ASP.NET Core Vue.js Templates, check Daniel’s article www.dotnetcurry.com/aspnet-core/1500/aspnet-core-vuejs-template.
No matter which template you choose, the client-side JavaScript application will be placed in the ClientApp folder. It will be a standard application for the
chosen framework which can be fully controlled using its corresponding command line tooling.
In addition to that, the JavaScript application will be fully integrated into the ASP.NET Core application. The generated static files will be hosted as static files in
the ASP.NET Core application. During development, the application will also automatically refresh in the browser whenever you change any of its source files.
When starting a new Angular or React application with an ASP.NET Core backend, these templates are probably your best starting point. They make
development and deployment more convenient because you don’t have to deal with two separate projects.
Blazor
With increasing support for WebAssembly in modern browsers, JavaScript isn’t the only supported language for applications running in a browser anymore.
WebAssembly is a binary format designed to be generated by compilers on one hand, and directly executed in browsers on the other hand. This is opening the
doors to frameworks for single-page application development which aren’t JavaScript (or TypeScript) based.
The one most interesting to .NET developers is Blazor which allows you to write your client-side code in C#. Since it’s still in preview, it requires some effort to
get it installed. For best experience you will require:
To create a new project, use the ASP.NET Core Web Application template in Visual Studio 2019. In the second step of the wizard, select Blazor (ASP.NET Core
hosted). You need to have NET Core 3.0 selected in the dropdowns at the top to make it available.
To create a project from the command line instead, you first need to install the Blazor templates:
dotnet new -i Microsoft.AspNetCore.Blazor.Templates::3.0.0-preview4-19216-03
dotnet new blazorhosted
The generated solution is functionally similar to the projects generated by the ASP.NET Core SPA templates. It consists of three projects:
*.Server contains the ASP.NET Core application with the web API.
*.Client contains the Blazor single-page application.
*.Shared contains classes which can be shared between the two projects because they both use the same language.
The ASP.NET Core application is almost identical to the one for the JavaScript SPA frameworks. The Blazor application is functionally very similar to the Angular
and React applications as well. It’s just developed using a different technology which makes the code more similar to an ASP.NET Core MVC application than a
JavaScript SPA.
The source code for both pages and components is placed in *.razor files, and it uses Razor syntax:
@page "/fetchdata"
@using AspNetCoreBlazor.Shared
@inject HttpClient Http
<h1>Weather forecast</h1>
Most importantly, the framework is still in preview and no official release has been announced yet. It will almost certainly be released after .NET Core 3.0.
The current implementation of Blazor is very inefficient. The code is not compiled directly to WebAssembly. Instead, it is compiled into a .NET assembly
which is interpreted in the browser with a .NET runtime which was compiled to WebAssembly. This might still change until the final release.
WebAssembly currently can’t access DOM (Document Object Model) APIs directly. It can only call JavaScript functions which then interact with the DOM.
Since DOM APIs are used for any client-side modification of the HTML page, this negatively affects WebAssembly performance in this field.
At least until the first official release of Blazor, JavaScript frameworks are a superior choice for development of single-page applications. Blazor is currently only
an interesting experiment showing what might be possible in the future. To learn more about it, you can read a dedicated article about it in the DNC Magazine
written by Daniel Jimenez Garcia: Blazor - .NET in the browser.
MVC applications run on the server, while SPAs run on the client. With the former, the browser acts as a thin client sending user requests to the server and
rendering the received responses for the user. With the latter, the browser is a fat client which only needs the web server to get the application files at the
beginning and to retrieve additional data while the application is running.
The programming model of MVC applications fully exposes the nature of the web: every interaction is an HTTP request and every response is the new state
of the web page. The SPA programming model is much more similar to desktop applications. User interactions trigger event handlers which modify the
existing page currently displayed in the browser. HTTP requests are only used for data access operations (and loading of static files).
There’s a third category of applications which are a hybrid between the two approaches. They are running on the server, but their programming model is event-
driven, “hiding” the request/response nature of the web from the developer.
.NET developers can choose between two frameworks for development of such applications.
Razor components
Razor components were originally named Blazor server-side. That name is a pretty good description of what they are about.
A Razor components application is an ASP.NET Core application configured to run Blazor code on the server. This means that the .NET Standard assemblies
built from the .razor files are not interpreted in the browser. Instead, the browser is only running a small SignalR-based JavaScript library which
uses WebSockets for real-time communication with the server where those assemblies are running.
The requirements for using Razor components are currently the same as for Blazor: the latest previews of .NET Core 3.0 SDK and Visual Studio 2019 are
recommended. To create a new project in Visual Studio 2019, the ASP.NET Core Web Application template must be used, and the Razor Components option
must be selected in the second step of the wizard.
From command line the same can be achieved using the following command:
dotnet new blazorserverside
In the generated solution, there’s only a single project because all the code is running on the server. The setup code specific to running Razor components on
the server is placed in the Startup class. The code in the .razor files in the Pages folder is almost identical to the code from the Blazor sample project. The
only important difference can be found in the @functions block of the FetchData.razor file:
@functions {
WeatherForecast[] forecasts;
However, since the code is running on the server, the browser must be constantly connected to it. As soon as the connection is broken, the application stops
working. There’s no way to support offline mode with this approach, unlike SPAs which can continue working without interruption even with no internet
connection, at least until they require new data from the server.
When Razor components are officially released with .NET Core 3.0, they will become a viable alternative to JavaScript frameworks for development of highly
interactive web applications, at least for scenarios where reliable connectivity to the server is not an issue. If you strictly use REST service calls for retrieving data
which would reside on the server if the application was a SPA, you might even be able to convert your application to a Blazor SPA without too much effort when
Blazor is officially released.
ASP.NET Web Forms have no successor available for .NET Core. This means that your application will only run on Windows and there’s no path available
for migrating the code to .NET Core in the future.
There’s no active development on ASP.NET Web Forms anymore. There were only a few minor new features added in recent versions of the .NET
frameworks, and you can expect even less of that in the future.
You have limited control over the generated HTML when using ASP.NET Web Forms. This can be an issue when having to exactly implement a specific
design or make the page responsive for mobile devices and different screen sizes.
For existing ASP.NET Web Forms applications, you don’t have a lot of choice. You will have to keep maintaining them in their current form unless you decide for
a complete rewrite in one of the other development frameworks described in previous sections.
Conclusion:
There are many approaches available for developing a web application in .NET. However, in most cases, you will choose between two of them based on the type
of the application you’re developing.
For content-focused public sites which depend on good indexing by search engines, the best fit is usually an MVC web application in ASP.NET Core.
For web applications with a lot of user interaction, potentially protected by a login, a single-page application (SPA) in your preferred JavaScript framework
with an ASP.NET Core web API backend is often a better choice.
For real-world applications which usually fall somewhere in between the two extremes, the advantages and disadvantages of each approach should be
carefully considered when making the choice for one or the other.
With the release of .NET Core, Razor components will become a good alternative to JavaScript SPAs if you prefer C# to JavaScript (or TypeScript) and the
requirement for a constant connection to the web server is not a serious limitation for your application.
The web frameworks in the .NET framework are not really recommended for starting the development of new applications. Instead, you should use .NET Core.
For existing applications developed using the .NET framework, you can keep maintaining them using the same technology, unless you require features the
framework does not support, e.g. you want to run your application on Windows, as well as other operating systems too.
This article has been editorially reviewed by Suprotim Agarwal.
C# and .NET have been around for a very long time, but their constant growth means there’s always more to learn.
We at DotNetCurry are very excited to announce The Absolutely Awesome Book on C# and .NET . This is a 500 pages concise technical eBook
available in PDF, ePub (iPad), and Mobi (Kindle).
Organized around concepts, this Book aims to provide a concise, yet solid foundation in C# and .NET, covering C# 6.0, C# 7.0 and .NET Core, with chapters
on the latest .NET Core 3.0, .NET Standard and C# 8.0 (final release) too. Use these concepts to deepen your existing knowledge of C# and .NET, to have a
solid grasp of the latest in C# and .NET OR to crack your next .NET Interview.
Using Blazor WebAssembly, SignalR and C# 9 to create Full-stack Real time Applications