Table of Contents
This tutorial series on learning API with ASP.NET Core will focus on ASP.NET Core features, request pipeline, how to create ASP.NET core API and how to use Entity Framework Core. We’ll try to create an API with ASP.NET Core and try to make the communication happen with database to perform simple CURD operations via Entity framework Core. The series will contain continuation articles to cover the topic in detail and end up having a functional application.
Prerequisites
Since we start from the beginning, it is expected that the reader of this article/series is new to ASP.NET Core and does not really have insight into what is it all about. Having said that, we’ll stick to our aim of starting and learning ASP.NET Core from scratch. We’ll use Visual Studio 2017 Enterprise Edition for the entire series, but one can also use Visual Studio 2015 or the community editions of Visual Studio. The best part about ASP.NET Core applications is that they can also be developed with Visual Studio codes which executes at OS X and Linux. To check the requests and response from the API, we’ll use a tool named Postman. It’s free and easy to use. Alternatively one can use the tool of choice for e.g. Fiddler.
RoadMap
We’ll follow a roadmap to learn and cover all the aspects of ASP.NET Core in detail. The following is the roadmap or list of articles that will cover the entire series.
- Create API with ASP.NET Core (Day 1): Getting Started and ASP.NET Core Request Pipeline
- Create API with ASP.NET Core (Day 2): Create an API and return resources in ASP.NET Core
- Create API with ASP.NET Core (Day 3): Working with HTTP Status Codes, Serializer Settings and Content Negotiation in ASP.NET Core API
- Create API with ASP.NET Core (Day 4): Understanding Resources in ASP.NET CORE API
- Create API with ASP.NET Core (Day 5): Inversion of Control and Dependency Injection in ASP.NET CORE API
- Create API with ASP.NET Core (Day 6): Getting Started with Entity Framework Core
- Create API with ASP.NET Core (Day 7): Entity Framework Core in ASP.NET CORE API
ASP.NET Core
There always has been a buzz with Microsoft to provide something open source, cross platform and more or less related to mobility. So, in general, ASP.NET Core is the answer to that buzz. It is an open source framework with cross platform capabilities which could be leveraged to build cloud-based applications that are internet connected. One can develop any kind of application like, normal web applications, API or mobile based applications. Its beauty of being open source and cross platform enables a developer to also contribute to the code or customize the code available as per the need or requirement and cross the platform barrier and develop the applications for Windows, Mac and as well as for Linux. Another interesting offering with ASP.NET Core is that it could be run on full .NET framework or on only .NET Core. We know what .NET framework is, but what is .NET Core? So in simple words, .NET Core is the modular version of .NET Framework or one can say that it is a subset of the full .NET Framework.
"ASP.NET Core is a lean and composable framework for building web and cloud applications. ASP.NET Core is fully open source and available on GitHub. ASP.NET Core is available on Windows, Mac, and Linux." from https://www.asp.net/core
We call it modular because it is released via NuGet in assembly packages rather than one large assembly that contains most of the core functionality. When we read about .NET Core, we also come across something called .NET Standard. .NET Standard is a standard which specifies a common layering that a platform should support and .NET Core is the implementation by Microsoft for that .NET Standard.
Installing ASP.NET Core
For Visual Studio 2017, .NET Core Tools is included in the installer. One can find the installation guide at https://www.microsoft.com/net/core#windowsvs2017.
But if someone uses Visual Studio 2015, installing .NET Core tools is not that tough; one can download .NET Core SDK and tooling for Visual Studio. The current .NET Core version is 1.1, but that too depends on when you are reading this article, so the version may be different depending upon when one is reading this post. One can find all the installation related SDK, tooling and platform specific installers at:
https://www.microsoft.com/net/download/core.
As soon as .NET Core is installed, one can start creating .NET Core projects. To verify that .NET Core is installed, open your Visual Studio, navigate to File-> New Project, and one can see the .NET Core project templates installed there.
.NET Core Project and its Structure
Moving on to some hands on exercise, we’ll create a sample ASP.NET Core project and try to understand the project structure and other details. We’ll create a fresh ASP.NET Core web application from scratch.
So, open your Visual Studio, navigate to File -> New project where you can see the available .NET CORE templates, and filter for ASP.NET Core web applications as shown in following image.
After filtering, we can see two options available in the templates, one saying to create a ASP.NET Core Web Application using >NET Core and other says using the .NET Framework. We earlier discussed the difference between .NET Core applications and .NET Framework applications and also know that ASP.NET Core web applications can be developed using any of the two options depending upon our choice and need. We’ll choose the .NET Core option as we just need to focus on this area and do not really require other capabilities of the complete .NET Framework. We’ll try to create an API that returns information of employees. So we’ll name our API as EmployeeInfo.API, and name the solution as EmployeeInfo as shown in the following image.
Click OK, and we get the list of templates we need to choose to create our application. When we choose the template, the other dependent and additional files will be added to the project via Nuget.
Note that we can also choose the current ASP.NET Core version i.e. 1.1 or the earlier stable version as well that was 1.0. Out of three available templates, since we are in process of creating an API, we could choose Web API template but that again may end up downloading unnecessary Nuget packages and default controller structure that we do not require. The purpose of this article is to make a .NET Core application from scratch to have better understanding/concept. So to understand each and every thing let’s start from the empty template so that we have full control to add what exactly we want. So Choose "Empty" and press the OK button. Nuget restore will download the required packages to support empty template that we chose, and we see that the empty project created also contains some structure and basic code as shown in following image.
We got a solution named EmployeeInfo and a project named EmployeeInfo.API i.e. our ASP.NET Core project. There are two classes added i.e. Program.cs and Startup.cs. We can closely look into these classes and understand them.
Program.cs
Program.cs acts as a starting point of the application like every other console application in .NET. It contains the Main method as the starting point. So we see that ASP.NET Core in general is a console application that talks to ASP.NET specific components and libraries. Application configuration and execution is the responsibility of Main
method here. We know that to run a web application, it needs to be hosted and we also need to do that. So if we closely look into the Main
method, we see that WebHostBuilder
is initialized and since we host the web application, there is a need of web server now. The beauty of ASP.NET Core is that it is decoupled from the environment that web server provides for hosting the web application. It is accompanied with two HTTP servers. The first is WebListener, for example, a Windows based web server. Another is Kestrel, for example, a web server for cross platform application hosting. So the statement UseKestrel
signifies Kestrel is the default. Since we currently are inside Visual Studio so it will by default use IIS Express as a default host. The statement UseIISIntegration
specifies that IIS Express works as a reverse proxy server for Kestrel. So if there is a need to deploy the ASP.NET Core application on a windows server, one should run IIS as a reverse proxy server for Kestrel, and in case application has to be deployed on Linux, one should use a comparable reverse proxy server like Apache to proxy requests to Kestrel.
One can independently self-host the application using Kestrel, but using IIS as a reverse proxy gets a lot of advantages. For example, IIS can filter requests, manage the SSL layer and certificates, and make sure the application restarts if it crashes, and so on.
The UseContentRoot
statement signifies the root directory of content used by the web host. As default, the content root remains same as the application base part for the executable that is hosting the application. One can specify an alternate location as per need via passing location in the UseContentRoot
statement, but for now we can stick to the default current directory. The line UseStartup
signifies the startup type that has to be used by the web host. Startup is the second class that we got in the empty web application at the time of creation. The "Build" statement means that it builds an iWeb host instance to host our web app. At the end, host.run will eventually run the application and blocks the calling thread till the host shuts down completely.
Startup.cs
Theoretically, the Startup
class is the entry point for an application. As shown in the image, it contains two methods. The ConfigureServices
method is used to add and configure services to the container that is used for dependency injection. A service in context of ASP.NET Core is a component that is created for common consumption in an application. For example, there are framework related services, such as Identity MVC Entity framework core services, but there are again also application services which then are application specific. For example, we can add an application specific service to send a mail or logging that could be made available for dependency injection via registering it in ConfigureServices
method.
The Configure
method takes IApplicationBuilder
, IHostingEnvironment
and ILoggerfactory
instances provided by the container. Note that ConfigureServices
is an optional method. But applications at some point of time will require at least some services that are not already automatically registered. The Configure method is called after the ConfigureServices
method because it uses services that are registered and configured in that method. It specifies the behavior of ASP.NET Core application on individual HTTP requests. This is the place where our application in upcoming articles will handle HTTP requests with the help of MVC. Currently as per default implementation, each and every HTTP request will print Hello World on the screen. So when we run the application, first as expected, ConfigureServices
will be called then Configure method will be called that prints Hello World on the screen. You can check the control flow by putting break points and running the application.
ASP.NET Core Middleware and Request Pipeline
When we get an HTTP request to the application, there has to be an HTTP response to that, and internally the request is handled to generate response and send. The components that are involved in handling the requests and generating results in response are responsible to make up the request pipeline. We can always add a middle ware component to that pipeline in between to handle the requests and responses. In earlier or older versions of ASP.NET, there was a concept of modules and handlers that use to take care of this request sand responses. In ASP.NET Core this is done by middleware. For example, a middleware could be added in the request pipeline to handle authentication and authorization.
MVC has its own middleware that could be added to the request pipeline. Whenever a request comes, it comes inside a request pipeline, and a request pipeline contains the list of requests those are delegated one after another from one middleware component to another.
Each middleware has an option to perform operations before receiving and after delegating the request and eventually generate the response needed. So each middleware component decides whether to delegate the request onto next component or not. For example, authentication middleware component if finds the request is not authorized, it will not pass the request to next component in the pipeline and return the response result from its own component.
Configure Request Pipeline
Let’s try to configure the request pipeline of ASP.NET Core. We’ll try to configure it in a way that a developer friendly exception page is shown as soon as an exception is thrown from the application. We already have an empty application template that we created and if we check the Configure
method of the Startup
class we see app.UseDeveloperExceptionPage()
method called within Configure
method and it is called by first checking if the application is in the developer environment or not, so half of our work is already done by this empty template.
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
This method basically configures our request pipeline in a way that it adds the middleware of developers exception page, so when now an exception will be thrown in developers mode, this middleware is responsible to handle that.
Press F12 on this method to see the assemble details and we find that it is the part of assemble Microsoft.AspNetCore.Diagnostic
.
Likewise one can found various middleware in various separate assemblies. That shows the modularity of ASP.NET Core.
Let’s check what happens in case any exception has occurred. So we’ll modify the Configure method and throw exception instead of showing "Hello World".
public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
{
loggerFactory.AddConsole();
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.Run(async (context) =>
{
throw new Exception("Test Dev Exception Page");
});
}
So, since we have already configured the request pipeline to show the details of exception on developer’s exception page, we should ideally see one. So run the application and an exception is thrown, since we are throwing an exception knowingly, continue with the exception by pressing F5 and we see a developer’s exception page as shown below.
Since this is a developer’s exception page, it will only be shown during development and not when the application is in production.
If we navigate to the Debug tab inside project properties as shown in following image.
We find an environment variable named ASPNETCORE_ENVIRONMENT
set to "Development" ASP.NET Core refers a unique environment variable and hosting environment to maintain the environment an application is currently running in. It could be set to one of the three conventional values. Those are Development, Staging and Production, but the good thing is that we can add our own also.
These values could be accessed programmatically and we make use of IHostingEnvironment service.
From env variable, one can access all the information related to hosting environment as shown below.
Since we needed to developer’s exception page is shown when app is in development mode, we used the UsedeveloperExceptionPage
, else we would have catch the exception or logged it, and to do so, ASP.NET Core also provides a middleware (for example, exception handler middleware). One can pass parameters to the UseExceptionHandler()
method (for example, to show a user friendly error page).
For now let’s stick to our default implementation.
Let’s try to change the development environment to Production
Now run the application, we get a friendly error page, that could be made more meaningful, when a parameter is passed to the UseExceptionHandler()
method.
Now to check the exception here, open developer’s tool (for example, press F12 on the page). In the Console, we see the exception has been thrown twice.
One for the favorite icon and another one that was expected from the application. That means that exception handler middleware also logs the exception, so which part is responsible for logging the exception? Going back to the Configure
method, we see the ILoggerFactory
injected by default, and that is responsible for logging the exception. We’ll cover this topic in detail in later parts of the series.
Conclusion
In this article, we learned about ow to get started with ASP.NET Core. We learnt that ASP.NET Core is open source and made to build cross platform cloud based internet applications. We figured out that how it is different from complete .NET Framework. We also explored how to install and create a basic service application with ASP.NET Core and explored what are request pipelines and middleware. We also learnt about how to configure the request pipeline through middle ware and got some interesting insights of ASP.NET Core. Next Article..
Source Code on Github
Source Code
References
Other Series
My series of articles: