visit
This article is a logical continuation of upgrading the nopCommerce project - a free open-source CMS for creating online stores. Last time we talked about our experience in migrating nopCommerce from ASP.NET MVC to ASP.NET Core 2.2. In this article, we will look at the migration to .NET Core 3.1.
.NET Core 3.1 will be until December 2022, so migration is a hot topic right now. If you want to take full advantage of the updated framework, keep up with technological innovations, and the growing global trends then it's time to start the migration.
Generic Host
In .NET Core 2.1 Generic Host is an addition to the Web Host. It allows you to use tools such as dependency injection (DI) and logging abstractions. .NET Core 3 emphasized the greater compatibility with Generic Host, so you can now use the updated Generic Host Builder instead of Web Host Builder.This allows to create any kind of application, from console applications and WPF to web applications, on the same basic hosting paradigm with the same common abstractions.public class Program
{
public static void Main(string[] args)
{
CreateHostBuilder(args).Build().Run();
}
public static IHostBuilder CreateHostBuilder(string[] args)
{
return Host.CreateDefaultBuilder(args)
.UseServiceProviderFactory(new AutofacServiceProviderFactory())
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder
.UseStartup<Startup>();
});
}
}
{
"sdk": {
"version": "3.1.201",
"rollForward": "latestFeature",
"allowPrerelease": false
}
}
It will also give you a guarantee that users of your application will run it exactly on those SDK assemblies that you have defined, and not the latest version installed on their server.
ASP.NET Core Module V2
<PropertyGroup>
<TargetFramework>netcoreapp3.1</TargetFramework>
<Copyright>Copyright (c) Nop Solutions, Ltd</Copyright>
<Company>Nop Solutions, Ltd</Company>
<Authors>Nop Solutions, Ltd</Authors>
<Version>4.4.0.0</Version>
<Description>Nop.Web is also an MVC web application project, a presentation layer for public store and admin area.</Description>
<PackageLicenseUrl>//www.nopcommerce.com/license</PackageLicenseUrl>
<PackageProjectUrl>//www.nopcommerce.com/</PackageProjectUrl>
<RepositoryUrl>//github.com/nopSolutions/nopCommerce</RepositoryUrl>
<RepositoryType>Git</RepositoryType>
<!--Set this parameter to true to get the dlls copied from the NuGet cache to the output of your project-->
<CopyLocalLockFileAssemblies>true</CopyLocalLockFileAssemblies>
<AspNetCoreHostingModel>InProcess</AspNetCoreHostingModel>
<!--When true, compiles and emits the Razor assembly as part of publishing the project-->
<RazorCompileOnPublish>false</RazorCompileOnPublish>
</PropertyGroup>
Endpoint Routing
In .NET Core 2.1, routing was done in Middleware (ASP.NET Core MVC middleware) at the end of the HTTP request pipeline. This means that information about the route, such as what controller action will be taken, was not available for the middleware that processed the request before the MVC middleware in the request pipeline. Starting with .NET Core 2.2, a new endpoint-based routing system was introduced. This routing concept addresses the aforementioned issues. Endpoint Routing is now built differently in .NET Core 3.1. The routing phase is separated from the call to the endpoint. This way we have two intermediate middlewares:EndpointMiddleware
- calls the endpointEndpointRoutingMiddleware
- this determines which endpoint will be called for each path of the URL request and essentially acts as a routing/// <summary>
/// Configure Endpoints routing
/// </summary>
/// <param name="application">Builder for configuring an application's request pipeline</param>
public static void UseNopEndpoints(this IApplicationBuilder application)
{
//Add the EndpointRoutingMiddleware
application.UseRouting();
//Execute the endpoint selected by the routing middleware
application.UseEndpoints(endpoints =>
{
//register all routes
EngineContext.Current.Resolve<IRoutePublisher>().RegisterRoutes(endpoints);
});
}
С# 8.0 syntactic sugar
In addition to updating the .NET Core itself, a new version of C # 8.0 was also released. There are a lot of updates. Some of them are fairly global, others involve cosmetic improvements, giving developers "syntactic sugar".After we upgraded our nopCommerce application, it was necessary to check how performance increased in our case. For users, this is one of the most important criteria when choosing an eCommerce platform.
Tests were run on Windows 10 (10.0.19041.388), where IIS 10 (10.0.19041.1) acted as a proxy for the Kestrel web server on the same machine. To simulate the high load, we used Apache JMeter, which allows us to simulate a very serious load with many parallel requests. For the test, we have specially prepared a database typical for an average online store.
The number of products was about 50,000 items, the number of product categories was 516 with random nesting, the number of registered users was about 50,000, and the number of orders was about 80,000 with a random inclusion of 1 to 5 products. All this was running by MS SQL Server 2017 (14.0.2014.14).
JMeter ran multiple load tests generating a summary measurement report for each request each time. The averaged results after several runs are presented below.
Test time is about 20% faster (less is better).
It is also important to note that, as always, .NET Core pays a lot of attention to security issues. By the way, since the release of .NET Core 3.1.0, a number of updates have already been released (the latest version is currently 3.5.1) including security updates.
A very important point is that .NET Core 3.1 is the next LTS version after 2.1, which guarantees us and our customers support and receiving the latest fixes, including security patches. Therefore, it is important for us to move forward with the release of the LTS versions of .NET Core. will be the next global release, and moving your application to .NET Core 3.1 is the best way to prepare for that.