最近公司要求netcore版本從2.2升級到3.1,升級需要修改的配置項和遇到的問題我這邊做一個簡單的總結。
可參考資料:
https://docs.microsoft.com/zh-cn/ef/core/what-is-new/ef-core-3.x/breaking-changes
netcore3.1 下載:
https://dotnet.microsoft.com/download/dotnet/3.1
升級之后使用VS2019以及以上版本哦
一、 配置項修改
1. netcore版本修改為3.1
2. Nuget包升級
(1)刪除包: Microsoft.AspNetCore.App
(2)刪除包:Microsoft.AspNetCore.Razor.Design
(3)升級包版本:Swashbuckle.AspNetCore 升級到5.0.0及以上
3. Program類修改
IWebHostBuilder 修改為IHostBuilder
代碼如下:

Microsoft.Extensions.Hosting.Host.CreateDefaultBuilder(args) .ConfigureWebHostDefaults(webBuilder => { webBuilder.UseStartup<Startup>() .ConfigureLogging((hostingContext, logging) => { logging.AddConsole(); }) .UseKestrel(op => { op.ListenAnyIP(5000, listenOptions => { listenOptions.Protocols = HttpProtocols.Http1; }); op.Limits.MaxRequestBodySize = null; }); }) .UseCastleWindsor(HKIocManager.Instance.IocContainer);
4. Startup類修改:
(1) IHostingEnvironment修改為IWebHostEnvironment
(2) ConfigureServices方法返回結果由IServiceProvider修改為void
(3) services.AddMvc()修改為 services.AddControllers().AddNewtonsoftJson()
注意:方法名結尾的async會自動取消。
比如:定義的方法名為SearchMemberAsync(),但是在請求方法SearchMemberAsync時提示沒有此方法 ,請求SearchMember方法時卻請求成功
為了方法名結尾不取消async,配置SuppressAsyncSuffixInActionNames參數為false。
代碼如下:

services.AddControllers(options => { options.SuppressAsyncSuffixInActionNames = false; }).AddNewtonsoftJson();
(4) swagger配置修改:
代碼如下:

services.AddSwaggerGen(options => { options.CustomSchemaIds(z => z.FullName); options.SwaggerDoc("v1", new OpenApiInfo { Title = "自定義 API", Version = "v1" }); options.DocInclusionPredicate((s, b) => true); options.IncludeXmlComments(Path.Combine(_environment.ContentRootPath, "XMLDocument", "自定義.xml")); options.IncludeXmlComments(Path.Combine(_environment.ContentRootPath, "XMLDocument", "自定義.xml")); options.AddSecurityDefinition("Bearer", new OpenApiSecurityScheme() { Description = "JWT 授權. Example: \"Authorization: Bearer {token}\"", Name = "Authorization", In = ParameterLocation.Header, Type = SecuritySchemeType.ApiKey, Scheme = "bearer", BearerFormat = "JWT" }); options.AddSecurityRequirement(new OpenApiSecurityRequirement { { new OpenApiSecurityScheme { Reference = new OpenApiReference { Id = "Bearer", Type = ReferenceType.SecurityScheme } }, Array.Empty<string>() } }); });
(5) return services.AddDynamicEF 刪除return
(6) app.UseMvc修改為app.UseEndpoints
代碼如下:

app.UseEndpoints(endpoints => { endpoints.MapControllerRoute("default", "{controller=Home}/{action=Index}/{id?}"); endpoints.MapControllerRoute("defaultWithArea", "{area}/{controller=Home}/{action=Index}/{id?}"); });
(7) 刪除app.UseDeveloperExceptionPage();
添加app.UseRouting();
5. 視圖:由以前的DbQuery修改為 DbSet
並添加以下配置:
代碼如下:

private void SetDbView(ModelBuilder modelBuilder) { modelBuilder.Entity<視圖對應的實體名稱>().ToView("數據庫中視圖名稱"); /* 舉例: modelBuilder.Entity<VwFilterSku>().HasNoKey().ToView("vw_filter_sku"); modelBuilder.Entity<VwQuerySku>().HasNoKey().ToView("vw_query_sku"); */ }
6. Map映射問題
使用映射必須在數據源或者映射源上面標記AutoMap特性
7. 表名列名轉換寫法變化
8. 枚舉DisplayName特征的獲取
由[DisplayName(" ")]特征 修改為[Display(Name=" ")] ,不支持DisplayName(" ")了。
二、 遇到的問題
具體變更請看3.x的重大變更事項:https://docs.microsoft.com/zh-cn/ef/core/what-is-new/ef-core-3.x/breaking-changes (認認真真仔仔細細看完)
以下舉例的只是我在項目中遇到的升級3.1之后的問題 ,並不包含所有變更講解。
1.
異常提示:
2. GroupBy寫法問題:
(1) GroupBy在分組之后沒有使用select指定查詢的列,就會報錯。因為此寫法法生成不了sql語句。
(2) GroupBy在分組之后聚合問題
異常提示:
3. 語句中使用了判斷表字段是否是非空使用了IsEmpty
異常提示:
參照以下寫法是可以生成sql語句的:
4. 查詢中使用了自定義的函數方法,不能轉成正常的sql語句
(1)如圖一
異常提示:
GetTimestamp方法是自定義的一個API用來處理時間轉換成時間戳。
如左圖:在查詢使用過程中,直接使用了自定義的方法(GetTimestamp)做時間戳轉換,在netcore3.1 直接異常了,
GetTimestamp方法不 是sql語句中可以中的函數,因此此條查詢寫法不能轉成一個正確的sql語句了 ,直接異常了。
如右圖:這種轉化只能先將數據查詢出來放在內存中,然后對內存中的數據再調用GetTimestamp方法做時間轉化。
(2)如圖二