asp.net core 3.0 更新简记

Intro

最近把活动室预约项目从 asp.net core 2.2 更新到了 asp.net core 3.0,记录一下,升级踩过的坑以及经验总结,包括但不限于

  • TargetFramework (netcoreapp2.2 需要更新为 netcoreapp3.0)
  • Dependency
  • Host/Environment
  • Mvc
  • Routing
  • Swagger
  • Dockerfile
  • EF(不推荐更新)

TargetFramework 更新

原来项目里的 netcoreapp2.x 版本需要更新为 netcoreapp3.0,原来有些基于 netstandard2.0 的项目的包如果有包更新之后依赖 netstandard2.1 可能需要更新为 netstandard2.1(非必须,看项目依赖)

Dependency

原来在 dotnetcore 2.x 版本时大部分的包以 nuget 的形式提供,可以直接通过 nuget 引用,从 dotnetcore 3.0 开始很多包不再发布 nuget 包,需要通过框架引用来引用包(FrameworkReference)

比如在一个类库项目 <Project Sdk="Microsoft.NET.Sdk"> 里有这么一个引用 <PackageReference Include="Microsoft.AspNetCore.Mvc.Core" Version="2.2.2" />,在 dotnetcore 3.0 并没有发布对应的 nuget 包,需要使用框架引用,示例如下:

<FrameworkReference Include="Microsoft.AspNetCore.App" />

如果是 Web 项目 <Project Sdk="Microsoft.NET.Sdk.Web">,Sdk 是 Web 的话直接把 targetFramework 更新的 netcoreapp3.0 就可以了,不需要再添加上面的引用了,项目里 <PackageReference Include="Microsoft.AspNetCore.App"/> 的引用也可以直接移除了

Host && Environment

原来的 IHostingEnvironment 改为了 IWebHostEnvironment,原来注入 IHostingEnvironment 的地方需要修改为注入 IWebHostEnvironment

原来 Program 里使用的 WebHostBuilder 改为 HostBuilder 并配置 ``ConfigureWebHostDefaults ,变更如下:

MVC

服务注册

3.0 里 MVC 对 ControllerRazorPages 以及 RazorViews 整理,注入服务的时候我们可以只注入自己需要的服务,如果是 WebAPI 项目可以只添加 Controller 需要的服务即可,对应的添加方式:

services.AddControllers(); // WebAPI
services.AddControllersWithViews(); // MVC
services.AddRazorPages(); // RazorPage

JSON 配置

asp.net core 3.0 默认使用微软新的 JSON,但是推荐还是用 Newtonsoft.Json,比较成熟而且对很多比较特殊的情况都有处理,已然成为了.NET 里 JSON 序列化的事实标准,使用方式如下:

  1. 引用 nuget 包 Microsoft.AspNetCore.Mvc.NewtonsoftJson

  2. 配置使用 Newtonsoft.Json

services.AddControllersWithViews()
.AddNewtonsoftJson(options =>
{
options.SerializerSettings.ContractResolver = new DefaultContractResolver();
options.SerializerSettings.DateTimeZoneHandling = DateTimeZoneHandling.Utc; // 设置时区为 UTC
});

Rounting

asp.net core 3.0 推荐使用 endpoint rounting

配置方式如下:

           app.UseStaticFiles();

            app.UseSwagger()
.UseSwaggerUI(c =>
{
// c.RoutePrefix = string.Empty; //
c.SwaggerEndpoint($"/swagger/{ApplicationHelper.ApplicationName}/swagger.json", "活动室预约系统 API");
c.DocumentTitle = "活动室预约系统 API";
}); app.UseRouting(); // 放在 UseStaticFiles 之后 app.UseCors(builder => builder.AllowAnyHeader().AllowAnyMethod().AllowAnyOrigin()); app.UseRequestLog();
app.UsePerformanceLog(); app.UseAuthentication();
app.UseAuthorization(); // 放在 UseAuthentication 之后 app.UseEndpoints(endpoints =>
{
endpoints.MapControllers(); // 属性路由
endpoints.MapControllerRoute("Notice", "/Notice/{path}.html", new
{
controller = "Home",
action = "NoticeDetails"
}); // 自定义路由
endpoints.MapControllerRoute(name: "areaRoute", "{area:exists}/{controller=Home}/{action=Index}"); // 区域路由
endpoints.MapControllerRoute("default", "{controller=Home}/{action=Index}/{id?}"); // 默认路由
});

Swagger

更新 swagger 依赖到最新的 5.0.0-rc-x 版本(还没发稳定版,需要显示预览版本才能看到)

services.AddSwaggerGen(options =>
{
options.SwaggerDoc(ApplicationHelper.ApplicationName, new Microsoft.OpenApi.Models.OpenApiInfo { Title = "活动室预约系统 API", Version = "1.0" }); options.IncludeXmlComments(System.IO.Path.Combine(AppContext.BaseDirectory, $"{typeof(Models.Notice).Assembly.GetName().Name}.xml"));
options.IncludeXmlComments(System.IO.Path.Combine(AppContext.BaseDirectory, $"{typeof(API.NoticeController).Assembly.GetName().Name}.xml"), true);
});

更多参考:

https://www.cnblogs.com/laozhang-is-phi/p/11520048.html#autoid-6-0-0

https://www.cnblogs.com/weihanli/p/ues-swagger-in-aspnetcore3_0.html

Docker

Dockerfile 里基础镜像需要更新到 3.0

示例 dockerfile:

FROM mcr.microsoft.com/dotnet/core/sdk:3.0-alpine AS build-env
WORKDIR /src # Copy csproj and restore as distinct layers
COPY ActivityReservation.Common/*.csproj ActivityReservation.Common/
COPY ActivityReservation.Models/*.csproj ActivityReservation.Models/
COPY ActivityReservation.DataAccess/*.csproj ActivityReservation.DataAccess/
COPY ActivityReservation.Business/*.csproj ActivityReservation.Business/
COPY ActivityReservation.Helper/*.csproj ActivityReservation.Helper/
COPY ActivityReservation.WechatAPI/*.csproj ActivityReservation.WechatAPI/
COPY ActivityReservation.AdminLogic/*.csproj ActivityReservation.AdminLogic/
COPY ActivityReservation.API/*.csproj ActivityReservation.API/
COPY ActivityReservation/ActivityReservation.csproj ActivityReservation/ # RUN dotnet restore ActivityReservation/ActivityReservation.csproj
## diff between netcore2.2 and netcore3.0
WORKDIR /src/ActivityReservation
RUN dotnet restore # copy everything and build
COPY . .
RUN dotnet publish -c Release -o out ActivityReservation/ActivityReservation.csproj # build runtime image
FROM mcr.microsoft.com/dotnet/core/aspnet:3.0-alpine LABEL Maintainer="WeihanLi"
WORKDIR /app
COPY --from=build-env /src/ActivityReservation/out .
EXPOSE 80
ENTRYPOINT ["dotnet", "ActivityReservation.dll"]

修改基础镜像一般不会有什么问题,需要注意的是如果 dockerfile 里有用到 dotnet publish 且publish 的项目不在当前目录下,可能会遇到这样的问题,最后找不到要发布的文件。

dotnet core 3.0 cli 有个 breaking change,如果要发布的项目不在当前目录下,在 2.x 版本是会发布到项目文件所在目录下的,但是 3.0 版本会发布在当前目录下,比如说执行dotnet publish -c Release ./src/ActivityReservation.csproj -o out命令:

2.x版本会在 src目录下生成一个 out 文件夹

3.0 版本会在当前目录下生成一个 out 文件夹,out文件夹和 src 同级

详细问题可以参考 https://github.com/dotnet/cli/issues/12696

EF

EF Core 3.0 和 asp.net core 3.0 完全独立,可以在 asp.net core 3.0 的项目里使用 2.x 的 EF Core

EF Core 3.0 有个 breaking change,不再隐式支持客户端渲染数据,这可以让你更清晰的知道哪些条件和在数据库执行的哪些条件是在本地执行的,但是实际试用下来,还是有很多问题的,在 EF 的基础上封装了一层,试用表达式树来拼接查询条件,但是最后执行的时候会有问题,但是简化后的条件实际上并不会在客户端执行任何过滤操作,所以暂时不推荐试用 ef core 3.0,而且更新之后可能会遇到其他的问题,比如在 docker alpine 中部署可能会遇到这个问题,详见issue https://github.com/aspnet/EntityFrameworkCore/issues/18025

现在的项目使用 ef core2.1 + asp.net core3.0 运行

More

其他的地方应该也有需要修改的地方,欢迎补充

Reference

asp.net core 3.0 更新简记的更多相关文章

  1. ASP.NET Core 1.0 开发记录

    官方资料: https://github.com/dotnet/core https://docs.microsoft.com/en-us/aspnet/core https://docs.micro ...

  2. 微软推出ASP.NET Core 2.0,并支持更新Visual Studio 2017

    微软推出ASP.NET Core 2.0的一般可用性,并发布.NET Core 2.0.该公司还推出了其旗舰集成开发环境(IDE)的更新:Visual Studio 2017版本15.3和Visual ...

  3. .NET Core 3.0预览版7中的ASP.NET Core和Blazor更新

    .NET Core 3.0 Preview 7现已推出,它包含一系列ASP.NET Core和Blazor的新更新. 以下是此预览中的新功能列表: 最新的Visual Studio预览包括.NET C ...

  4. asp.net core 3.0 中使用 swagger

    asp.net core 3.0 中使用 swagger Intro 上次更新了 asp.net core 3.0 简单的记录了一下 swagger 的使用,那个项目的 api 比较简单,都是匿名接口 ...

  5. .NET Core & ASP.NET Core 1.0在Redhat峰会上正式发布

    众所周知,Red Hat和微软正在努力使.NET Core成为Red Hat企业版Linux (RHEL)系统上的一流开发平台选项.这个团队已经一起工作好几个月了,RHEL对.NET有许多需求.今天在 ...

  6. ASP.NET 5 RC1 升级 ASP.NET Core 1.0 RC2 记录

    升级文档: Migrating from DNX to .NET Core Migrating from ASP.NET 5 RC1 to ASP.NET Core 1.0 RC2 Migrating ...

  7. .NET跨平台之旅:将示例站点从 ASP.NET 5 RC1 升级至 ASP.NET Core 1.0

    终于将“.NET跨平台之旅”的示例站点 about.cnblogs.com 从 ASP.NET 5 RC1 升级至 ASP.NET Core 1.0 ,经历了不少周折,在这篇博文中记录一下. 从 AS ...

  8. ASP.NET Core 1.0 静态文件、路由、自定义中间件、身份验证简介

    概述 ASP.NET Core 1.0是ASP.NET的一个重要的重新设计. 例如,在ASP.NET Core中,使用Middleware编写请求管道. ASP.NET Core中间件对HttpCon ...

  9. 跨平台运行ASP.NET Core 1.0

    前言 首先提一下微软更名后的叫法: ASP.NET 5 更名为 ASP.NET Core 1.0 .NET Core 更名为 .NET Core 1.0 Entity Framework 7 更名为  ...

随机推荐

  1. Codeforces Round #385 (Div. 2) C - Hongcow Builds A Nation

    题目链接:http://codeforces.com/contest/745/problem/C 题意:给出n个点m条边,还有k个不能连通的点,问最多能添加几条边. 要知道如果有n个点最多的边是n*( ...

  2. CH 4302 Interval GCD 题解

    题意 给定一个长度为N的数列A,以及M条指令 (N≤5* 10^5, M<=10^5),每条指令可能是以下两种之一: "C l r d",表示把 A[l],A[l+1],-, ...

  3. Tomcat9控制台中文乱码的解决方案

    1.网上大部分都是这种方法 注释掉 tomcat 9 安装目录下的conf里的 logging.properties 找到 java.util.logging.ConsoleHandler.encod ...

  4. 史上最全Docker环境安装指南-让安装docker简单到爆

    一.思考❓❔ 1.什么是Docker? 装应用的容器 开发.测试.运维都偏爱的容器化技术 轻量级 扩展性 一次构建.多次分享.随处运行 2.安装Docker难不难? So easy! 此文看过之后,读 ...

  5. Nacos配置服务原理

    Nacos Client配置机制 spring加载远程配置 在了解NACOS客户端配置之前,我们先看看spring怎么样加载远程配置的.spring 提供了加载远程配置的扩展接口 PropertySo ...

  6. Docker入门到实践——简单操作

    1.对比传统虚拟机总结 特性 容器 虚拟机 启动 秒级 分钟级 硬盘使用 一般为MB 一般为GB 性能 接近原生 弱于 系统支持量 单机支持上千个容器 一般几十个 2.基本概念 Docker包括三个基 ...

  7. win7 安装mysql5.7

    Windows 64 位 mysql 5.7以上版本包解压中没有data目录和my-default.ini以及服务无法启动的解决办法以及修改初始密码的方法 LZ初学SQL,本来以为开源的安装很简单,但 ...

  8. Hive bucket表

    Hive 桶 对于每一个表(table)或者分区, Hive可以进一步组织成桶,也就是说桶是更为细粒度的数据范围划分.Hive也是 针对某一列进行桶的组织.Hive采用对列值哈希,然后除以桶的个数求余 ...

  9. Nightmare Ⅱ(双向BFS)

    Problem Description Last night, little erriyue had a horrible nightmare. He dreamed that he and his ...

  10. 新建Servlet工程——IDEA

    Servlet是sun公司提供的一套接口规范,是运行在服务端的java程序.实现了Servlet的类能够被服务器识别,而普通的java类不能被识别. 1.新建工程 2. 3.工程名字“: 4.在WEB ...