panduan ASP.NET Core BlazorSignalR
Catatan
Ini bukan versi terbaru dari artikel ini. Untuk rilis saat ini, lihat versi .NET 8 dari artikel ini.
Peringatan
Versi ASP.NET Core ini tidak lagi didukung. Untuk informasi selengkapnya, lihat Kebijakan Dukungan .NET dan .NET Core. Untuk rilis saat ini, lihat versi .NET 8 dari artikel ini.
Penting
Informasi ini berkaitan dengan produk pra-rilis yang mungkin dimodifikasi secara substansial sebelum dirilis secara komersial. Microsoft tidak memberikan jaminan, tersirat maupun tersurat, sehubungan dengan informasi yang diberikan di sini.
Untuk rilis saat ini, lihat versi .NET 8 dari artikel ini.
Artikel ini menjelaskan cara mengonfigurasi dan mengelola SignalR koneksi di Blazor aplikasi.
Untuk panduan umum tentang konfigurasi ASP.NET CoreSignalR, lihat topik dalam Gambaran Umum area ASP.NET Core SignalRdokumentasi, terutama konfigurasi ASP.NET CoreSignalR.
Aplikasi sisi server menggunakan ASP.NET Core SignalR untuk berkomunikasi dengan browser. SignalRKondisi hosting dan penskalakan berlaku untuk aplikasi sisi server.
Blazor berfungsi paling baik saat menggunakan WebSocket sebagai SignalR transportasi karena latensi, keandalan, dan keamanan yang lebih rendah. Polling Panjang digunakan oleh SignalR saat WebSockets tidak tersedia atau ketika aplikasi secara eksplisit dikonfigurasi untuk menggunakan Long Polling.
Layanan Azure SignalR dengan koneksi ulang stateful
Koneksi ulang stateful (WithStatefulReconnect) dirilis dengan .NET 8 tetapi saat ini tidak didukung untuk Layanan Azure SignalR . Untuk informasi selengkapnya, lihat Dukungan Sambungkan Ulang Stateful? (Azure/azure-signalr
#1878).
Kompresi WebSocket untuk komponen Server Interaktif
Secara default, komponen Server Interaktif:
Aktifkan pemadatan untuk koneksi WebSocket.
ConfigureWebsocketOptions
mengontrol kompresi WebSocket.frame-ancestors
Mengadopsi direktif Kebijakan Keamanan Konten (CSP) diatur ke'self'
, yang hanya mengizinkan penyematan aplikasi di<iframe>
asal tempat aplikasi dilayani saat kompresi diaktifkan atau saat konfigurasi untuk konteks WebSocket disediakan.ContentSecurityFrameAncestorPolicy
frame-ancestors
mengontrol CSP.
frame-ancestors
CSP dapat dihapus secara manual dengan mengatur nilai ConfigureWebSocketOptions
ke null
, karena Anda mungkin ingin mengonfigurasi CSP dengan cara terpusat. frame-ancestors
Ketika CSP dikelola dengan cara terpusat, perawatan harus diambil untuk menerapkan kebijakan setiap kali dokumen pertama dirender. Kami tidak menyarankan untuk menghapus kebijakan sepenuhnya, karena mungkin membuat aplikasi rentan terhadap serangan.
Contoh penggunaan:
Nonaktifkan kompresi dengan mengatur ConfigureWebSocketOptions
ke null
, yang mengurangi kerentanan aplikasi untuk menyerang tetapi dapat mengakibatkan penurunan performa:
builder.MapRazorComponents<App>()
.AddInteractiveServerRenderMode(o => o.ConfigureWebSocketOptions = null)
Saat pemadatan diaktifkan, konfigurasikan CSP yang lebih frame-ancestors
ketat dengan nilai 'none'
(tanda kutip tunggal diperlukan), yang memungkinkan kompresi WebSocket tetapi mencegah browser menyematkan aplikasi ke dalam :<iframe>
builder.MapRazorComponents<App>()
.AddInteractiveServerRenderMode(o => o.ContentSecurityFrameAncestorsPolicy = "'none'")
Saat pemadatan diaktifkan, hapus frame-ancestors
CSP dengan mengatur ContentSecurityFrameAncestorsPolicy
ke null
. Skenario ini hanya direkomendasikan untuk aplikasi yang mengatur CSP dengan cara terpusat:
builder.MapRazorComponents<App>()
.AddInteractiveServerRenderMode(o => o.ContentSecurityFrameAncestorsPolicy = null)
Penting
Browser menerapkan arahan CSP dari beberapa header CSP menggunakan nilai arahan kebijakan paling ketat. Oleh karena itu, pengembang tidak dapat menambahkan kebijakan yang lebih frame-ancestors
lemah daripada 'self'
sengaja atau secara tidak sengaja.
Tanda kutip tunggal diperlukan pada nilai string yang diteruskan ke ContentSecurityFrameAncestorsPolicy
:
Nilai yang tidak didukung: none
, self
'self'
Opsi tambahan termasuk menentukan satu atau beberapa sumber host dan sumber skema.
Untuk implikasi keamanan, lihat Panduan mitigasi ancaman untuk ASP.NET penyajian sisi server interaktif CoreBlazor. Untuk informasi selengkapnya tentang arahan frame-ancestors
, lihat CSP: frame-ancestors
(dokumentasi MDN).
Menonaktifkan kompresi respons untuk Hot Reload
Saat menggunakan Hot Reload, nonaktifkan Middleware Kompresi Respons di Development
lingkungan. Apakah kode default dari templat proyek digunakan atau tidak, selalu panggil UseResponseCompression terlebih dahulu dalam alur pemrosesan permintaan.
Dalam file Program
:
if (!app.Environment.IsDevelopment())
{
app.UseResponseCompression();
}
Negosiasi lintas asal sisi SignalR klien untuk autentikasi
Bagian ini menjelaskan cara mengonfigurasi SignalRklien yang mendasar untuk mengirim kredensial, seperti cookie atau header autentikasi HTTP.
Gunakan SetBrowserRequestCredentials untuk mengatur Include permintaan lintas asal fetch
.
IncludeRequestCredentialsMessageHandler.cs
:
using System.Net.Http;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Components.WebAssembly.Http;
public class IncludeRequestCredentialsMessageHandler : DelegatingHandler
{
protected override Task<HttpResponseMessage> SendAsync(
HttpRequestMessage request, CancellationToken cancellationToken)
{
request.SetBrowserRequestCredentials(BrowserRequestCredentials.Include);
return base.SendAsync(request, cancellationToken);
}
}
Di mana koneksi hub dibangun, tetapkan ke HttpMessageHandler HttpMessageHandlerFactory opsi :
private HubConnectionBuilder? hubConnection;
...
hubConnection = new HubConnectionBuilder()
.WithUrl(new Uri(Navigation.ToAbsoluteUri("/chathub")), options =>
{
options.HttpMessageHandlerFactory = innerHandler =>
new IncludeRequestCredentialsMessageHandler { InnerHandler = innerHandler };
}).Build();
Contoh sebelumnya mengonfigurasi URL koneksi hub ke alamat URI absolut di /chathub
. URI juga dapat diatur melalui string, misalnya https://signalr.example.com
, atau melalui konfigurasi. Navigation
adalah disuntikkan NavigationManager.
Untuk informasi selengkapnya, lihat konfigurasi ASP.NET CoreSignalR.
Penyajian sisi klien
Jika pra-penyajian dikonfigurasi, pra-penyajian terjadi sebelum koneksi klien ke server dibuat. Untuk informasi selengkapnya, lihat Prarender komponen ASP.NET CoreRazor.
Jika pra-penyajian dikonfigurasi, pra-penyajian terjadi sebelum koneksi klien ke server dibuat. Untuk informasi lebih lanjut, baca artikel berikut:
Ukuran status dan SignalR batas ukuran pesan yang telah dirender sebelumnya
Ukuran status besar yang telah dirender mungkin melebihi SignalR batas ukuran pesan sirkuit, yang menghasilkan hal berikut:
- SignalR Sirkuit gagal diinisialisasi dengan kesalahan pada klien:Circuit host not initialized.
- Antarmuka pengguna koneksi ulang pada klien muncul ketika sirkuit gagal. Pemulihan tidak dimungkinkan.
Untuk mengatasi masalah tersebut, gunakan salah satu pendekatan berikut:
- Kurangi jumlah data yang Anda masukkan ke dalam status yang telah dirender sebelumnya.
- Tingkatkan SignalR batas ukuran pesan. PERINGATAN: Meningkatkan batas dapat meningkatkan risiko serangan Denial of Service (DoS).
Sumber daya sisi klien tambahan
- SignalR Mengamankan hub
- Gambaran umum ASP.NET Core SignalR
- Konfigurasi ASP.NET Core SignalR
- Blazorsampel repositori GitHub () (
dotnet/blazor-samples
cara mengunduh)
Gunakan afinitas sesi (sesi lengket) untuk hosting webfarm sisi server
Ketika lebih dari satu server backend sedang digunakan, aplikasi harus menerapkan afinitas sesi, juga disebut sesi lengket. Afinitas sesi memastikan bahwa sirkuit klien terhubung kembali ke server yang sama jika koneksi terputus, yang penting karena status klien hanya disimpan dalam memori server yang pertama kali menetapkan sirkuit klien.
Kesalahan berikut dilemparkan oleh aplikasi yang belum mengaktifkan afinitas sesi di webfarm:
Uncaught (in promise) Error: Invocation canceled due to the underlying connection being closed.
Untuk informasi selengkapnya tentang afinitas sesi dengan hosting Azure App Service, lihat Menghosting dan menyebarkan aplikasi sisi Blazor server ASP.NET Core.
Layanan Azure SignalR
Layanan Azure SignalR opsional berfungsi bersama dengan hub aplikasi SignalR untuk meningkatkan skala aplikasi sisi server ke sejumlah besar koneksi bersamaan. Selain itu, jangkauan global layanan dan pusat data berkinerja tinggi secara signifikan membantu mengurangi latensi karena geografi.
Layanan ini tidak diperlukan untuk Blazor aplikasi yang dihosting di Azure App Service atau Azure Container Apps tetapi dapat membantu di lingkungan hosting lainnya:
- Untuk memfasilitasi peluasan skala koneksi.
- Menangani distribusi global.
Untuk informasi selengkapnya, lihat Menghosting dan menyebarkan aplikasi sisi Blazor server ASP.NET Core.
Opsi penanganan sirkuit sisi server
Konfigurasikan sirkuit dengan CircuitOptions. Lihat nilai default di sumber referensi.
Catatan
Tautan dokumentasi ke sumber referensi .NET biasanya memuat cabang default repositori, yang mewakili pengembangan saat ini untuk rilis .NET berikutnya. Untuk memilih tag rilis tertentu, gunakan daftar dropdown Beralih cabang atau tag. Untuk informasi lebih lanjut, lihat Cara memilih tag versi kode sumber ASP.NET Core (dotnet/AspNetCore.Docs #26205).
Membaca atau mengatur opsi dalam Program
file dengan opsi yang mendelegasikan ke AddInteractiveServerComponents. Tempat {OPTION}
penampung mewakili opsi, dan {VALUE}
tempat penampung adalah nilainya.
Dalam file Program
:
builder.Services.AddRazorComponents().AddInteractiveServerComponents(options =>
{
options.{OPTION} = {VALUE};
});
Membaca atau mengatur opsi dalam Program
file dengan opsi yang mendelegasikan ke AddServerSideBlazor. Tempat {OPTION}
penampung mewakili opsi, dan {VALUE}
tempat penampung adalah nilainya.
Dalam file Program
:
builder.Services.AddServerSideBlazor(options =>
{
options.{OPTION} = {VALUE};
});
Membaca atau mengatur opsi di Startup.ConfigureServices
dengan opsi yang mendelegasikan ke AddServerSideBlazor. Tempat {OPTION}
penampung mewakili opsi, dan {VALUE}
tempat penampung adalah nilainya.
Dalam Startup.ConfigureServices
dari Startup.cs
:
services.AddServerSideBlazor(options =>
{
options.{OPTION} = {VALUE};
});
Untuk mengonfigurasi HubConnectionContext, gunakan HubConnectionContextOptions dengan AddHubOptions. Lihat default untuk opsi konteks koneksi hub di sumber referensi. Untuk deskripsi opsi dalam SignalR dokumentasi, lihat konfigurasi ASP.NET CoreSignalR. Tempat {OPTION}
penampung mewakili opsi, dan {VALUE}
tempat penampung adalah nilainya.
Catatan
Tautan dokumentasi ke sumber referensi .NET biasanya memuat cabang default repositori, yang mewakili pengembangan saat ini untuk rilis .NET berikutnya. Untuk memilih tag rilis tertentu, gunakan daftar dropdown Beralih cabang atau tag. Untuk informasi lebih lanjut, lihat Cara memilih tag versi kode sumber ASP.NET Core (dotnet/AspNetCore.Docs #26205).
Dalam file Program
:
builder.Services.AddRazorComponents().AddInteractiveServerComponents().AddHubOptions(options =>
{
options.{OPTION} = {VALUE};
});
Dalam file Program
:
builder.Services.AddServerSideBlazor().AddHubOptions(options =>
{
options.{OPTION} = {VALUE};
});
Dalam Startup.ConfigureServices
dari Startup.cs
:
services.AddServerSideBlazor().AddHubOptions(options =>
{
options.{OPTION} = {VALUE};
});
Peringatan
Nilai MaximumReceiveMessageSize default adalah 32 KB. Meningkatkan nilai dapat meningkatkan risiko serangan Denial of Service (DoS).
Blazor bergantung pada MaximumParallelInvocationsPerClient atur ke 1, yang merupakan nilai default. Untuk informasi selengkapnya, lihat MaximumParallelInvocationsPerClient > 1 memutus unggahan file dalam Blazor Server mode (dotnet/aspnetcore
#53951).
Untuk informasi tentang manajemen memori, lihat Menghosting dan menyebarkan aplikasi sisi Blazor server ASP.NET Core.
Blazor opsi hub
Konfigurasikan MapBlazorHub opsi untuk mengontrol HttpConnectionDispatcherOptions Blazor hub. Lihat default untuk opsi dispatcher koneksi hub di sumber referensi. Tempat {OPTION}
penampung mewakili opsi, dan {VALUE}
tempat penampung adalah nilainya.
Catatan
Tautan dokumentasi ke sumber referensi .NET biasanya memuat cabang default repositori, yang mewakili pengembangan saat ini untuk rilis .NET berikutnya. Untuk memilih tag rilis tertentu, gunakan daftar dropdown Beralih cabang atau tag. Untuk informasi lebih lanjut, lihat Cara memilih tag versi kode sumber ASP.NET Core (dotnet/AspNetCore.Docs #26205).
Lakukan panggilan app.MapBlazorHub
setelah panggilan ke app.MapRazorComponents
dalam file aplikasi Program
:
app.MapBlazorHub(options =>
{
options.{OPTION} = {VALUE};
});
Mengonfigurasi hub yang digunakan oleh AddInteractiveServerRenderMode dengan MapBlazorHub gagal dengan AmbiguousMatchException
:
Microsoft.AspNetCore.Routing.Matching.AmbiguousMatchException: The request matched multiple endpoints.
Untuk mengatasi masalah untuk aplikasi yang menargetkan .NET 8, berikan hub yang dikonfigurasi Blazor khusus lebih diutamakan menggunakan WithOrder metode :
app.MapBlazorHub(options =>
{
options.CloseOnAuthenticationExpiration = true;
}).WithOrder(-1);
Untuk informasi selengkapnya, lihat sumber daya berikut:
Berikan opsi ke app.MapBlazorHub
dalam file aplikasi Program
:
app.MapBlazorHub(options =>
{
options.{OPTION} = {VALUE};
});
Berikan opsi ke app.MapBlazorHub
dalam konfigurasi perutean titik akhir:
app.UseEndpoints(endpoints =>
{
endpoints.MapBlazorHub(options =>
{
options.{OPTION} = {VALUE};
});
...
});
Ukuran pesan penerimaan maksimum
Bagian ini hanya berlaku untuk proyek yang mengimplementasikan SignalR.
Ukuran pesan masuk SignalR maksimum yang diizinkan untuk metode hub dibatasi oleh HubOptions.MaximumReceiveMessageSize (default: 32 KB). SignalR pesan yang lebih besar dari MaximumReceiveMessageSize melemparkan kesalahan. Kerangka kerja tidak memberlakukan batasan SignalR ukuran pesan dari hub ke klien.
Saat SignalR pengelogan tidak diatur ke Debug atau Pelacakan, kesalahan ukuran pesan hanya muncul di konsol alat pengembang browser:
Kesalahan: Koneksi terputus dengan kesalahan 'Kesalahan: Server mengembalikan kesalahan saat ditutup: Koneksi ditutup dengan kesalahan.'.
Saat SignalR pengelogan sisi server diatur ke Debug atau Pelacakan, pengelogan sisi server menampilkan InvalidDataException kesalahan ukuran pesan.
appsettings.Development.json
:
{
"DetailedErrors": true,
"Logging": {
"LogLevel": {
...
"Microsoft.AspNetCore.SignalR": "Debug"
}
}
}
Kesalahan:
System.IO.InvalidDataException: Ukuran pesan maksimum 32768B terlampaui. Ukuran pesan dapat dikonfigurasi di AddHubOptions.
Salah satu pendekatan melibatkan peningkatan batas dengan mengatur MaximumReceiveMessageSize dalam Program
file. Contoh berikut mengatur ukuran pesan penerimaan maksimum menjadi 64 KB:
builder.Services.AddRazorComponents().AddInteractiveServerComponents()
.AddHubOptions(options => options.MaximumReceiveMessageSize = 64 * 1024);
SignalR Meningkatkan batas ukuran pesan masuk dikenakan biaya untuk membutuhkan lebih banyak sumber daya server, dan meningkatkan risiko serangan Denial of Service (DoS). Selain itu, membaca sejumlah besar konten ke memori sebagai string atau array byte juga dapat mengakibatkan alokasi yang bekerja dengan buruk dengan pengumpul sampah, yang mengakibatkan hukuman performa tambahan.
Opsi yang lebih baik untuk membaca payload besar adalah mengirim konten dalam gugus yang lebih kecil dan memproses payload sebagai Stream. Ini dapat digunakan saat membaca payload JSON interop JavaScript (JS) besar atau jika JS data interop tersedia sebagai byte mentah. Misalnya yang menunjukkan pengiriman payload biner besar di aplikasi sisi server yang menggunakan teknik yang mirip InputFile
dengan komponen, lihat aplikasi sampel Binary Submit danBlazorInputLargeTextArea
Sampel Komponen.
Catatan
Tautan dokumentasi ke sumber referensi .NET biasanya memuat cabang default repositori, yang mewakili pengembangan saat ini untuk rilis .NET berikutnya. Untuk memilih tag rilis tertentu, gunakan daftar dropdown Beralih cabang atau tag. Untuk informasi lebih lanjut, lihat Cara memilih tag versi kode sumber ASP.NET Core (dotnet/AspNetCore.Docs #26205).
Formulir yang memproses payload besar juga SignalR dapat menggunakan interop streaming JS secara langsung. Untuk informasi selengkapnya, lihat Memanggil metode .NET dari fungsi JavaScript di ASP.NET Core Blazor. Untuk contoh formulir yang mengalirkan <textarea>
data ke server, lihat Memecahkan masalah formulir ASP.NET CoreBlazor.
Salah satu pendekatan melibatkan peningkatan batas dengan mengatur MaximumReceiveMessageSize dalam Program
file. Contoh berikut mengatur ukuran pesan penerimaan maksimum menjadi 64 KB:
builder.Services.AddServerSideBlazor()
.AddHubOptions(options => options.MaximumReceiveMessageSize = 64 * 1024);
SignalR Meningkatkan batas ukuran pesan masuk dikenakan biaya untuk membutuhkan lebih banyak sumber daya server, dan meningkatkan risiko serangan Denial of Service (DoS). Selain itu, membaca sejumlah besar konten ke memori sebagai string atau array byte juga dapat mengakibatkan alokasi yang bekerja dengan buruk dengan pengumpul sampah, yang mengakibatkan hukuman performa tambahan.
Opsi yang lebih baik untuk membaca payload besar adalah mengirim konten dalam gugus yang lebih kecil dan memproses payload sebagai Stream. Ini dapat digunakan saat membaca payload JSON interop JavaScript (JS) besar atau jika JS data interop tersedia sebagai byte mentah. Misalnya yang menunjukkan pengiriman payload biner besar dalam Blazor Server yang menggunakan teknik yang mirip InputFile
dengan komponen, lihat aplikasi sampel Binary Submit danInputLargeTextArea
BlazorSampel Komponen.
Catatan
Tautan dokumentasi ke sumber referensi .NET biasanya memuat cabang default repositori, yang mewakili pengembangan saat ini untuk rilis .NET berikutnya. Untuk memilih tag rilis tertentu, gunakan daftar dropdown Beralih cabang atau tag. Untuk informasi lebih lanjut, lihat Cara memilih tag versi kode sumber ASP.NET Core (dotnet/AspNetCore.Docs #26205).
Formulir yang memproses payload besar juga SignalR dapat menggunakan interop streaming JS secara langsung. Untuk informasi selengkapnya, lihat Memanggil metode .NET dari fungsi JavaScript di ASP.NET Core Blazor. Untuk contoh formulir yang mengalirkan data dalam Blazor Server aplikasi, lihat Memecahkan masalah formulir ASP.NET CoreBlazor.<textarea>
Tingkatkan batas dengan mengatur MaximumReceiveMessageSize di Startup.ConfigureServices
:
services.AddServerSideBlazor()
.AddHubOptions(options => options.MaximumReceiveMessageSize = 64 * 1024);
SignalR Meningkatkan batas ukuran pesan masuk dikenakan biaya untuk membutuhkan lebih banyak sumber daya server, dan meningkatkan risiko serangan Denial of Service (DoS). Selain itu, membaca sejumlah besar konten ke memori sebagai string atau array byte juga dapat mengakibatkan alokasi yang bekerja dengan buruk dengan pengumpul sampah, yang mengakibatkan hukuman performa tambahan.
Pertimbangkan panduan berikut saat mengembangkan kode yang mentransfer sejumlah besar data:
- Manfaatkan dukungan interop streaming JS asli untuk mentransfer data yang lebih besar dari SignalR batas ukuran pesan masuk:
- Tips umum:
- Jangan alokasikan objek besar dalam JS dan kode C#.
- Memori gratis yang dikonsumsi ketika proses selesai atau dibatalkan.
- Berlakukan persyaratan tambahan berikut untuk tujuan keamanan:
- Deklarasikan file maksimum atau ukuran data yang dapat diteruskan.
- Nyatakan tingkat unggahan minimum dari klien ke server.
- Setelah data diterima oleh server, data dapat berupa:
- Disimpan sementara dalam buffer memori hingga semua segmen dikumpulkan.
- Segera dikonsumsi. Misalnya, data dapat segera disimpan dalam database atau ditulis ke disk saat setiap segmen diterima.
- Ikat data menjadi potongan yang lebih kecil, dan kirim segmen data secara berurutan hingga semua data diterima oleh server.
- Jangan alokasikan objek besar dalam JS dan kode C#.
- Jangan memblokir utas UI utama untuk jangka waktu yang lama saat mengirim atau menerima data.
- Memori gratis yang dikonsumsi ketika proses selesai atau dibatalkan.
- Berlakukan persyaratan tambahan berikut untuk tujuan keamanan:
- Deklarasikan file maksimum atau ukuran data yang dapat diteruskan.
- Nyatakan tingkat unggahan minimum dari klien ke server.
- Setelah data diterima oleh server, data dapat berupa:
- Disimpan sementara dalam buffer memori hingga semua segmen dikumpulkan.
- Segera dikonsumsi. Misalnya, data dapat segera disimpan dalam database atau ditulis ke disk saat setiap segmen diterima.
Blazor konfigurasi rute titik akhir Hub sisi server
Program
Dalam file, panggil MapBlazorHub untuk memetakan BlazorHub ke jalur default aplikasi. Blazor Skrip (blazor.*.js
) secara otomatis menunjuk ke titik akhir yang dibuat oleh MapBlazorHub.
Mencerminkan status koneksi sisi server di UI
Ketika klien mendeteksi bahwa koneksi telah hilang, antarmuka pengguna default ditampilkan kepada pengguna saat klien mencoba menyambungkan kembali. Jika koneksi ulang gagal, pengguna disediakan opsi untuk mencoba kembali.
Untuk menyesuaikan UI, tentukan elemen tunggal dengan id
dari components-reconnect-modal
. Contoh berikut menempatkan elemen dalam App
komponen.
App.razor
:
Untuk menyesuaikan UI, tentukan elemen tunggal dengan id
dari components-reconnect-modal
. Contoh berikut menempatkan elemen di halaman host.
Pages/_Host.cshtml
:
Untuk menyesuaikan UI, tentukan elemen tunggal dengan id
dari components-reconnect-modal
. Contoh berikut menempatkan elemen di halaman tata letak.
Pages/_Layout.cshtml
:
Untuk menyesuaikan UI, tentukan elemen tunggal dengan id
dari components-reconnect-modal
. Contoh berikut menempatkan elemen di halaman host.
Pages/_Host.cshtml
:
<div id="components-reconnect-modal">
There was a problem with the connection!
</div>
Catatan
Jika lebih dari satu elemen dengan id
dirender components-reconnect-modal
oleh aplikasi, hanya elemen pertama yang dirender yang menerima perubahan kelas CSS untuk menampilkan atau menyembunyikan elemen.
Tambahkan gaya CSS berikut ke lembar gaya situs.
wwwroot/app.css
:
wwwroot/css/site.css
:
#components-reconnect-modal {
display: none;
}
#components-reconnect-modal.components-reconnect-show,
#components-reconnect-modal.components-reconnect-failed,
#components-reconnect-modal.components-reconnect-rejected {
display: block;
}
Tabel berikut ini menjelaskan kelas CSS yang diterapkan ke components-reconnect-modal
elemen oleh Blazor kerangka kerja.
Kelas CSS | Menunjukkan... |
---|---|
components-reconnect-show |
Koneksi yang hilang. Klien mencoba menyambungkan kembali. Tampilkan modal. |
components-reconnect-hide |
Koneksi aktif dibuat ulang ke server. Sembunyikan modal. |
components-reconnect-failed |
Koneksi ulang gagal, mungkin karena kegagalan jaringan. Untuk mencoba menyambungkan kembali, panggil window.Blazor.reconnect() di JavaScript. |
components-reconnect-rejected |
Koneksi ulang ditolak. Server tercapai tetapi menolak koneksi, dan status pengguna di server hilang. Untuk memuat ulang aplikasi, panggil location.reload() di JavaScript. Status koneksi ini dapat mengakibatkan ketika:
|
Kustomisasi penundaan sebelum antarmuka pengguna koneksi ulang muncul dengan mengatur transition-delay
properti di CSS situs untuk elemen modal. Contoh berikut mengatur penundaan transisi dari 500 md (default) menjadi 1.000 md (1 detik).
wwwroot/app.css
:
wwwroot/css/site.css
:
#components-reconnect-modal {
transition: visibility 0s linear 1000ms;
}
Untuk menampilkan upaya koneksi ulang saat ini, tentukan elemen dengan id
.components-reconnect-current-attempt
Untuk menampilkan jumlah maksimum percobaan ulang koneksi ulang, tentukan elemen dengan id
.components-reconnect-max-retries
Contoh berikut menempatkan elemen-elemen ini di dalam elemen modal upaya koneksi ulang mengikuti contoh sebelumnya.
<div id="components-reconnect-modal">
There was a problem with the connection!
(Current reconnect attempt:
<span id="components-reconnect-current-attempt"></span> /
<span id="components-reconnect-max-retries"></span>)
</div>
Saat modal koneksi ulang kustom muncul, ini merender konten yang mirip dengan yang berikut ini berdasarkan kode sebelumnya:
There was a problem with the connection! (Current reconnect attempt: 3 / 8)
Penyajian sisi server
Secara default, komponen telah dirender di server sebelum koneksi klien ke server dibuat. Untuk informasi selengkapnya, lihat Prarender komponen ASP.NET CoreRazor.
Secara default, komponen telah dirender di server sebelum koneksi klien ke server dibuat. Untuk informasi selengkapnya, lihat Pembantu Tag Komponen di ASP.NET Core.
Memantau aktivitas sirkuit sisi server
Pantau aktivitas sirkuit masuk menggunakan CreateInboundActivityHandler metode pada CircuitHandler. Aktivitas sirkuit masuk adalah aktivitas apa pun yang dikirim dari browser ke server, seperti peristiwa UI atau panggilan interop JavaScript-to-.NET.
Misalnya, Anda dapat menggunakan handler aktivitas sirkuit untuk mendeteksi apakah klien menganggur dan mencatat ID sirkuitnya (Circuit.Id):
using Microsoft.AspNetCore.Components.Server.Circuits;
using Microsoft.Extensions.Options;
using Timer = System.Timers.Timer;
public sealed class IdleCircuitHandler : CircuitHandler, IDisposable
{
private Circuit? currentCircuit;
private readonly ILogger logger;
private readonly Timer timer;
public IdleCircuitHandler(ILogger<IdleCircuitHandler> logger,
IOptions<IdleCircuitOptions> options)
{
timer = new Timer
{
Interval = options.Value.IdleTimeout.TotalMilliseconds,
AutoReset = false
};
timer.Elapsed += CircuitIdle;
this.logger = logger;
}
private void CircuitIdle(object? sender, System.Timers.ElapsedEventArgs e)
{
logger.LogInformation("{CircuitId} is idle", currentCircuit?.Id);
}
public override Task OnCircuitOpenedAsync(Circuit circuit,
CancellationToken cancellationToken)
{
currentCircuit = circuit;
return Task.CompletedTask;
}
public override Func<CircuitInboundActivityContext, Task> CreateInboundActivityHandler(
Func<CircuitInboundActivityContext, Task> next)
{
return context =>
{
timer.Stop();
timer.Start();
return next(context);
};
}
public void Dispose() => timer.Dispose();
}
public class IdleCircuitOptions
{
public TimeSpan IdleTimeout { get; set; } = TimeSpan.FromMinutes(5);
}
public static class IdleCircuitHandlerServiceCollectionExtensions
{
public static IServiceCollection AddIdleCircuitHandler(
this IServiceCollection services,
Action<IdleCircuitOptions> configureOptions)
{
services.Configure(configureOptions);
services.AddIdleCircuitHandler();
return services;
}
public static IServiceCollection AddIdleCircuitHandler(
this IServiceCollection services)
{
services.AddScoped<CircuitHandler, IdleCircuitHandler>();
return services;
}
}
Daftarkan layanan dalam Program
file. Contoh berikut mengonfigurasi batas waktu menganggur default lima menit hingga lima detik untuk menguji implementasi sebelumnya IdleCircuitHandler
:
builder.Services.AddIdleCircuitHandler(options =>
options.IdleTimeout = TimeSpan.FromSeconds(5));
Penangan aktivitas sirkuit juga menyediakan pendekatan untuk mengakses layanan tercakup Blazor dari cakupan injeksi non-dependensiBlazor (DI) lainnya. Untuk informasi dan contoh selengkapnya, lihat:
Blazor Startup
Konfigurasikan awal Blazor manual sirkuit aplikasi SignalR dalam App.razor
file Blazor Web App:
Konfigurasikan awal Blazor manual sirkuit aplikasi SignalR dalam Pages/_Host.cshtml
file (Blazor Server):
Konfigurasikan awal Blazor manual sirkuit aplikasi SignalR dalam Pages/_Layout.cshtml
file (Blazor Server):
Konfigurasikan awal Blazor manual sirkuit aplikasi SignalR dalam Pages/_Host.cshtml
file (Blazor Server):
autostart="false"
Tambahkan atribut ke<script>
tag untukblazor.*.js
skrip.- Tempatkan skrip yang memanggil
Blazor.start()
setelah Blazor skrip dimuat dan di dalam tag penutup</body>
.
Saat autostart
dinonaktifkan, aspek apa pun dari aplikasi yang tidak bergantung pada sirkuit berfungsi secara normal. Misalnya, perutean sisi klien beroperasi. Namun, aspek apa pun yang tergantung pada sirkuit tidak beroperasi sampai Blazor.start()
dipanggil. Perilaku aplikasi tidak dapat diprediksi tanpa sirkuit yang mapan. Misalnya, metode komponen gagal dijalankan saat sirkuit terputus.
Untuk informasi selengkapnya, termasuk cara menginisialisasi Blazor saat dokumen siap dan cara menautkan ke JS Promise
, lihat startup ASP.NET CoreBlazor.
Mengonfigurasi SignalR batas waktu dan Keep-Alive pada klien
Konfigurasikan nilai berikut untuk klien:
withServerTimeout
: Mengonfigurasi batas waktu server dalam milidetik. Jika batas waktu ini berlalu tanpa menerima pesan apa pun dari server, koneksi dihentikan dengan kesalahan. Nilai batas waktu default adalah 30 detik. Batas waktu server harus setidaknya dua kali lipat nilai yang ditetapkan ke interval Keep-Alive (withKeepAliveInterval
).withKeepAliveInterval
: Mengonfigurasi interval Keep-Alive dalam milidetik (interval default untuk melakukan ping server). Pengaturan ini memungkinkan server mendeteksi pemutusan sambungan keras, seperti ketika klien mencabut sambungan komputernya dari jaringan. Ping paling sering terjadi sesering ping server. Jika server melakukan ping setiap lima detik, menetapkan nilai yang lebih rendah dari5000
(5 detik) ping setiap lima detik. Nilai defaultnya adalah 15 detik. Interval Keep-Alive harus kurang dari atau sama dengan setengah nilai yang ditetapkan ke batas waktu server (withServerTimeout
).
Contoh berikut untuk App.razor
file (Blazor Web App) menunjukkan penetapan nilai default.
Blazor Web App:
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script>
Blazor.start({
circuit: {
configureSignalR: function (builder) {
builder.withServerTimeout(30000).withKeepAliveInterval(15000);
}
}
});
</script>
Contoh berikut untuk Pages/_Host.cshtml
file (Blazor Server, semua versi kecuali ASP.NET Core di .NET 6) atau Pages/_Layout.cshtml
file (Blazor Server, ASP.NET Core di .NET 6).
Blazor Server:
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script>
Blazor.start({
configureSignalR: function (builder) {
builder.withServerTimeout(30000).withKeepAliveInterval(15000);
}
});
</script>
Dalam contoh sebelumnya, {BLAZOR SCRIPT}
tempat penampung adalah Blazor jalur skrip dan nama file. Untuk lokasi skrip dan jalur yang akan digunakan, lihat struktur proyek ASP.NET CoreBlazor.
Saat membuat koneksi hub dalam komponen, atur ServerTimeout (default: 30 detik) dan KeepAliveInterval (default: 15 detik) pada HubConnectionBuilder. Atur HandshakeTimeout (default: 15 detik) pada bawaan HubConnection. Contoh berikut menunjukkan penetapan nilai default:
protected override async Task OnInitializedAsync()
{
hubConnection = new HubConnectionBuilder()
.WithUrl(Navigation.ToAbsoluteUri("/chathub"))
.WithServerTimeout(TimeSpan.FromSeconds(30))
.WithKeepAliveInterval(TimeSpan.FromSeconds(15))
.Build();
hubConnection.HandshakeTimeout = TimeSpan.FromSeconds(15);
hubConnection.On<string, string>("ReceiveMessage", (user, message) => ...
await hubConnection.StartAsync();
}
Konfigurasikan nilai berikut untuk klien:
serverTimeoutInMilliseconds
: Batas waktu server dalam milidetik. Jika batas waktu ini berlalu tanpa menerima pesan apa pun dari server, koneksi dihentikan dengan kesalahan. Nilai batas waktu default adalah 30 detik. Batas waktu server harus setidaknya dua kali lipat nilai yang ditetapkan ke interval Keep-Alive (keepAliveIntervalInMilliseconds
).keepAliveIntervalInMilliseconds
: Interval default untuk melakukan ping pada server. Pengaturan ini memungkinkan server mendeteksi pemutusan sambungan keras, seperti ketika klien mencabut sambungan komputernya dari jaringan. Ping paling sering terjadi sesering ping server. Jika server melakukan ping setiap lima detik, menetapkan nilai yang lebih rendah dari5000
(5 detik) ping setiap lima detik. Nilai defaultnya adalah 15 detik. Interval Keep-Alive harus kurang dari atau sama dengan setengah nilai yang ditetapkan ke batas waktu server (serverTimeoutInMilliseconds
).
Contoh berikut untuk Pages/_Host.cshtml
file (Blazor Server, semua versi kecuali ASP.NET Core di .NET 6) atau Pages/_Layout.cshtml
file (Blazor Server, ASP.NET Core di .NET 6):
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script>
Blazor.start({
configureSignalR: function (builder) {
let c = builder.build();
c.serverTimeoutInMilliseconds = 30000;
c.keepAliveIntervalInMilliseconds = 15000;
builder.build = () => {
return c;
};
}
});
</script>
Dalam contoh sebelumnya, {BLAZOR SCRIPT}
tempat penampung adalah Blazor jalur skrip dan nama file. Untuk lokasi skrip dan jalur yang akan digunakan, lihat struktur proyek ASP.NET CoreBlazor.
Saat membuat koneksi hub dalam komponen, atur ServerTimeout (default: 30 detik), HandshakeTimeout (default: 15 detik), dan KeepAliveInterval (default: 15 detik) di bawaan HubConnection. Contoh berikut menunjukkan penetapan nilai default:
protected override async Task OnInitializedAsync()
{
hubConnection = new HubConnectionBuilder()
.WithUrl(Navigation.ToAbsoluteUri("/chathub"))
.Build();
hubConnection.ServerTimeout = TimeSpan.FromSeconds(30);
hubConnection.HandshakeTimeout = TimeSpan.FromSeconds(15);
hubConnection.KeepAliveInterval = TimeSpan.FromSeconds(15);
hubConnection.On<string, string>("ReceiveMessage", (user, message) => ...
await hubConnection.StartAsync();
}
Saat mengubah nilai batas waktu server (ServerTimeout) atau interval Keep-Alive (KeepAliveInterval):
- Batas waktu server harus setidaknya dua kali lipat nilai yang ditetapkan ke interval Keep-Alive.
- Interval Keep-Alive harus kurang dari atau sama dengan setengah nilai yang ditetapkan ke batas waktu server.
Untuk informasi selengkapnya, lihat bagian Penyebaran global dan kegagalan koneksi dari artikel berikut ini:
- Menghosting dan menyebarkan aplikasi sisi Blazor server ASP.NET Core
- Menghosting dan menyebarkan ASP.NET Core Blazor WebAssembly
Mengubah handler koneksi ulang sisi server
Peristiwa koneksi sirkuit handler rekoneksi dapat dimodifikasi untuk perilaku kustom, seperti:
- Untuk memberi tahu pengguna jika koneksi terputus.
- Untuk melakukan pengelogan (dari klien) saat sirkuit tersambung.
Untuk mengubah peristiwa koneksi, daftarkan panggilan balik untuk perubahan koneksi berikut:
- Koneksi yang dihilangkan menggunakan
onConnectionDown
. - Koneksi yang dibuat/dibuat ulang menggunakan
onConnectionUp
.
Keduanya onConnectionDown
dan onConnectionUp
harus ditentukan.
Blazor Web App:
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script>
Blazor.start({
circuit: {
reconnectionHandler: {
onConnectionDown: (options, error) => console.error(error),
onConnectionUp: () => console.log("Up, up, and away!")
}
}
});
</script>
Blazor Server:
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script>
Blazor.start({
reconnectionHandler: {
onConnectionDown: (options, error) => console.error(error),
onConnectionUp: () => console.log("Up, up, and away!")
}
});
</script>
Dalam contoh sebelumnya, {BLAZOR SCRIPT}
tempat penampung adalah Blazor jalur skrip dan nama file. Untuk lokasi skrip dan jalur yang akan digunakan, lihat struktur proyek ASP.NET CoreBlazor.
Merefresh halaman secara otomatis saat koneksi ulang sisi server gagal
Perilaku koneksi ulang default mengharuskan pengguna untuk mengambil tindakan manual untuk menyegarkan halaman setelah koneksi ulang gagal. Namun, handler rekoneksi kustom dapat digunakan untuk me-refresh halaman secara otomatis:
App.razor
:
Pages/_Host.cshtml
:
<div id="reconnect-modal" style="display: none;"></div>
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script src="boot.js"></script>
Dalam contoh sebelumnya, {BLAZOR SCRIPT}
tempat penampung adalah Blazor jalur skrip dan nama file. Untuk lokasi skrip dan jalur yang akan digunakan, lihat struktur proyek ASP.NET CoreBlazor.
Buat file berikut wwwroot/boot.js
.
Blazor Web App:
(() => {
const maximumRetryCount = 3;
const retryIntervalMilliseconds = 5000;
const reconnectModal = document.getElementById('reconnect-modal');
const startReconnectionProcess = () => {
reconnectModal.style.display = 'block';
let isCanceled = false;
(async () => {
for (let i = 0; i < maximumRetryCount; i++) {
reconnectModal.innerText = `Attempting to reconnect: ${i + 1} of ${maximumRetryCount}`;
await new Promise(resolve => setTimeout(resolve, retryIntervalMilliseconds));
if (isCanceled) {
return;
}
try {
const result = await Blazor.reconnect();
if (!result) {
// The server was reached, but the connection was rejected; reload the page.
location.reload();
return;
}
// Successfully reconnected to the server.
return;
} catch {
// Didn't reach the server; try again.
}
}
// Retried too many times; reload the page.
location.reload();
})();
return {
cancel: () => {
isCanceled = true;
reconnectModal.style.display = 'none';
},
};
};
let currentReconnectionProcess = null;
Blazor.start({
circuit: {
reconnectionHandler: {
onConnectionDown: () => currentReconnectionProcess ??= startReconnectionProcess(),
onConnectionUp: () => {
currentReconnectionProcess?.cancel();
currentReconnectionProcess = null;
}
}
}
});
})();
Blazor Server:
(() => {
const maximumRetryCount = 3;
const retryIntervalMilliseconds = 5000;
const reconnectModal = document.getElementById('reconnect-modal');
const startReconnectionProcess = () => {
reconnectModal.style.display = 'block';
let isCanceled = false;
(async () => {
for (let i = 0; i < maximumRetryCount; i++) {
reconnectModal.innerText = `Attempting to reconnect: ${i + 1} of ${maximumRetryCount}`;
await new Promise(resolve => setTimeout(resolve, retryIntervalMilliseconds));
if (isCanceled) {
return;
}
try {
const result = await Blazor.reconnect();
if (!result) {
// The server was reached, but the connection was rejected; reload the page.
location.reload();
return;
}
// Successfully reconnected to the server.
return;
} catch {
// Didn't reach the server; try again.
}
}
// Retried too many times; reload the page.
location.reload();
})();
return {
cancel: () => {
isCanceled = true;
reconnectModal.style.display = 'none';
},
};
};
let currentReconnectionProcess = null;
Blazor.start({
reconnectionHandler: {
onConnectionDown: () => currentReconnectionProcess ??= startReconnectionProcess(),
onConnectionUp: () => {
currentReconnectionProcess?.cancel();
currentReconnectionProcess = null;
}
}
});
})();
Untuk informasi lebih lanjut tentang startup Blazor, lihat startup BlazorASP.NET Core.
Menyesuaikan jumlah dan interval coba lagi koneksi ulang sisi server
Untuk menyesuaikan jumlah dan interval coba lagi koneksi ulang, atur jumlah percobaan ulang (maxRetries
) dan periode dalam milidetik yang diizinkan untuk setiap upaya coba lagi (retryIntervalMilliseconds
).
Blazor Web App:
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script>
Blazor.start({
circuit: {
reconnectionOptions: {
maxRetries: 3,
retryIntervalMilliseconds: 2000
}
}
});
</script>
Blazor Server:
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script>
Blazor.start({
reconnectionOptions: {
maxRetries: 3,
retryIntervalMilliseconds: 2000
}
});
</script>
Dalam contoh sebelumnya, {BLAZOR SCRIPT}
tempat penampung adalah Blazor jalur skrip dan nama file. Untuk lokasi skrip dan jalur yang akan digunakan, lihat struktur proyek ASP.NET CoreBlazor.
Saat pengguna menavigasi kembali ke aplikasi dengan sirkuit yang terputus, koneksi ulang dicoba segera daripada menunggu durasi interval koneksi ulang berikutnya. Perilaku ini berusaha melanjutkan koneksi secepat mungkin untuk pengguna.
Waktu koneksi ulang default menggunakan strategi backoff komputasi. Beberapa upaya koneksi ulang pertama terjadi secara berturut-turut sebelum penundaan komputasi diperkenalkan di antara upaya. Logika default untuk menghitung interval coba lagi adalah detail implementasi yang dapat berubah tanpa pemberitahuan, tetapi Anda dapat menemukan logika default yang Blazor digunakan kerangka kerja dalam computeDefaultRetryInterval
fungsi (sumber referensi).
Catatan
Tautan dokumentasi ke sumber referensi .NET biasanya memuat cabang default repositori, yang mewakili pengembangan saat ini untuk rilis .NET berikutnya. Untuk memilih tag rilis tertentu, gunakan daftar dropdown Beralih cabang atau tag. Untuk informasi lebih lanjut, lihat Cara memilih tag versi kode sumber ASP.NET Core (dotnet/AspNetCore.Docs #26205).
Sesuaikan perilaku interval coba lagi dengan menentukan fungsi untuk menghitung interval coba lagi. Dalam contoh backoff eksponensial berikut, jumlah upaya koneksi ulang sebelumnya dikalikan dengan 1.000 ms untuk menghitung interval coba lagi. Ketika jumlah upaya sebelumnya untuk menyambungkan kembali (previousAttempts
) lebih besar dari batas coba lagi maksimum (maxRetries
), null
ditetapkan ke interval coba lagi (retryIntervalMilliseconds
) untuk menghentikan upaya koneksi ulang lebih lanjut:
Blazor.start({
circuit: {
reconnectionOptions: {
retryIntervalMilliseconds: (previousAttempts, maxRetries) =>
previousAttempts >= maxRetries ? null : previousAttempts * 1000
},
},
});
Alternatifnya adalah menentukan urutan interval coba lagi yang tepat. Setelah interval coba lagi yang terakhir ditentukan, coba lagi berhenti karena retryIntervalMilliseconds
fungsi mengembalikan undefined
:
Blazor.start({
circuit: {
reconnectionOptions: {
retryIntervalMilliseconds:
Array.prototype.at.bind([0, 1000, 2000, 5000, 10000, 15000, 30000]),
},
},
});
Untuk informasi lebih lanjut tentang startup Blazor, lihat startup BlazorASP.NET Core.
Kontrol saat antarmuka pengguna koneksi ulang muncul
Mengontrol kapan antarmuka pengguna koneksi ulang muncul dapat berguna dalam situasi berikut:
- Aplikasi yang disebarkan sering menampilkan antarmuka pengguna koneksi ulang karena batas waktu ping yang disebabkan oleh jaringan internal atau latensi Internet, dan Anda ingin meningkatkan penundaan.
- Aplikasi harus melaporkan kepada pengguna bahwa koneksi telah turun lebih cepat, dan Anda ingin mempersingkat penundaan.
Waktu munculnya UI koneksi ulang dipengaruhi oleh penyesuaian interval Keep-Alive dan batas waktu pada klien. UI koneksi ulang muncul ketika batas waktu server tercapai pada klien (withServerTimeout
, bagian Konfigurasi klien). Namun, mengubah nilai withServerTimeout
memerlukan perubahan pada pengaturan Keep-Alive, timeout, dan handshake lainnya yang dijelaskan dalam panduan berikut.
Sebagai rekomendasi umum untuk panduan yang mengikuti:
- Interval Keep-Alive harus cocok antara konfigurasi klien dan server.
- Batas waktu harus setidaknya dua kali lipat nilai yang ditetapkan ke interval Keep-Alive.
Konfigurasi server
Atur berikut ini:
- ClientTimeoutInterval (default: 30 detik): Klien jendela waktu harus mengirim pesan sebelum server menutup koneksi.
- HandshakeTimeout (default: 15 detik): Interval yang digunakan oleh server untuk waktu habis permintaan jabat tangan masuk oleh klien.
- KeepAliveInterval (default: 15 detik): Interval yang digunakan oleh server untuk mengirim ping tetap hidup ke klien yang terhubung. Perhatikan bahwa ada juga pengaturan interval Keep-Alive pada klien, yang harus cocok dengan nilai server.
ClientTimeoutInterval dan HandshakeTimeout dapat ditingkatkan, dan KeepAliveInterval dapat tetap sama. Pertimbangan pentingnya adalah bahwa jika Anda mengubah nilai, pastikan bahwa batas waktu setidaknya dua kali lipat nilai interval Keep-Alive dan interval Keep-Alive cocok antara server dan klien. Untuk informasi selengkapnya, lihat bagian Mengonfigurasi SignalR batas waktu dan Keep-Alive di klien .
Dalam contoh berikut:
- ditingkatkan ClientTimeoutInterval menjadi 60 detik (nilai default: 30 detik).
- ditingkatkan HandshakeTimeout menjadi 30 detik (nilai default: 15 detik).
- KeepAliveInterval tidak diatur dalam kode pengembang dan menggunakan nilai defaultnya 15 detik. Mengurangi nilai interval Keep-Alive meningkatkan frekuensi ping komunikasi, yang meningkatkan beban pada aplikasi, server, dan jaringan. Perawatan harus dilakukan untuk menghindari pengenalan performa yang buruk saat menurunkan interval Keep-Alive.
Blazor Web App (.NET 8 atau yang lebih baru) dalam file proyek Program
server:
builder.Services.AddRazorComponents().AddInteractiveServerComponents()
.AddHubOptions(options =>
{
options.ClientTimeoutInterval = TimeSpan.FromSeconds(60);
options.HandshakeTimeout = TimeSpan.FromSeconds(30);
});
Blazor ServerProgram
dalam file:
builder.Services.AddServerSideBlazor()
.AddHubOptions(options =>
{
options.ClientTimeoutInterval = TimeSpan.FromSeconds(60);
options.HandshakeTimeout = TimeSpan.FromSeconds(30);
});
Untuk informasi selengkapnya, lihat bagian Opsi penanganan sirkuit sisi server.
Konfigurasi klien
Atur berikut ini:
withServerTimeout
(default: 30 detik): Mengonfigurasi batas waktu server, yang ditentukan dalam milidetik, untuk koneksi hub sirkuit.withKeepAliveInterval
(default: 15 detik): Interval, yang ditentukan dalam milidetik, di mana koneksi mengirim pesan Keep-Alive.
Batas waktu server dapat ditingkatkan, dan interval Keep-Alive dapat tetap sama. Pertimbangan pentingnya adalah bahwa jika Anda mengubah nilai, pastikan bahwa batas waktu server setidaknya dua kali lipat nilai interval Keep-Alive dan bahwa nilai interval Keep-Alive cocok antara server dan klien. Untuk informasi selengkapnya, lihat bagian Mengonfigurasi SignalR batas waktu dan Keep-Alive di klien .
Dalam contoh konfigurasi startup berikut (lokasi Blazor skrip), nilai kustom 60 detik digunakan untuk batas waktu server. Interval Keep-Alive (withKeepAliveInterval
) tidak diatur dan menggunakan nilai defaultnya 15 detik.
Blazor Web App:
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script>
Blazor.start({
circuit: {
configureSignalR: function (builder) {
builder.withServerTimeout(60000);
}
}
});
</script>
Blazor Server:
<script src="{BLAZOR SCRIPT}" autostart="false"></script>
<script>
Blazor.start({
configureSignalR: function (builder) {
builder.withServerTimeout(60000);
}
});
</script>
Saat membuat koneksi hub dalam komponen, atur batas waktu server (WithServerTimeout, default: 30 detik) pada HubConnectionBuilder. Atur HandshakeTimeout (default: 15 detik) pada bawaan HubConnection. Konfirmasikan bahwa batas waktu setidaknya dua kali lipat interval Keep-Alive (WithKeepAliveInterval/KeepAliveInterval) dan bahwa nilai Keep-Alive cocok antara server dan klien.
Contoh berikut didasarkan pada Index
komponen dalam SignalR tutorial.Blazor Batas waktu server ditingkatkan menjadi 60 detik, dan batas waktu jabat tangan ditingkatkan menjadi 30 detik. Interval Keep-Alive tidak diatur dan menggunakan nilai defaultnya 15 detik.
protected override async Task OnInitializedAsync()
{
hubConnection = new HubConnectionBuilder()
.WithUrl(Navigation.ToAbsoluteUri("/chathub"))
.WithServerTimeout(TimeSpan.FromSeconds(60))
.Build();
hubConnection.HandshakeTimeout = TimeSpan.FromSeconds(30);
hubConnection.On<string, string>("ReceiveMessage", (user, message) => ...
await hubConnection.StartAsync();
}
Atur berikut ini:
serverTimeoutInMilliseconds
(default: 30 detik): Mengonfigurasi batas waktu server, yang ditentukan dalam milidetik, untuk koneksi hub sirkuit.keepAliveIntervalInMilliseconds
(default: 15 detik): Interval, yang ditentukan dalam milidetik, di mana koneksi mengirim pesan Keep-Alive.
Batas waktu server dapat ditingkatkan, dan interval Keep-Alive dapat tetap sama. Pertimbangan pentingnya adalah bahwa jika Anda mengubah nilai, pastikan bahwa batas waktu server setidaknya dua kali lipat nilai interval Keep-Alive dan bahwa nilai interval Keep-Alive cocok antara server dan klien. Untuk informasi selengkapnya, lihat bagian Mengonfigurasi SignalR batas waktu dan Keep-Alive di klien .
Dalam contoh konfigurasi startup berikut (lokasi Blazor skrip), nilai kustom 60 detik digunakan untuk batas waktu server. Interval Keep-Alive (keepAliveIntervalInMilliseconds
) tidak diatur dan menggunakan nilai defaultnya 15 detik.
Di Pages/_Host.cshtml
:
<script src="_framework/blazor.server.js" autostart="false"></script>
<script>
Blazor.start({
configureSignalR: function (builder) {
let c = builder.build();
c.serverTimeoutInMilliseconds = 60000;
builder.build = () => {
return c;
};
}
});
</script>
Saat membuat koneksi hub dalam komponen, atur ServerTimeout (default: 30 detik) dan HandshakeTimeout (default: 15 detik) pada bawaan HubConnection. Konfirmasikan bahwa batas waktu setidaknya dua kali lipat interval Keep-Alive. Konfirmasikan bahwa interval Keep-Alive cocok antara server dan klien.
Contoh berikut didasarkan pada Index
komponen dalam SignalR tutorial.Blazor ditingkatkan ServerTimeout menjadi 60 detik, dan HandshakeTimeout ditingkatkan menjadi 30 detik. Interval Keep-Alive (KeepAliveInterval) tidak diatur dan menggunakan nilai defaultnya 15 detik.
protected override async Task OnInitializedAsync()
{
hubConnection = new HubConnectionBuilder()
.WithUrl(Navigation.ToAbsoluteUri("/chathub"))
.Build();
hubConnection.ServerTimeout = TimeSpan.FromSeconds(60);
hubConnection.HandshakeTimeout = TimeSpan.FromSeconds(30);
hubConnection.On<string, string>("ReceiveMessage", (user, message) => ...
await hubConnection.StartAsync();
}
Memutuskan sambungan Blazor sirkuit dari klien
Blazor Sirkuit terputus saat unload
peristiwa halaman dipicu. Untuk memutuskan sambungan sirkuit untuk skenario lain pada klien, panggil Blazor.disconnect
di penanganan aktivitas yang sesuai. Dalam contoh berikut, sirkuit terputus saat halaman disembunyikan (pagehide
peristiwa):
window.addEventListener('pagehide', () => {
Blazor.disconnect();
});
Untuk informasi lebih lanjut tentang startup Blazor, lihat startup BlazorASP.NET Core.
Handler sirkuit sisi server
Anda dapat menentukan handler sirkuit, yang memungkinkan menjalankan kode pada perubahan pada status sirkuit pengguna. Handler sirkuit diimplementasikan dengan turunan dari CircuitHandler dan mendaftarkan kelas dalam kontainer layanan aplikasi. Contoh handler sirkuit berikut melacak koneksi terbuka SignalR .
TrackingCircuitHandler.cs
:
using Microsoft.AspNetCore.Components.Server.Circuits;
public class TrackingCircuitHandler : CircuitHandler
{
private HashSet<Circuit> circuits = new();
public override Task OnConnectionUpAsync(Circuit circuit,
CancellationToken cancellationToken)
{
circuits.Add(circuit);
return Task.CompletedTask;
}
public override Task OnConnectionDownAsync(Circuit circuit,
CancellationToken cancellationToken)
{
circuits.Remove(circuit);
return Task.CompletedTask;
}
public int ConnectedCircuits => circuits.Count;
}
Penangan sirkuit terdaftar menggunakan DI. Instans terlingkup dibuat per instans sirkuit. TrackingCircuitHandler
Menggunakan dalam contoh sebelumnya, layanan singleton dibuat karena status semua sirkuit harus dilacak.
Dalam file Program
:
builder.Services.AddSingleton<CircuitHandler, TrackingCircuitHandler>();
Dalam Startup.ConfigureServices
dari Startup.cs
:
services.AddSingleton<CircuitHandler, TrackingCircuitHandler>();
Jika metode handler sirkuit kustom melemparkan pengecualian yang tidak tertangani, pengecualiannya fatal bagi sirkuit. Untuk mentolerir pengecualian dalam kode handler atau metode yang disebut, bungkus kode dalam satu atau beberapa try-catch
pernyataan dengan penanganan kesalahan dan pengelogan.
Ketika sirkuit berakhir karena pengguna telah terputus dan kerangka kerja membersihkan status sirkuit, kerangka kerja membuang cakupan DI sirkuit. Membuang cakupan membuang layanan DI cakupan sirkuit apa pun yang menerapkan System.IDisposable. Jika ada layanan DI yang melemparkan pengecualian yang tidak tertangani selama pembuangan, kerangka kerja mencatat pengecualian. Untuk informasi selengkapnya, lihat Injeksi dependensi ASP.NET Core Blazor.
Penanganan sirkuit sisi server untuk menangkap pengguna untuk layanan kustom
CircuitHandler Gunakan untuk mengambil pengguna dari dan mengatur pengguna tersebut AuthenticationStateProvider dalam layanan. Untuk informasi selengkapnya dan contoh kode, lihat Skenario keamanan tambahan sisi server ASP.NET CoreBlazor.
Penutupan sirkuit ketika tidak ada komponen Server Interaktif yang tersisa
Komponen Server Interaktif menangani peristiwa UI web menggunakan koneksi real-time dengan browser yang disebut sirkuit. Sirkuit dan status terkait dibuat ketika komponen Server Interaktif akar dirender. Sirkuit ditutup ketika tidak ada komponen Server Interaktif yang tersisa di halaman, yang membebaskan sumber daya server.
IHttpContextAccessor
/HttpContext
dalam Razor komponen
IHttpContextAccessor harus dihindari dengan penyajian interaktif karena tidak tersedia yang valid HttpContext
.
IHttpContextAccessor dapat digunakan untuk komponen yang dirender secara statis di server. Namun, sebaiknya hindari jika memungkinkan.
HttpContext dapat digunakan sebagai parameter kaskading hanya dalam komponen akar yang dirender secara statis untuk tugas umum, seperti memeriksa dan memodifikasi header atau properti lain dalam App
komponen (Components/App.razor
). Nilainya selalu null
untuk penyajian interaktif.
[CascadingParameter]
public HttpContext? HttpContext { get; set; }
Untuk skenario di mana HttpContext diperlukan dalam komponen interaktif, sebaiknya mengalirkan data melalui status komponen persisten dari server. Untuk informasi selengkapnya, lihat Skenario keamanan tambahan ASP.NET Core Blazor sisi server.
Jangan gunakan IHttpContextAccessor/HttpContext secara langsung atau tidak langsung dalam Razor komponen aplikasi sisi Blazor server. Blazor aplikasi berjalan di luar konteks alur ASP.NET Core. HttpContext tidak dijamin tersedia dalam IHttpContextAccessor, dan HttpContext tidak dijamin untuk menyimpan konteks yang memulai Blazor aplikasi.
Pendekatan yang direkomendasikan untuk meneruskan status permintaan ke Blazor aplikasi adalah melalui parameter komponen akar selama penyajian awal aplikasi. Atau, aplikasi dapat menyalin data ke dalam layanan tercakup dalam peristiwa siklus hidup inisialisasi komponen akar untuk digunakan di seluruh aplikasi. Untuk informasi selengkapnya, lihat Skenario keamanan tambahan ASP.NET Core Blazor sisi server.
Aspek penting dari keamanan sisi Blazor server adalah bahwa pengguna yang melekat pada sirkuit tertentu mungkin diperbarui pada beberapa titik setelah Blazor sirkuit dibuat tetapi IHttpContextAccessortidak diperbarui. Untuk informasi selengkapnya tentang mengatasi situasi ini dengan layanan kustom, lihat Skenario keamanan tambahan ASP.NET Core Blazor sisi server.
Sumber daya sisi server tambahan
- Panduan penyebaran dan host sisi server: SignalR konfigurasi
- Gambaran umum ASP.NET Core SignalR
- Konfigurasi ASP.NET Core SignalR
- Dokumentasi keamanan sisi server
- Peristiwa koneksi ulang sisi server dan peristiwa siklus hidup komponen
- Apa itu Azure SignalR Service?
- Panduan performa untuk Layanan Azure SignalR
- Menerbitkan aplikasi ASP.NET Core SignalR ke Azure App Service
- Blazorsampel repositori GitHub () (
dotnet/blazor-samples
cara mengunduh)
ASP.NET Core