Migrasi dari ASP.NET Core 2.2 ke 3.0

Oleh Scott Addie dan Rick Anderson

Artikel ini menjelaskan cara memperbarui proyek ASP.NET Core 2.2 yang ada ke ASP.NET Core 3.0. Mungkin berguna untuk membuat proyek ASP.NET Core 3.0 baru untuk:

  • Bandingkan dengan kode ASP.NET Core 2.2.
  • Salin perubahan yang relevan ke proyek ASP.NET Core 3.0 Anda.

Prasyarat

Memperbarui versi .NET Core SDK di global.json

Jika solusi Anda bergantung pada global.json file untuk menargetkan versi .NET Core SDK tertentu, perbarui propertinya version ke versi 3.0 yang diinstal pada komputer Anda:

{
  "sdk": {
    "version": "3.0.100"
  }
}

Memperbarui file proyek

Memperbarui Kerangka Kerja Target

ASP.NET Core 3.0 dan yang lebih baru hanya berjalan pada .NET Core. Atur Moniker Kerangka Kerja Target (TFM) ke netcoreapp3.0:

<Project Sdk="Microsoft.NET.Sdk.Web">

  <PropertyGroup>
    <TargetFramework>netcoreapp3.0</TargetFramework>
  </PropertyGroup>

</Project>

Menghapus referensi paket usang

Sejumlah besar paket NuGet tidak diproduksi untuk ASP.NET Core 3.0. Referensi paket tersebut harus dihapus dari file proyek Anda. Pertimbangkan file proyek berikut untuk aplikasi web ASP.NET Core 2.2:

<Project Sdk="Microsoft.NET.Sdk.Web">

  <PropertyGroup>
    <TargetFramework>netcoreapp2.2</TargetFramework>
    <AspNetCoreHostingModel>InProcess</AspNetCoreHostingModel>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Microsoft.AspNetCore.App"/>
    <PackageReference Include="Microsoft.AspNetCore.Razor.Design" Version="2.2.0" PrivateAssets="All" />
  </ItemGroup>

</Project>

File proyek yang diperbarui untuk ASP.NET Core 3.0:

<Project Sdk="Microsoft.NET.Sdk.Web">

  <PropertyGroup>
    <TargetFramework>netcoreapp3.0</TargetFramework>
  </PropertyGroup>

</Project>

File proyek ASP.NET Core 3.0 yang diperbarui:

  • <PropertyGroup>Dalam :

    • Memperbarui TFM ke netcoreapp3.0
    • <AspNetCoreHostingModel> Menghapus elemen . Untuk informasi selengkapnya, lihat Model hosting dalam proses dalam dokumen ini.
  • <ItemGroup>Dalam :

    • Microsoft.AspNetCore.App dihapus. Untuk informasi selengkapnya, lihat Referensi kerangka kerja dalam dokumen ini.
    • Microsoft.AspNetCore.Razor.Design dihapus dan dalam daftar paket berikut tidak lagi diproduksi.

Untuk melihat daftar lengkap paket yang tidak lagi diproduksi, pilih daftar perluas berikut:

Klik untuk memperluas daftar paket yang tidak lagi diproduksi
  • Microsoft.AspNetCore
  • Microsoft.AspNetCore.All
  • Microsoft.AspNetCore.App
  • Microsoft.AspNetCore.Antiforgery
  • Microsoft.AspNetCore.Authentication
  • Microsoft.AspNetCore.Authentication.Abstractions
  • Microsoft.AspNetCore.Authentication.CookieS
  • Microsoft.AspNetCore.Authentication.Core
  • Microsoft.AspNetCore.Authentication.OAuth
  • Microsoft.AspNetCore.Authorization.Policy
  • Microsoft.AspNetCore.CookieKebijakan
  • Microsoft.AspNetCore.Cors
  • Microsoft.AspNetCore.Diagnostics
  • Microsoft.AspNetCore.Diagnostics.HealthChecks
  • Microsoft.AspNetCore.HostFiltering
  • Microsoft.AspNetCore.Hosting
  • Microsoft.AspNetCore.Hosting.Abstractions
  • Microsoft.AspNetCore.Hosting.Server.Abstractions
  • Microsoft.AspNetCore.Http
  • Microsoft.AspNetCore.Http.Abstractions
  • Microsoft.AspNetCore.Http. Koneksi
  • Microsoft.AspNetCore.Http.Extensions
  • Microsoft.AspNetCore.HttpOverrides
  • Microsoft.AspNetCore.HttpsPolicy
  • Microsoft.AspNetCore.Identity
  • Microsoft.AspNetCore.Localization
  • Microsoft.AspNetCore.Localization.Routing
  • Microsoft.AspNetCore.Mvc
  • Microsoft.AspNetCore.Mvc.Abstractions
  • Microsoft.AspNetCore.Mvc.Analyzers
  • Microsoft.AspNetCore.Mvc.ApiExplorer
  • Microsoft.AspNetCore.Mvc.Api.Analyzers
  • Microsoft.AspNetCore.Mvc.Core
  • Microsoft.AspNetCore.Mvc.Cors
  • Microsoft.AspNetCore.Mvc.DataAnnotations
  • Microsoft.AspNetCore.Mvc.Formatters.Json
  • Microsoft.AspNetCore.Mvc.Formatters.Xml
  • Microsoft.AspNetCore.Mvc.Localization
  • Microsoft.AspNetCore.Mvc.Razor
  • Microsoft.AspNetCore.Mvc.Razor. Lihat Kompilasi
  • Microsoft.AspNetCore.Mvc.RazorHalaman
  • Microsoft.AspNetCore.Mvc.TagHelpers
  • Microsoft.AspNetCore.Mvc.ViewFeatures
  • Microsoft.AspNetCore.Razor
  • Microsoft.AspNetCore.Razor. Runtime
  • Microsoft.AspNetCore.Razor. Desain
  • Microsoft.AspNetCore.ResponseCaching
  • Microsoft.AspNetCore.ResponseCaching.Abstractions
  • Microsoft.AspNetCore.ResponseCompression
  • Microsoft.AspNetCore.Rewrite
  • Microsoft.AspNetCore.Routing
  • Microsoft.AspNetCore.Routing.Abstractions
  • Microsoft.AspNetCore.Server.HttpSys
  • Microsoft.AspNetCore.Server.IIS
  • Microsoft.AspNetCore.Server.IISIntegration
  • Microsoft.AspNetCore.Server.Kestrel
  • Microsoft.AspNetCore.Server.Kestrel. Inti
  • Microsoft.AspNetCore.Server.Kestrel. Https
  • Microsoft.AspNetCore.Server.Kestrel. Transport.Abstractions
  • Microsoft.AspNetCore.Server.Kestrel. Transport.Sockets
  • Microsoft.AspNetCore.Session
  • Microsoft.AspNetCore.SignalR
  • Microsoft.AspNetCore.SignalR. Inti
  • Microsoft.AspNetCore.StaticFiles
  • Microsoft.AspNetCore.WebSockets
  • Microsoft.AspNetCore.WebUtilities
  • Microsoft.Net.Http.Headers

Tinjau perubahan yang melanggar

Tinjau perubahan yang melanggar

Referensi kerangka kerja

Fitur ASP.NET Core yang tersedia melalui salah satu paket yang tercantum di atas tersedia sebagai bagian Microsoft.AspNetCore.App dari kerangka kerja bersama. Kerangka kerja bersama adalah sekumpulan rakitan (file.dll) yang diinstal pada komputer dan menyertakan komponen runtime dan paket penargetan. Untuk informasi selengkapnya, lihat Kerangka kerja bersama.

  • Proyek yang menargetkan Microsoft.NET.Sdk.Web SDK secara implisit mereferensikan Microsoft.AspNetCore.App kerangka kerja.

    Tidak ada referensi tambahan yang diperlukan untuk proyek-proyek ini:

    <Project Sdk="Microsoft.NET.Sdk.Web">
      <PropertyGroup>
        <TargetFramework>netcoreapp3.0</TargetFramework>
      </PropertyGroup>
        ...
    </Project>
    
  • Proyek yang menargetkan Microsoft.NET.Sdk atau Microsoft.NET.Sdk.Razor SDK, harus menambahkan eksplisit FrameworkReference ke Microsoft.AspNetCore.App:

    <Project Sdk="Microsoft.NET.Sdk.Razor">
      <PropertyGroup>
        <TargetFramework>netcoreapp3.0</TargetFramework>
      </PropertyGroup>
    
      <ItemGroup>
        <FrameworkReference Include="Microsoft.AspNetCore.App" />
      </ItemGroup>
        ...
    </Project>
    

Build yang bergantung pada kerangka kerja menggunakan Docker

Build aplikasi konsol yang bergantung pada kerangka kerja yang menggunakan paket yang bergantung pada kerangka kerja bersama ASP.NET Core dapat memberikan kesalahan runtime berikut:

It was not possible to find any compatible framework version
The specified framework 'Microsoft.AspNetCore.App', version '3.0.0' was not found.
  - No frameworks were found.

Microsoft.AspNetCore.App adalah kerangka kerja bersama yang berisi runtime ASP.NET Core dan hanya ada pada dotnet/core/aspnet gambar Docker. SDK 3.0 mengurangi ukuran build yang bergantung pada kerangka kerja menggunakan ASP.NET Core dengan tidak menyertakan salinan pustaka duplikat yang tersedia dalam kerangka kerja bersama. Ini adalah potensi penghematan hingga 18 MB, tetapi mengharuskan runtime ASP.NET Core hadir / diinstal untuk menjalankan aplikasi.

Untuk menentukan apakah aplikasi memiliki dependensi (baik langsung atau tidak langsung) pada kerangka kerja bersama ASP.NET Core, periksa runtimeconfig.json file yang dihasilkan selama build/penerbitan aplikasi Anda. File ON berikut JSmenunjukkan dependensi pada kerangka kerja bersama ASP.NET Core:

{
  "runtimeOptions": {
    "tfm": "netcoreapp3.0",
    "framework": {
      "name": "Microsoft.AspNetCore.App",
      "version": "3.0.0"
    },
    "configProperties": {
      "System.GC.Server": true
    }
  }
}

Jika aplikasi Anda menggunakan Docker, gunakan gambar dasar yang menyertakan ASP.NET Core 3.0. Contohnya, docker pull mcr.microsoft.com/dotnet/core/aspnet:3.0.

Menambahkan referensi paket untuk rakitan yang dihapus

ASP.NET Core 3.0 menghapus beberapa rakitan yang sebelumnya merupakan bagian Microsoft.AspNetCore.App dari referensi paket. Untuk memvisualisasikan rakitan mana yang dihapus, bandingkan dua folder kerangka kerja bersama. Misalnya, perbandingan versi 2.2.7 dan 3.0.0:

shared framework assemblies comparison

Untuk terus menggunakan fitur yang disediakan oleh rakitan yang dihapus, referensikan versi 3.0 dari paket yang sesuai:

Perubahan startup

Gambar berikut menunjukkan baris yang dihapus dan diubah di aplikasi Web Halaman ASP.NET Core 2.2 Razor :

the deleted and changed lines in an ASP.NET Core 2.2 Razor Web app

Pada gambar sebelumnya, kode yang dihapus ditampilkan dengan warna merah. Kode yang dihapus tidak menampilkan cookie kode opsi, yang dihapus sebelum membandingkan file.

Gambar berikut menunjukkan baris yang ditambahkan dan diubah di aplikasi Web Halaman ASP.NET Core 3.0 Razor :

the added and changed lines in an ASP.NET Core 3.0 Razor Web app

Pada gambar sebelumnya, kode yang ditambahkan ditampilkan dalam warna hijau. Untuk informasi tentang perubahan berikut:

  • services.AddMvc ke services.AddRazorPages, lihat Pendaftaran layanan MVC dalam dokumen ini.
  • CompatibilityVersion, lihat Versi kompatibilitas untuk ASP.NET Core MVC.
  • IHostingEnvironment ke IWebHostEnvironment, lihat pengumuman GitHub ini.
  • app.UseAuthorization ditambahkan ke templat untuk menampilkan middleware otorisasi pesanan harus ditambahkan. Jika aplikasi tidak menggunakan otorisasi, Anda dapat menghapus panggilan dengan aman ke app.UseAuthorization.
  • app.UseEndpoints, lihat Razor Pages atau Migrate Startup.Configure dalam dokumen ini.

Dukungan Analyzer

Proyek yang menargetkan Microsoft.NET.Sdk.Web penganalisis referensi implisit yang sebelumnya dikirim sebagai bagian dari paket Microsoft.AspNetCore.Mvc.Analyzers . Tidak ada referensi tambahan yang diperlukan untuk mengaktifkannya.

Jika aplikasi Anda menggunakan penganalisisAPI yang sebelumnya dikirim menggunakan paket Microsoft.AspNetCore.Mvc.Api.Analyzers, edit file proyek Anda untuk mereferensikan penganalisis yang dikirim sebagai bagian dari .NET Core Web SDK:

<Project Sdk="Microsoft.NET.Sdk.Web">
    <PropertyGroup>
        <TargetFramework>netcoreapp3.0</TargetFramework>
        <IncludeOpenAPIAnalyzers>true</IncludeOpenAPIAnalyzers>
    </PropertyGroup>

    ...
</Project>

Razor Pustaka Kelas

Razor Proyek Pustaka Kelas yang menyediakan komponen UI untuk MVC harus mengatur AddRazorSupportForMvc properti dalam file proyek:

<PropertyGroup>
  <AddRazorSupportForMvc>true</AddRazorSupportForMvc>
</PropertyGroup>

Model hosting dalam proses

Proyek default ke model hosting dalam proses di ASP.NET Core 3.0 atau yang lebih baru. Anda dapat secara opsional menghapus <AspNetCoreHostingModel> properti dalam file proyek jika nilainya adalah InProcess.

Kestrel

Konfigurasi

Migrasikan Kestrel konfigurasi ke penyusun host web yang disediakan oleh ConfigureWebHostDefaults (Program.cs):

public static IHostBuilder CreateHostBuilder(string[] args) =>
    Host.CreateDefaultBuilder(args)
        .ConfigureWebHostDefaults(webBuilder =>
        {
            webBuilder.ConfigureKestrel(serverOptions =>
            {
                // Set properties and call methods on options
            })
            .UseStartup<Startup>();
        });

Jika aplikasi membuat host secara manual dengan ConfigureWebHost alih-alih ConfigureWebHostDefaults, panggil UseKestrel pembangun host web:

public static void Main(string[] args)
{
    var host = new HostBuilder()
        .UseContentRoot(Directory.GetCurrentDirectory())
        .ConfigureWebHost(webBuilder =>
        {
            webBuilder.UseKestrel(serverOptions =>
            {
                // Set properties and call methods on options
            })
            .UseIISIntegration()
            .UseStartup<Startup>();
        })
        .Build();

    host.Run();
}

Middleware Koneksi ion menggantikan Adaptor Koneksi ion

Adaptor Koneksi ion (Microsoft.AspNetCore.Server.Kestrel.Core.Adapter.Internal.IConnectionAdapter) telah dihapus dari Kestrel. Ganti Adaptor Koneksi ion dengan Middleware Koneksi ion. Koneksi ion Middleware mirip dengan HTTP Middleware di alur ASP.NET Core tetapi untuk koneksi tingkat bawah. HTTPS dan pengelogan koneksi:

  • Telah dipindahkan dari Adaptor Koneksi ke Middleware Koneksi ion.
  • Metode ekstensi ini berfungsi seperti pada versi ASP.NET Core sebelumnya.

Untuk informasi selengkapnya, lihat contoh TlsFilter Koneksi ionHandler di bagian ListenOptions.Protocols di Kestrel artikel.

Abstraksi transportasi dipindahkan dan dipublikasikan

Lapisan Kestrel transportasi telah diekspos sebagai antarmuka publik di Connections.Abstractions. Sebagai bagian dari pembaruan ini:

  • Microsoft.AspNetCore.Server.Kestrel.Transport.Abstractions dan jenis terkait telah dihapus.
  • NoDelay dipindahkan dari ListenOptions ke opsi transportasi.
  • Microsoft.AspNetCore.Server.Kestrel.Transport.Abstractions.Internal.SchedulingMode dihapus dari KestrelServerOptions.

Untuk informasi selengkapnya, lihat sumber daya GitHub berikut ini:

Kestrel Meminta header trailer

Untuk aplikasi yang menargetkan versi ASP.NET Core yang lebih lama:

  • Kestrel menambahkan header trailer terpotong HTTP/1.1 ke dalam koleksi header permintaan.
  • Trailer tersedia setelah isi permintaan dibaca hingga akhir.

Ini menyebabkan beberapa kekhawatiran tentang ambiguitas antara header dan trailer, sehingga trailer telah dipindahkan ke koleksi baru (RequestTrailerExtensions) di 3.0.

Trailer permintaan HTTP/2 adalah:

  • Tidak tersedia di ASP.NET Core 2.2.
  • Tersedia dalam 3.0 sebagai RequestTrailerExtensions.

Metode ekstensi permintaan baru hadir untuk mengakses trailer ini. Seperti halnya HTTP/1.1, trailer tersedia setelah isi permintaan dibaca hingga akhir.

Untuk rilis 3.0, metode berikut RequestTrailerExtensions tersedia:

  • GetDeclaredTrailers: Mendapatkan header permintaan Trailer yang mencantumkan trailer mana yang diharapkan setelah isi.
  • SupportsTrailers: Menunjukkan apakah permintaan mendukung penerimaan header trailer.
  • CheckTrailersAvailable: Memeriksa apakah permintaan mendukung trailer dan apakah mereka tersedia untuk dibaca. Pemeriksaan ini tidak mengasumsikan bahwa ada trailer yang akan dibaca. Mungkin tidak ada trailer untuk dibaca bahkan jika true dikembalikan oleh metode ini.
  • GetTrailer: Mendapatkan header berikutnya yang diminta dari respons. Periksa SupportsTrailers sebelum memanggil GetTrailer, atau NotSupportedException mungkin terjadi jika permintaan tidak mendukung header berikutnya.

Untuk informasi selengkapnya, lihat Menempatkan trailer permintaan dalam koleksi terpisah (dotnet/AspNetCore #10410).

AllowSynchronousIO dinonaktifkan

AllowSynchronousIO mengaktifkan atau menonaktifkan API I/O sinkron, seperti HttpRequest.Body.Read, , HttpResponse.Body.Writedan Stream.Flush. API ini adalah sumber kelaparan utas yang menyebabkan crash aplikasi. Dalam 3.0, AllowSynchronousIO dinonaktifkan secara default. Untuk informasi selengkapnya, lihat bagian I/O Sinkron di Kestrel artikel.

Jika I/O sinkron diperlukan, I/O dapat diaktifkan dengan mengonfigurasi AllowSynchronousIO opsi pada server yang digunakan (saat memanggil ConfigureKestrel, misalnya, jika menggunakan Kestrel). Perhatikan bahwa server (Kestrel, HttpSys, TestServer, dll.) semuanya memiliki opsi mereka sendiri AllowSynchronousIO yang tidak akan memengaruhi server lain. I/O sinkron dapat diaktifkan untuk semua server berdasarkan per permintaan menggunakan IHttpBodyControlFeature.AllowSynchronousIO opsi :

var syncIOFeature = HttpContext.Features.Get<IHttpBodyControlFeature>();

if (syncIOFeature != null)
{
    syncIOFeature.AllowSynchronousIO = true;
}

Jika Anda mengalami masalah dengan TextWriter implementasi atau aliran lain yang memanggil API sinkron di Buang, panggil API baru DisposeAsync sebagai gantinya.

Untuk informasi selengkapnya, lihat [Pengumuman] AllowSynchronousIO dinonaktifkan di semua server (dotnet/AspNetCore #7644).

Buffering formatter output

Newtonsoft.Json, XmlSerializer, dan DataContractSerializer formatter output berbasis hanya mendukung serialisasi sinkron. Untuk memungkinkan formatter ini bekerja dengan pembatasan AllowSynchronousIO server, MVC buffer output dari formatter ini sebelum menulis ke disk. Sebagai hasil dari buffering, MVC akan menyertakan header Content-Length saat merespons menggunakan formatter ini.

System.Text.Json mendukung serialisasi asinkron dan akibatnya System.Text.Json formatter berbasis tidak buffer. Pertimbangkan untuk menggunakan formatter ini untuk meningkatkan performa.

Untuk menonaktifkan buffering, aplikasi dapat mengonfigurasi SuppressOutputFormatterBuffering dalam startup mereka:

services.AddControllers(options => options.SuppressOutputFormatterBuffering = true)

Perhatikan bahwa ini dapat mengakibatkan aplikasi melemparkan pengecualian runtime jika AllowSynchronousIO tidak juga dikonfigurasi.

Microsoft.AspNetCore.Server.Kestrel. Rakitan Https dihapus

Di ASP.NET Core 2.1, konten Microsoft.AspNetCore.Server.Kestrel. Https.dll dipindahkan ke Microsoft.AspNetCore.Server.Kestrel. Core.dll. Ini adalah pembaruan yang tidak melanggar menggunakan TypeForwardedTo atribut. Untuk 3.0, Microsoft.AspNetCore.Server kosong .Kestrel. Rakitan Https.dll dan paket NuGet telah dihapus.

Pustaka yang mereferensikan Microsoft.AspNetCore.Server.Kestrel. Https harus memperbarui dependensi ASP.NET Core ke 2.1 atau yang lebih baru.

Aplikasi dan pustaka yang menargetkan ASP.NET Core 2.1 atau yang lebih baru harus menghapus referensi langsung apa pun ke Microsoft.AspNetCore.Server.Kestrel. Paket Https .

Dukungan Newtonsoft.Json (Json.NET)

Sebagai bagian dari pekerjaan untuk meningkatkan kerangka kerja bersama ASP.NET Core, Newtonsoft.Json (Json.NET) telah dihapus dari kerangka kerja bersama ASP.NET Core.

Serializer ON default JSuntuk ASP.NET Core sekarang System.Text.Json, yang baru di .NET Core 3.0. Pertimbangkan untuk menggunakan System.Text.Json jika memungkinkan. Ini berkinerja tinggi dan tidak memerlukan dependensi pustaka tambahan. Namun, karena System.Text.Json baru, mungkin saat ini fitur yang dibutuhkan aplikasi Anda hilang. Untuk informasi selengkapnya, lihat Cara bermigrasi dari Newtonsoft.Json ke System.Text.Json.

Menggunakan Newtonsoft.Json dalam proyek ASP.NET Core 3.0 SignalR

  • Instal Microsoft.AspNetCore.SignalR. Paket Protocols.NewtonsoftJson NuGet.

  • Pada klien, rantai AddNewtonsoftJsonProtocol panggilan metode ke HubConnectionBuilder instans:

    new HubConnectionBuilder()
        .WithUrl("/chathub")
        .AddNewtonsoftJsonProtocol(...)
        .Build();
    
  • Di server, rantai AddNewtonsoftJsonProtocol panggilan metode ke AddSignalR panggilan metode di Startup.ConfigureServices:

    services.AddSignalR()
        .AddNewtonsoftJsonProtocol(...);
    

Menggunakan Newtonsoft.Json dalam proyek MVC ASP.NET Core 3.0

  • Pasang paket Microsoft.AspNetCore.Mvc.NewtonsoftJson.

  • Perbarui Startup.ConfigureServices untuk memanggil AddNewtonsoftJson.

    services.AddMvc()
        .AddNewtonsoftJson();
    

    AddNewtonsoftJson kompatibel dengan metode pendaftaran layanan MVC baru:

    • AddRazorPages
    • AddControllersWithViews
    • AddControllers
    services.AddControllers()
        .AddNewtonsoftJson();
    

    Newtonsoft.Json pengaturan dapat diatur dalam panggilan ke AddNewtonsoftJson:

    services.AddMvc()
        .AddNewtonsoftJson(options =>
               options.SerializerSettings.ContractResolver =
                  new CamelCasePropertyNamesContractResolver());
    

    Catatan: Jika AddNewtonsoftJson metode tidak tersedia, pastikan Anda menginstal Microsoft.AspNetCore.Mvc.NewtonsoftJson paket. Kesalahan umum adalah menginstal paket Newtonsoft.Json alih-alih Microsoft.AspNetCore.Mvc.NewtonsoftJson paket.

Untuk informasi selengkapnya, lihat Menambahkan dukungan format ON berbasis JSNewtonsoft.Json.

Pendaftaran layanan MVC

ASP.NET Core 3.0 menambahkan opsi baru untuk mendaftarkan skenario MVC di dalam Startup.ConfigureServices.

Tiga metode ekstensi tingkat atas baru yang terkait dengan skenario IServiceCollection MVC tersedia. Templat menggunakan metode baru ini alih-alih AddMvc. Namun, AddMvc terus berulah seperti yang ada di rilis sebelumnya.

Contoh berikut menambahkan dukungan untuk pengontrol dan fitur terkait API, tetapi bukan tampilan atau halaman. Templat API menggunakan kode ini:

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllers();
}

Contoh berikut menambahkan dukungan untuk pengontrol, fitur terkait API, dan tampilan, tetapi bukan halaman. Templat Aplikasi Web (MVC) menggunakan kode ini:

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllersWithViews();
}

Contoh berikut menambahkan dukungan untuk Razor Pages dan dukungan pengontrol minimal. Templat Aplikasi Web menggunakan kode ini:

public void ConfigureServices(IServiceCollection services)
{
    services.AddRazorPages();
}

Metode baru juga dapat digabungkan. Contoh berikut setara dengan panggilan AddMvc di ASP.NET Core 2.2:

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllersWithViews();
    services.AddRazorPages();
}

Kode startup perutean

Jika aplikasi memanggil UseMvc atau UseSignalR, migrasikan aplikasi ke Perutean Titik Akhir jika memungkinkan. Untuk meningkatkan kompatibilitas Perutean Titik Akhir dengan versi MVC sebelumnya, kami telah mengembalikan beberapa perubahan dalam pembuatan URL yang diperkenalkan di ASP.NET Core 2.2. Jika Anda mengalami masalah saat menggunakan Perutean Titik Akhir di 2.2, harapkan peningkatan di ASP.NET Core 3.0 dengan pengecualian berikut:

  • Jika aplikasi menerapkan IRouter atau mewarisi dari Route, gunakan DynamicRouteValuesTransformer sebagai pengganti.
  • Jika aplikasi langsung mengakses RouteData.Routers di dalam MVC untuk mengurai URL, Anda dapat menggantinya dengan penggunaan LinkParser.ParsePathByEndpointName.
    • Tentukan rute dengan nama rute.
    • Gunakan LinkParser.ParsePathByEndpointName dan berikan nama rute yang diinginkan.

Perutean Titik Akhir mendukung sintaks pola rute yang sama dan fitur penulisan pola rute sebagai IRouter. Perutean Titik Akhir mendukung IRouteConstraint. Perutean titik akhir mendukung [Route], [HttpGet], dan atribut perutean MVC lainnya.

Untuk sebagian besar aplikasi, hanya Startup memerlukan perubahan.

Memigrasikan Startup.Configure

Saran umum:

  • Tambahkan UseRouting.

  • Jika aplikasi memanggil UseStaticFiles, tempatkan UseStaticFilessebelumnyaUseRouting.

  • Jika aplikasi menggunakan fitur autentikasi/otorisasi seperti AuthorizePage atau , lakukan panggilan ke UseAuthentication dan UseAuthorization: setelah, UseRouting dan UseCors, tetapi sebelum UseEndpoints[Authorize]:

    public void Configure(IApplicationBuilder app)
    {
      ...
    
      app.UseStaticFiles();
    
      app.UseRouting();
      app.UseCors();
    
      app.UseAuthentication();
      app.UseAuthorization();
    
      app.UseEndpoints(endpoints => {
         endpoints.MapControllers();
      });
    
  • Ganti UseMvc atau UseSignalR dengan UseEndpoints.

  • Jika aplikasi menggunakan skenario CORS , seperti [EnableCors], lakukan panggilan ke UseCors sebelum middleware lain yang menggunakan CORS (misalnya, tempatkan UseCors sebelum UseAuthentication, UseAuthorization, dan UseEndpoints).

  • Ganti IHostingEnvironment dengan IWebHostEnvironment dan tambahkan using pernyataan untuk Microsoft.AspNetCore.Hosting namespace.

  • Ganti IApplicationLifetime dengan IHostApplicationLifetime (Microsoft.Extensions.Hosting namespace).

  • Ganti EnvironmentName dengan Environments (Microsoft.Extensions.Hosting namespace).

Kode berikut adalah contoh Startup.Configure dalam aplikasi ASP.NET Core 2.2 yang khas:

public void Configure(IApplicationBuilder app)
{
    ...

    app.UseStaticFiles();

    app.UseAuthentication();

    app.UseSignalR(hubs =>
    {
        hubs.MapHub<ChatHub>("/chat");
    });

    app.UseMvc(routes =>
    {
        routes.MapRoute("default", "{controller=Home}/{action=Index}/{id?}");
    });
}

Setelah memperbarui kode sebelumnya Startup.Configure :

public void Configure(IApplicationBuilder app)
{
    ...

    app.UseStaticFiles();

    app.UseRouting();

    app.UseCors();

    app.UseAuthentication();
    app.UseAuthorization();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapHub<ChatHub>("/chat");
        endpoints.MapControllerRoute("default", "{controller=Home}/{action=Index}/{id?}");
    });
}

Peringatan

Untuk sebagian besar aplikasi, panggilan ke UseAuthentication, UseAuthorization, dan UseCors harus muncul antara panggilan ke UseRouting dan UseEndpoints agar efektif.

Pemeriksaan Kesehatan

Pemeriksaan Kesehatan menggunakan perutean titik akhir dengan Host Generik. Di Startup.Configure, panggil MapHealthChecks pembangun titik akhir dengan URL titik akhir atau jalur relatif:

app.UseEndpoints(endpoints =>
{
    endpoints.MapHealthChecks("/health");
});

Titik akhir Pemeriksaan Kesehatan dapat:

  • Tentukan satu atau beberapa host/port yang diizinkan.
  • Memerlukan otorisasi.
  • Memerlukan CORS.

Untuk informasi lebih lanjut, lihat Pemeriksaan kondisi di ASP.NET Core.

Panduan middleware keamanan

Dukungan untuk otorisasi dan CORS disatukan di sekitar pendekatan middleware . Ini memungkinkan penggunaan middleware dan fungsionalitas yang sama di seluruh skenario ini. Middleware otorisasi yang diperbarui disediakan dalam rilis ini, dan CORS Middleware ditingkatkan sehingga dapat memahami atribut yang digunakan oleh pengontrol MVC.

CORS

Sebelumnya, CORS mungkin sulit dikonfigurasi. Middleware disediakan untuk digunakan dalam beberapa kasus penggunaan, tetapi filter MVC dimaksudkan untuk digunakan tanpa middleware dalam kasus penggunaan lainnya. Dengan ASP.NET Core 3.0, sebaiknya semua aplikasi yang memerlukan CORS menggunakan CORS Middleware bersama dengan Perutean Titik Akhir. UseCors dapat diberikan kebijakan default, dan [EnableCors][DisableCors] atribut dapat digunakan untuk mengambil alih kebijakan default jika diperlukan.

Dalam contoh berikut:

  • CORS diaktifkan untuk semua titik akhir dengan default kebijakan bernama.
  • Kelas MyController menonaktifkan CORS dengan [DisableCors] atribut .
public void Configure(IApplicationBuilder app)
{
    ...

    app.UseRouting();

    app.UseCors("default");

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapDefaultControllerRoute();
    });
}

[DisableCors]
public class MyController : ControllerBase
{
    ...
}

Authorization

Dalam versi ASP.NET Core yang lebih lama, dukungan otorisasi disediakan melalui [Authorize] atribut . Middleware otorisasi tidak tersedia. Di ASP.NET Core 3.0, middleware otorisasi diperlukan. Sebaiknya tempatkan Middleware Otorisasi Inti ASP.NET (UseAuthorization) segera setelah UseAuthentication. Middleware Otorisasi juga dapat dikonfigurasi dengan kebijakan default, yang dapat ditimpa.

Di ASP.NET Core 3.0 atau yang lebih baru, UseAuthorization dipanggil di Startup.Configure, dan berikut ini HomeController memerlukan pengguna yang masuk:

public void Configure(IApplicationBuilder app)
{
    ...

    app.UseRouting();

    app.UseAuthentication();
    app.UseAuthorization();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapDefaultControllerRoute();
    });
}

public class HomeController : Controller
{
    [Authorize]
    public IActionResult BuyWidgets()
    {
        ...
    }
}

Saat menggunakan perutean titik akhir, kami sarankan untuk tidak mengonfigurasi AuthorizeFilter dan sebaliknya mengandalkan middleware Otorisasi. Jika aplikasi menggunakan AuthorizeFilter sebagai filter global di MVC, sebaiknya refaktor kode untuk memberikan kebijakan dalam panggilan ke AddAuthorization.

DefaultPolicy awalnya dikonfigurasi untuk memerlukan autentikasi, jadi tidak diperlukan konfigurasi tambahan. Dalam contoh berikut, titik akhir MVC ditandai sebagai RequireAuthorization sehingga semua permintaan harus diotorisasi berdasarkan DefaultPolicy. Namun, akses yang HomeController diizinkan tanpa pengguna masuk ke aplikasi karena [AllowAnonymous]:

public void Configure(IApplicationBuilder app)
{
    ...

    app.UseRouting();

    app.UseAuthentication();
    app.UseAuthorization();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapDefaultControllerRoute().RequireAuthorization();
    });
}

[AllowAnonymous]
public class HomeController : Controller
{
    ...
}

Otorisasi untuk titik akhir tertentu

Otorisasi juga dapat dikonfigurasi untuk kelas titik akhir tertentu. Kode berikut adalah contoh mengonversi aplikasi MVC yang mengonfigurasi global AuthorizeFilter ke aplikasi dengan kebijakan tertentu yang memerlukan otorisasi:

public class Startup
{
    public Startup(IConfiguration configuration)
    {
        Configuration = configuration;
    }

    static readonly string _RequireAuthenticatedUserPolicy = 
                            "RequireAuthenticatedUserPolicy";
    public IConfiguration Configuration { get; }

    public void ConfigureServices(IServiceCollection services)
    {
        services.AddDbContext<ApplicationDbContext>(options =>
            options.UseSqlServer(
                Configuration.GetConnectionString("DefaultConnection")));
        services.AddDefaultIdentity<IdentityUser>(
                 options => options.SignIn.RequireConfirmedAccount = true)
            .AddEntityFrameworkStores<ApplicationDbContext>();

        // Pre 3.0:
        // services.AddMvc(options => options.Filters.Add(new AuthorizeFilter(...));

        services.AddControllersWithViews();
        services.AddRazorPages();
        services.AddAuthorization(o => o.AddPolicy(_RequireAuthenticatedUserPolicy,
                        builder => builder.RequireAuthenticatedUser()));

    }

    public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
    {
        if (env.IsDevelopment())
        {
            app.UseDeveloperExceptionPage();
            app.UseDatabaseErrorPage();
        }
        else
        {
            app.UseExceptionHandler("/Home/Error");
            app.UseHsts();
        }
        app.UseHttpsRedirection();
        app.UseStaticFiles();

        app.UseRouting();

        app.UseAuthentication();
        app.UseAuthorization();

        app.UseEndpoints(endpoints =>
        {
            endpoints.MapDefaultControllerRoute()
                .RequireAuthorization(_RequireAuthenticatedUserPolicy);
            endpoints.MapRazorPages();
        });
    }
}

Kebijakan juga dapat disesuaikan. dikonfigurasi DefaultPolicy untuk memerlukan autentikasi:

public class Startup
{
    public Startup(IConfiguration configuration)
    {
        Configuration = configuration;
    }

    public IConfiguration Configuration { get; }

    public void ConfigureServices(IServiceCollection services)
    {
        services.AddDbContext<ApplicationDbContext>(options =>
            options.UseSqlServer(
                Configuration.GetConnectionString("DefaultConnection")));
        services.AddDefaultIdentity<IdentityUser>(
                 options => options.SignIn.RequireConfirmedAccount = true)
            .AddEntityFrameworkStores<ApplicationDbContext>();

        services.AddControllersWithViews();
        services.AddRazorPages();
        services.AddAuthorization(options =>
        {
            options.DefaultPolicy = new AuthorizationPolicyBuilder()
              .RequireAuthenticatedUser()
              .Build();
        });

    }

    public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
    {
        if (env.IsDevelopment())
        {
            app.UseDeveloperExceptionPage();
            app.UseDatabaseErrorPage();
        }
        else
        {
            app.UseExceptionHandler("/Home/Error");
            app.UseHsts();
        }
        app.UseHttpsRedirection();
        app.UseStaticFiles();

        app.UseRouting();

        app.UseAuthentication();
        app.UseAuthorization();

        app.UseEndpoints(endpoints =>
        {
            endpoints.MapDefaultControllerRoute().RequireAuthorization();
            endpoints.MapRazorPages();
        });
    }
}
[AllowAnonymous]
public class HomeController : Controller
{

Atau, semua titik akhir dapat dikonfigurasi untuk memerlukan otorisasi tanpa [Authorize] atau RequireAuthorization dengan mengonfigurasi FallbackPolicy. FallbackPolicy berbeda dari DefaultPolicy. dipicu DefaultPolicy oleh [Authorize] atau RequireAuthorization, saat FallbackPolicy dipicu ketika tidak ada kebijakan lain yang ditetapkan. FallbackPolicy awalnya dikonfigurasi untuk mengizinkan permintaan tanpa otorisasi.

Contoh berikut sama dengan contoh sebelumnya DefaultPolicy tetapi menggunakan FallbackPolicy untuk selalu memerlukan autentikasi pada semua titik akhir kecuali ketika [AllowAnonymous] ditentukan:

public void ConfigureServices(IServiceCollection services)
{
    ...

    services.AddAuthorization(options =>
    {
        options.FallbackPolicy = new AuthorizationPolicyBuilder()
          .RequireAuthenticatedUser()
          .Build();
    });
}

public void Configure(IApplicationBuilder app)
{
    ...

    app.UseRouting();

    app.UseAuthentication();
    app.UseAuthorization();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapDefaultControllerRoute();
    });
}

[AllowAnonymous]
public class HomeController : Controller
{
    ...
}

Otorisasi oleh middleware berfungsi tanpa kerangka kerja memiliki pengetahuan khusus tentang otorisasi. Misalnya, pemeriksaan kesehatan tidak memiliki pengetahuan khusus tentang otorisasi, tetapi pemeriksaan kesehatan dapat memiliki kebijakan otorisasi yang dapat dikonfigurasi yang diterapkan oleh middleware.

Selain itu, setiap titik akhir dapat menyesuaikan persyaratan otorisasinya. Dalam contoh berikut, UseAuthorization memproses otorisasi dengan DefaultPolicy, tetapi /healthz titik akhir pemeriksaan kesehatan memerlukan admin pengguna:

public void Configure(IApplicationBuilder app)
{
    ...

    app.UseRouting();

    app.UseAuthentication();
    app.UseAuthorization();

    app.UseEndpoints(endpoints =>
    {
        endpoints
            .MapHealthChecks("/healthz")
            .RequireAuthorization(new AuthorizeAttribute(){ Roles = "admin", });
    });
}

Perlindungan diimplementasikan untuk beberapa skenario. Middleware Titik Akhir melemparkan pengecualian jika kebijakan otorisasi atau CORS dilewati karena middleware yang hilang. Dukungan Penganalisis untuk memberikan umpan balik tambahan tentang kesalahan konfigurasi sedang berlangsung.

Penangan otorisasi kustom

Jika aplikasi menggunakan handler otorisasi kustom, perutean titik akhir meneruskan jenis sumber daya yang berbeda ke handler daripada MVC. Handler yang mengharapkan sumber daya konteks handler otorisasi berjenis AuthorizationFilterContext(jenis sumber daya yang disediakan oleh filter MVC) perlu diperbarui untuk menangani sumber daya jenis RouteEndpoint (jenis sumber daya yang diberikan kepada penangan otorisasi oleh perutean titik akhir).

MVC masih menggunakan AuthorizationFilterContext sumber daya, jadi jika aplikasi menggunakan filter otorisasi MVC bersama dengan otorisasi perutean titik akhir, mungkin perlu untuk menangani kedua jenis sumber daya.

SignalR

Pemetaan SignalR hub sekarang terjadi di dalam UseEndpoints.

Petakan setiap hub dengan MapHub. Seperti pada versi sebelumnya, setiap hub secara eksplisit tercantum.

Dalam contoh berikut, dukungan untuk ChatHubSignalR hub ditambahkan:

public void Configure(IApplicationBuilder app)
{
    ...

    app.UseRouting();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapHub<ChatHub>();
    });
}

Ada opsi baru untuk mengontrol batas ukuran pesan dari klien. Misalnya, dalam Startup.ConfigureServices:

services.AddSignalR(hubOptions =>
{
    hubOptions.MaximumReceiveMessageSize = 32768;
});

Dalam ASP.NET Core 2.2, Anda dapat mengatur TransportMaxBufferSize dan yang akan secara efektif mengontrol ukuran pesan maksimum. Dalam ASP.NET Core 3.0, opsi itu sekarang hanya mengontrol ukuran maksimum sebelum backpressure diamati.

SignalR rakitan dalam kerangka kerja bersama

ASP.NET rakitan sisi server Core SignalR sekarang diinstal dengan .NET Core SDK. Untuk informasi selengkapnya, lihat Menghapus referensi paket usang dalam dokumen ini.

Pengontrol MVC

Pemetaan pengontrol sekarang terjadi di dalam UseEndpoints.

Tambahkan MapControllers jika aplikasi menggunakan perutean atribut. Karena perutean mencakup dukungan untuk banyak kerangka kerja di ASP.NET Core 3.0 atau yang lebih baru, menambahkan pengontrol yang dirutekan atribut adalah keikutsertaan.

Ganti yang berikut ini:

  • MapRoutedenganMapControllerRoute
  • MapAreaRoutedenganMapAreaControllerRoute

Karena perutean sekarang mencakup dukungan untuk lebih dari sekadar MVC, terminologi telah berubah untuk membuat metode ini dengan jelas menyatakan apa yang mereka lakukan. Rute konvensional seperti MapControllerRoute//MapAreaControllerRouteMapDefaultControllerRoute diterapkan dalam urutan ditambahkan. Tempatkan rute yang lebih spesifik (seperti rute untuk suatu area) terlebih dahulu.

Dalam contoh berikut:

  • MapControllers menambahkan dukungan untuk pengontrol yang dirutekan atribut.
  • MapAreaControllerRoute menambahkan rute konvensional untuk pengontrol di suatu area.
  • MapControllerRoute menambahkan rute konvensional untuk pengontrol.
public void Configure(IApplicationBuilder app)
{
    ...

    app.UseRouting();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapControllers();
        endpoints.MapAreaControllerRoute(
            "admin",
            "admin",
            "Admin/{controller=Home}/{action=Index}/{id?}");
        endpoints.MapControllerRoute(
            "default", "{controller=Home}/{action=Index}/{id?}");
    });
}

Penghapusan akhiran asinkron dari nama tindakan pengontrol

Di ASP.NET Core 3.0, ASP.NET Core MVC menghapus Async akhiran dari nama tindakan pengontrol. Perutean dan pembuatan tautan terpengaruh oleh default baru ini. Misalnya:

public class ProductsController : Controller
{
    public async Task<IActionResult> ListAsync()
    {
        var model = await _dbContext.Products.ToListAsync();
        return View(model);
    }
}

Sebelum ASP.NET Core 3.0:

  • Tindakan sebelumnya dapat diakses di rute Products/ListAsync .

  • Pembuatan tautan diperlukan untuk menentukan akhiran Async . Misalnya:

    <a asp-controller="Products" asp-action="ListAsync">List</a>
    

Di ASP.NET Core 3.0:

  • Tindakan sebelumnya dapat diakses di rute Produk/Daftar .

  • Pembuatan tautan tidak memerlukan penentuan akhiran Async . Misalnya:

    <a asp-controller="Products" asp-action="List">List</a>
    

Perubahan ini tidak memengaruhi nama yang ditentukan menggunakan [ActionName] atribut . Perilaku default dapat dinonaktifkan dengan kode berikut di Startup.ConfigureServices:

services.AddMvc(options =>
    options.SuppressAsyncSuffixInActionNames = false);

Ada beberapa perbedaan dalam pembuatan tautan (menggunakan Url.Link dan API serupa, misalnya). Ini termasuk:

  • Secara default, saat menggunakan perutean titik akhir, casing parameter rute dalam URI yang dihasilkan belum tentu dipertahankan. Perilaku ini dapat dikontrol dengan IOutboundParameterTransformer antarmuka.
  • Membuat URI untuk rute yang tidak valid (pengontrol/tindakan atau halaman yang tidak ada) akan menghasilkan string kosong di bawah perutean titik akhir alih-alih menghasilkan URI yang tidak valid.
  • Nilai sekitar (parameter rute dari konteks saat ini) tidak secara otomatis digunakan dalam pembuatan tautan dengan perutean titik akhir. Sebelumnya, saat membuat tautan ke tindakan lain (atau halaman), nilai rute yang tidak ditentukan akan disimpulkan dari nilai sekitar rute saat ini . Saat menggunakan perutean titik akhir, semua parameter rute harus ditentukan secara eksplisit selama pembuatan tautan.

Razor Pages

Halaman Pemetaan Razor sekarang berlangsung di dalam UseEndpoints.

Tambahkan MapRazorPages jika aplikasi menggunakan Razor Pages. Karena Perutean Titik Akhir menyertakan dukungan untuk banyak kerangka kerja, menambahkan Razor Pages sekarang ikut serta.

Dalam metode berikut Startup.Configure , MapRazorPages menambahkan dukungan untuk Razor Pages:

public void Configure(IApplicationBuilder app)
{
    ...

    app.UseRouting();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapRazorPages();
    });
}

Menggunakan MVC tanpa Perutean Titik Akhir

Menggunakan MVC melalui UseMvc atau UseMvcWithDefaultRoute di ASP.NET Core 3.0 memerlukan keikutsertaan eksplisit di dalam Startup.ConfigureServices. Hal ini diperlukan karena MVC harus mengetahui apakah MVC dapat mengandalkan otorisasi dan CORS Middleware selama inisialisasi. Penganalisis disediakan yang memperingatkan jika aplikasi mencoba menggunakan konfigurasi yang tidak didukung.

Jika aplikasi memerlukan dukungan warisan IRouter , nonaktifkan EnableEndpointRouting menggunakan salah satu pendekatan berikut di Startup.ConfigureServices:

services.AddMvc(options => options.EnableEndpointRouting = false);
services.AddControllers(options => options.EnableEndpointRouting = false);
services.AddControllersWithViews(options => options.EnableEndpointRouting = false);
services.AddRazorPages().AddMvcOptions(options => options.EnableEndpointRouting = false);

Pemeriksaan kesehatan

Pemeriksaan kesehatan dapat digunakan sebagai router-ware dengan Perutean Titik Akhir.

Tambahkan MapHealthChecks untuk menggunakan pemeriksaan kesehatan dengan Perutean Titik Akhir. Metode MapHealthChecks menerima argumen yang mirip UseHealthChecksdengan . Keuntungan menggunakan MapHealthChecks lebih UseHealthChecks dari adalah kemampuan untuk menerapkan otorisasi dan memiliki kontrol yang lebih halus atas kebijakan pencocokan.

Dalam contoh berikut, MapHealthChecks dipanggil untuk titik akhir pemeriksaan kesehatan di /healthz:

public void Configure(IApplicationBuilder app)
{
    ...

    app.UseRouting();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapHealthChecks("/healthz", new HealthCheckOptions() { });
    });
}

HostBuilder menggantikan WebHostBuilder

Templat ASP.NET Core 3.0 menggunakan Host Generik. Versi sebelumnya menggunakan Web Host. Kode berikut menunjukkan kelas yang dihasilkan Program templat ASP.NET Core 3.0:

// requires using Microsoft.AspNetCore.Hosting;
// requires using Microsoft.Extensions.Hosting;

public class Program
{
    public static void Main(string[] args)
    {
        CreateHostBuilder(args).Build().Run();
    }

    public static IHostBuilder CreateHostBuilder(string[] args) =>
        Host.CreateDefaultBuilder(args)
            .ConfigureWebHostDefaults(webBuilder =>
            {
                webBuilder.UseStartup<Startup>();
            });
}

Kode berikut menunjukkan kelas yang dihasilkan Program templat ASP.NET Core 2.2:

public class Program
{
    public static void Main(string[] args)
    {
        CreateWebHostBuilder(args).Build().Run();
    }

    public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
        WebHost.CreateDefaultBuilder(args)
            .UseStartup<Startup>();
}

IWebHostBuilder tetap dalam 3.0 dan merupakan jenis yang webBuilder terlihat dalam sampel kode sebelumnya. WebHostBuilder akan ditolak dalam rilis mendatang dan digantikan oleh HostBuilder.

Perubahan paling signifikan dari WebHostBuilder ke adalah dalam injeksi dependensi (DI)HostBuilder. Saat menggunakan HostBuilder, Anda hanya dapat menyuntikkan yang berikut ini ke dalam Startupkonstruktor :

Batasan HostBuilder DI:

  • Aktifkan kontainer DI untuk dibangun hanya satu kali.
  • Menghindari masalah masa pakai objek yang dihasilkan seperti menyelesaikan beberapa instans singleton.

Untuk informasi selengkapnya, lihat Menghindari injeksi layanan Startup di ASP.NET Core 3.

TambahkanAuthorization dipindahkan ke rakitan yang berbeda

Metode ASP.NET Core 2.2 dan yang lebih rendah AddAuthorization di Microsoft.AspNetCore.Authorization.dll:

  • Telah diganti AddAuthorizationCorenamanya .
  • Telah dipindahkan ke Microsoft.AspNetCore.Authorization.Policy.dll.

Aplikasi yang menggunakan Microsoft.AspNetCore.Authorization.dll dan Microsoft.AspNetCore.Authorization.Policy.dll tidak terpengaruh.

Aplikasi yang tidak menggunakan Microsoft.AspNetCore.Authorization.Policy.dll harus melakukan salah satu hal berikut:

  • Tambahkan referensi ke Microsoft.AspNetCore.Authorization.Policy.dll. Pendekatan ini berfungsi untuk sebagian besar aplikasi dan hanya itu yang diperlukan.
  • Beralih menggunakan AddAuthorizationCore

Untuk informasi selengkapnya, lihat Melanggar perubahan dalam AddAuthorization(o =>) overload tinggal di rakitan yang berbeda #386.

Identity UI

Identity Pembaruan UI untuk ASP.NET Core 3.0:

  • Tambahkan referensi paket ke Microsoft.AspNetCore.Identity. UI.
  • Aplikasi yang tidak menggunakan Razor Pages harus memanggil MapRazorPages. Lihat Razor Halaman dalam dokumen ini.
  • Bootstrap 4 adalah kerangka kerja UI default. Atur IdentityUIFrameworkVersion properti proyek untuk mengubah default. Untuk informasi selengkapnya, lihat pengumuman GitHub ini.

SignalR

Klien SignalR JavaScript telah berubah dari @aspnet/signalr menjadi @microsoft/signalr. Untuk bereaksi terhadap perubahan ini, ubah referensi dalam package.json file, require pernyataan, dan pernyataan ECMAScript import .

System.Text.Json adalah protokol default

System.Text.Json sekarang menjadi protokol Hub default yang digunakan oleh klien dan server.

Di Startup.ConfigureServices, panggil AddJsonProtocol untuk mengatur opsi serializer.

Server:

services.AddSignalR(...)
        .AddJsonProtocol(options =>
        {
            options.PayloadSerializerOptions.WriteIndented = false;
        })

Klien:

new HubConnectionBuilder()
    .WithUrl("/chathub")
    .AddJsonProtocol(options =>
    {
        options.PayloadSerializerOptions.WriteIndented = false;
    })
    .Build();

Beralih ke Newtonsoft.Json

Jika Anda menggunakan fitur Newtonsoft.Json yang tidak didukung di System.Text.Json, Anda dapat beralih kembali ke Newtonsoft.Json. Lihat Menggunakan Newtonsoft.Json dalam proyek ASP.NET Core 3.0 SignalR sebelumnya di artikel ini.

Cache terdistribusi Redis

Paket Microsoft.Extensions.Caching.Redis tidak tersedia untuk aplikasi ASP.NET Core 3.0 atau yang lebih baru. Ganti referensi paket dengan Microsoft.Extensions.Caching.StackExchangeRedis. Untuk informasi selengkapnya, lihat Penembolokan terdistribusi di ASP.NET Core.

Ikut serta dalam kompilasi runtime

Sebelum ASP.NET Core 3.0, kompilasi runtime tampilan adalah fitur implisit dari kerangka kerja. Kompilasi runtime melengkapi kompilasi build-time tampilan. Ini memungkinkan kerangka kerja untuk mengkompilasi Razor tampilan dan halaman (.cshtml file) ketika file dimodifikasi, tanpa harus membangun kembali seluruh aplikasi. Fitur ini mendukung skenario membuat pengeditan cepat di IDE dan menyegarkan browser untuk melihat perubahan.

Dalam ASP.NET Core 3.0, kompilasi runtime adalah skenario keikutsertaan. Kompilasi build-time adalah satu-satunya mekanisme untuk melihat kompilasi yang diaktifkan secara default. Runtime bergantung pada Visual Studio atau dotnet-watch di Visual Studio Code untuk membangun kembali proyek saat mendeteksi perubahan .cshtml pada file. Di Visual Studio, ubah ke .cs, .cshtml, atau .razor file dalam proyek yang dijalankan (Ctrl+F5), tetapi tidak di-debug (F5), picu kompilasi ulang proyek.

Untuk mengaktifkan kompilasi runtime di proyek ASP.NET Core 3.0 Anda:

  1. Instal Microsoft.AspNetCore.Mvc.Razor. Paket RuntimeCompilation NuGet.

  2. Perbarui Startup.ConfigureServices untuk memanggil AddRazorRuntimeCompilation:

    Untuk ASP.NET Core MVC, gunakan kode berikut:

    services.AddControllersWithViews()
        .AddRazorRuntimeCompilation(...);
    

    Untuk ASP.NET Core Razor Pages, gunakan kode berikut:

    services.AddRazorPages()
        .AddRazorRuntimeCompilation(...);
    

Sampel di https://github.com/aspnet/samples/tree/main/samples/aspnetcore/mvc/runtimecompilation menunjukkan contoh mengaktifkan kompilasi runtime secara kondisional di lingkungan Pengembangan.

Untuk informasi selengkapnya tentang Razor kompilasi file, lihat Razor kompilasi file di ASP.NET Core.

Memigrasikan pustaka melalui multi-penargetan

Pustaka sering kali perlu mendukung beberapa versi ASP.NET Core. Sebagian besar pustaka yang dikompilasi terhadap versi ASP.NET Core sebelumnya harus terus berfungsi tanpa masalah. Kondisi berikut mengharuskan aplikasi dikompilasi silang:

  • Pustaka bergantung pada fitur yang memiliki perubahan pemecahan biner.
  • Pustaka ingin memanfaatkan fitur baru di ASP.NET Core 3.0.

Misalnya:

<Project Sdk="Microsoft.NET.Sdk">
  <PropertyGroup>
    <TargetFrameworks>netcoreapp3.0;netstandard2.0</TargetFrameworks>
  </PropertyGroup>

  <ItemGroup Condition="'$(TargetFramework)' == 'netcoreapp3.0'">
    <FrameworkReference Include="Microsoft.AspNetCore.App" />
  </ItemGroup>

  <ItemGroup Condition="'$(TargetFramework)' == 'netstandard2.0'">
    <PackageReference Include="Microsoft.AspNetCore" Version="2.1.0" />
  </ItemGroup>
</Project>

Gunakan #ifdefs untuk mengaktifkan API khusus ASP.NET Core 3.0:

var webRootFileProvider =
#if NETCOREAPP3_0
    GetRequiredService<IWebHostEnvironment>().WebRootFileProvider;
#elif NETSTANDARD2_0
    GetRequiredService<IHostingEnvironment>().WebRootFileProvider;
#else
#error unknown target framework
#endif

Untuk informasi selengkapnya tentang menggunakan API ASP.NET Core di pustaka kelas, lihat Menggunakan API inti ASP.NET di pustaka kelas.

Perubahan lain-lain

Sistem validasi di .NET Core 3.0 dan yang lebih baru memperlakukan parameter yang tidak dapat diubah ke null atau properti terikat seolah-olah mereka memiliki [Required] atribut. Untuk informasi selengkapnya, lihat atribut [Wajib] .

Terbitkan

Hapus folder bin dan obj di direktori proyek.

TestServer

Untuk aplikasi yang menggunakan TestServer langsung dengan Host Generik, buat TestServer di IWebHostBuilder di ConfigureWebHost:

[Fact]
public async Task GenericCreateAndStartHost_GetTestServer()
{
    using var host = await new HostBuilder()
        .ConfigureWebHost(webBuilder =>
        {
            webBuilder
                .UseTestServer()
                .Configure(app => { });
        })
    .StartAsync();

    var response = await host.GetTestServer().CreateClient().GetAsync("/");

    Assert.Equal(HttpStatusCode.NotFound, response.StatusCode);
}

Perubahan BREAKING API

Tinjau perubahan yang melanggar:

Perutean titik akhir dengan parameter catch-all

Peringatan

Parameter catch-all mungkin salah mencocokkan rute karena bug dalam perutean. Aplikasi yang terpengaruh oleh bug ini memiliki karakteristik berikut:

  • Rute catch-all, misalnya, {**slug}"
  • Rute catch-all gagal mencocokkan permintaan yang harus cocok.
  • Menghapus rute lain membuat rute catch-all mulai berfungsi.

Lihat bug GitHub 18677 dan 16579 misalnya kasus yang mengenai bug ini.

Perbaikan keikutsertaan untuk bug ini terkandung dalam .NET Core 3.1.301 SDK dan yang lebih baru. Kode berikut menetapkan sakelar internal yang memperbaiki bug ini:

public static void Main(string[] args)
{
   AppContext.SetSwitch("Microsoft.AspNetCore.Routing.UseCorrectCatchAllBehavior", 
                         true);
   CreateHostBuilder(args).Build().Run();
}
// Remaining code removed for brevity.

.NET Core 3.0 di Azure App Service

Peluncuran .NET Core ke Azure App Service selesai. .NET Core 3.0 tersedia di semua pusat data Azure App Service.

Modul Inti ASP.NET (ANCM)

Jika ASP.NET Core Module (ANCM) bukan komponen yang dipilih saat Visual Studio diinstal atau jika versi ANCM sebelumnya diinstal pada sistem, unduh Penginstal Bundel Hosting .NET Core terbaru (unduh langsung) dan jalankan alat penginstal. Untuk informasi selengkapnya, lihat Bundel Hosting.