składnik ASP.NET Core BlazorQuickGrid
Uwaga
Nie jest to najnowsza wersja tego artykułu. Aby zapoznać się z bieżącą wersją, zobacz wersję tego artykułu dla platformy .NET 9.
Ważne
Te informacje odnoszą się do produktu w wersji wstępnej, który może zostać znacząco zmodyfikowany, zanim zostanie wydany komercyjnie. Firma Microsoft nie udziela żadnych gwarancji, jawnych lub domniemanych, w odniesieniu do informacji podanych w tym miejscu.
Aby zapoznać się z bieżącą wersją, zobacz wersję tego artykułu .NET 9.
Składnik QuickGrid
jest składnikiem Razor umożliwiającym szybkie i wydajne wyświetlanie danych w formie tabelarycznej.
QuickGrid Udostępnia prosty i wygodny składnik siatki danych dla typowych scenariuszy renderowania siatki i służy jako architektura referencyjna i punkt odniesienia wydajności dla składników siatki danych.
QuickGrid jest wysoce zoptymalizowany i wykorzystuje zaawansowane techniki w celu uzyskania optymalnej wydajności renderowania.
Pakiet
Dodaj odwołanie do pakietu Microsoft.AspNetCore.Components.QuickGrid
.
Uwaga
Aby uzyskać instrukcje dodawania pakietów do aplikacji .NET, zobacz artykuły w sekcji Instalowanie pakietów i zarządzanie nimi w temacie Przepływ pracy użycia pakietów (dokumentacja programu NuGet). Sprawdź prawidłowe wersje pakietów pod adresem NuGet.org.
Przykładowa aplikacja
Aby zapoznać się z różnymi pokazami QuickGrid, zobacz QuickGrid dla przykładowej aplikacji Blazor. Witryna demonstracyjna jest hostowana w witrynie GitHub Pages. Witryna ładuje się szybko dzięki statycznemu prerenderingowi przy użyciu projektu
QuickGrid implementacja
Aby zaimplementować QuickGrid
składnik:
- Określ tagi składnika
QuickGrid
w Razor znaczniku (<QuickGrid>...</QuickGrid>
). - Nadaj siatce nazwę możliwe do utworzenia zapytania źródło danych. Użyj jednego z następujących źródeł danych:
-
Items: dopuszczana
IQueryable<TGridItem>
wartość null , gdzieTGridItem
jest typem danych reprezentowanych przez każdy wiersz w siatce. - ItemsProvider: wywołanie zwrotne, które dostarcza dane dla siatki.
-
Items: dopuszczana
-
Class: opcjonalna nazwa klasy CSS. Jeśli zostanie podana, nazwa klasy jest uwzględniona w atrybucie
class
renderowanej tabeli. -
Theme: Nazwa motywu (wartość domyślna:
default
). Ma to wpływ na to, które reguły stylu pasują do tabeli. - Virtualize: Jeśli wartość true, siatka jest renderowana przy użyciu wirtualizacji. Jest to zwykle używane w połączeniu z przewijaniem i umożliwia pobranie oraz renderowanie tylko danych wokół obszaru przewijanego widoku. Może to znacznie poprawić wydajność podczas przewijania dużych zestawów danych. Jeśli używasz Virtualize, należy podać wartość dla ItemSize i upewnić się, że każdy wiersz jest renderowany ze stałą wysokością. Ogólnie rzecz biorąc, zaleca się nie używać Virtualize , jeśli ilość renderowanych danych jest mała lub jeśli używasz stronicowania.
- ItemSize: dotyczy tylko podczas korzystania z Virtualize. ItemSize definiuje oczekiwaną wysokość w pikselach dla każdego wiersza, umożliwiając mechanizmowi wirtualizacji pobranie prawidłowej liczby elementów odpowiadających rozmiarowi wyświetlania i zapewnienie dokładnego przewijania.
-
ItemKey: Opcjonalnie definiuje wartość dla
@key
każdego renderowanego wiersza. Zazwyczaj służy do określania unikatowego identyfikatora, takiego jak wartość klucza podstawowego, dla każdego elementu danych. Dzięki temu siatka może zachować skojarzenie między elementami wierszy a elementami danych na podstawie ich unikalnych identyfikatorów, nawet jeśliTGridItem
wystąpienia są zastępowane przez nowe kopie (na przykład po nowym zapytaniu względem bazowego magazynu danych). Jeśli@key
nie jest ustawiona, to jest instancjaTGridItem
. - OverscanCount: definiuje liczbę dodatkowych elementów do renderowania przed i po widocznym regionie w celu zmniejszenia częstotliwości renderowania podczas przewijania. Chociaż wyższe wartości mogą poprawić płynność przewijania przez renderowanie większej liczby elementów poza ekranem, wyższa wartość może również spowodować wzrost początkowych czasów ładowania. Zalecane jest znalezienie równowagi na podstawie rozmiaru zestawu danych i wymagań dotyczących środowiska użytkownika. Domyślna wartość wynosi 3. Dostępne tylko w przypadku korzystania z programu Virtualize.
-
Pagination: opcjonalnie łączy to wystąpienie
TGridItem
z modelem PaginationState, poprzez co siatka pobiera i renderuje tylko bieżącą stronę danych. Jest to zwykle używane w połączeniu ze składnikiem Paginator lub inną logiką interfejsu użytkownika, która wyświetla i aktualizuje podane wystąpienie PaginationState. - W treści podrzędnej QuickGrid (RenderFragment) określ elementy PropertyColumn<TGridItem,TProp>, reprezentujące kolumny
TGridItem
, których komórki wyświetlają wartości:- Property: definiuje wartość, która ma być wyświetlana w komórkach tej kolumny.
-
Format: opcjonalnie określa ciąg formatu dla wartości. Użycie Format wymaga, aby typ
TProp
implementował IFormattable. - Sortable: wskazuje, czy dane powinny być sortowalne według tej kolumny. Wartość domyślna może się różnić w zależności od typu kolumny. Na przykład element TemplateColumn<TGridItem> jest sortowany, jeśli określono jakikolwiek SortBy parametr.
-
InitialSortDirection: wskazuje kierunek sortowania, jeśli IsDefaultSortColumn ma wartość
true
. - IsDefaultSortColumn: wskazuje, czy ta kolumna ma być sortowana domyślnie.
- PlaceholderTemplate: Jeśli określono, zwirtualizowane siatki używają tego szablonu do renderowania komórek, których dane nie zostały załadowane.
- HeaderTemplate: opcjonalny szablon komórki nagłówka tej kolumny. Jeśli nie zostanie określony, domyślny szablon nagłówka zawiera Titleelement , wraz z dowolnymi odpowiednimi wskaźnikami sortowania i przyciskami opcji.
- Title: tekst tytułu kolumny. Tytuł jest renderowany automatycznie, jeśli HeaderTemplate nie jest używany.
- Określ tagi składnika
QuickGrid
w znacznikach Razor (<QuickGrid>...</QuickGrid>
). - Nazwij źródło danych do siatki, które można poddawać zapytaniom. Użyj jednego z następujących źródeł danych:
-
Items: wartość dopuszczająca
IQueryable<TGridItem>
null, gdzieTGridItem
jest typem danych reprezentowanych przez każdy wiersz w tabeli. - ItemsProvider: wywołanie zwrotne, które dostarcza dane dla siatki.
-
Items: wartość dopuszczająca
-
Class: opcjonalna nazwa klasy CSS. Jeśli zostanie podana, nazwa klasy jest uwzględniona w atrybucie
class
renderowanej tabeli. -
Theme: Nazwa motywu (wartość domyślna:
default
). To wpływa na to, które reguły stylów pasują do tabeli. - Virtualize: Jeśli wartość jest true, siatka renderowana jest przy użyciu wirtualizacji. Zwykle jest to używane w połączeniu z przewijaniem i powoduje, że siatka pobiera i renderuje tylko te dane, które znajdują się wokół aktualnego widocznego obszaru przewijania. Może to znacznie poprawić wydajność podczas przewijania dużych zestawów danych. Jeśli używasz Virtualize, należy podać wartość ItemSize i upewnić się, że każdy wiersz jest renderowany ze stałą wysokością. Ogólnie rzecz biorąc, zaleca się nie używać Virtualize , jeśli ilość renderowanych danych jest mała lub jeśli używasz stronicowania.
- ItemSize: dotyczy tylko podczas korzystania z Virtualize. ItemSize definiuje oczekiwaną wysokość w pikselach dla każdego wiersza, umożliwiając mechanizmowi wirtualizacji pobranie prawidłowej liczby elementów odpowiadających rozmiarowi wyświetlania i zapewnienie dokładnego przewijania.
-
ItemKey: Opcjonalnie definiuje wartość dla
@key
każdego renderowanego wiersza. Zazwyczaj służy do określania unikatowego identyfikatora, takiego jak wartość klucza podstawowego, dla każdego elementu danych. Dzięki temu siatka może zachować skojarzenie między elementami wiersza i elementami danych na podstawie ich unikatowych identyfikatorów, nawet jeśliTGridItem
wystąpienia są zastępowane przez nowe kopie (na przykład po nowym zapytaniu względem bazowego magazynu danych). Jeśli nie zostanie ustawiony,@key
to instancjaTGridItem
. -
Pagination: opcjonalnie łączy to
TGridItem
wystąpienie z modelem PaginationState , co powoduje pobranie siatki i renderowanie tylko bieżącej strony danych. Jest to zwykle używane w połączeniu ze składnikiem Paginator lub inną logiką interfejsu użytkownika, która wyświetla i aktualizuje podany egzemplarz PaginationState. - W zawartości podrzędnej QuickGrid (RenderFragment), określ PropertyColumn<TGridItem,TProp>, które reprezentują kolumny
TGridItem
, gdzie komórki wyświetlają wartości:- Property: definiuje wartość, która ma być wyświetlana w komórkach tej kolumny.
-
Format: opcjonalnie określa ciąg formatu dla wartości. Użycie Format wymaga, aby typ
TProp
zaimplementował IFormattable. - Sortable: wskazuje, czy dane powinny być sortowalne według tej kolumny. Wartość domyślna może się różnić w zależności od typu kolumny. Na przykład element TemplateColumn<TGridItem> jest sortowany, jeśli określono jakikolwiek SortBy parametr.
-
InitialSortDirection: wskazuje kierunek sortowania, jeśli IsDefaultSortColumn ma wartość
true
. - IsDefaultSortColumn: wskazuje, czy ta kolumna ma być sortowana domyślnie.
- PlaceholderTemplate: Jeśli określono, zwirtualizowane siatki używają tego szablonu do renderowania komórek, których dane nie zostały załadowane.
- HeaderTemplate: opcjonalny szablon komórki nagłówka tej kolumny. Jeśli nie zostanie określony, domyślny szablon nagłówka zawiera element Title, wraz z wszelkimi odpowiednimi wskaźnikami sortowania i przyciskami opcji.
- Title: tekst tytułu kolumny. Tytuł jest renderowany automatycznie, jeśli HeaderTemplate nie jest używany.
Dodaj na przykład następujący składnik, aby renderować siatkę.
W przypadku
PromotionGrid.razor
:
@page "/promotion-grid"
@using Microsoft.AspNetCore.Components.QuickGrid
<PageTitle>Promotion Grid</PageTitle>
<h1>Promotion Grid Example</h1>
<QuickGrid Items="people">
<PropertyColumn Property="@(p => p.PersonId)" Sortable="true" />
<PropertyColumn Property="@(p => p.Name)" Sortable="true" />
<PropertyColumn Property="@(p => p.PromotionDate)" Format="yyyy-MM-dd" Sortable="true" />
</QuickGrid>
@code {
private record Person(int PersonId, string Name, DateOnly PromotionDate);
private IQueryable<Person> people = new[]
{
new Person(10895, "Jean Martin", new DateOnly(1985, 3, 16)),
new Person(10944, "António Langa", new DateOnly(1991, 12, 1)),
new Person(11203, "Julie Smith", new DateOnly(1958, 10, 10)),
new Person(11205, "Nur Sari", new DateOnly(1922, 4, 27)),
new Person(11898, "Jose Hernandez", new DateOnly(2011, 5, 3)),
new Person(12130, "Kenji Sato", new DateOnly(2004, 1, 9)),
}.AsQueryable();
}
@page "/promotion-grid"
@using Microsoft.AspNetCore.Components.QuickGrid
<PageTitle>Promotion Grid</PageTitle>
<h1>Promotion Grid Example</h1>
<QuickGrid Items="people">
<PropertyColumn Property="@(p => p.PersonId)" Sortable="true" />
<PropertyColumn Property="@(p => p.Name)" Sortable="true" />
<PropertyColumn Property="@(p => p.PromotionDate)" Format="yyyy-MM-dd" Sortable="true" />
</QuickGrid>
@code {
private record Person(int PersonId, string Name, DateOnly PromotionDate);
private IQueryable<Person> people = new[]
{
new Person(10895, "Jean Martin", new DateOnly(1985, 3, 16)),
new Person(10944, "António Langa", new DateOnly(1991, 12, 1)),
new Person(11203, "Julie Smith", new DateOnly(1958, 10, 10)),
new Person(11205, "Nur Sari", new DateOnly(1922, 4, 27)),
new Person(11898, "Jose Hernandez", new DateOnly(2011, 5, 3)),
new Person(12130, "Kenji Sato", new DateOnly(2004, 1, 9)),
}.AsQueryable();
}
Uzyskaj dostęp do składnika w przeglądarce w ścieżce względnej /promotion-grid
.
Nie ma bieżących planów rozszerzenia QuickGrid o funkcje, jakie oferują pełnowymiarowe komercyjne siatki, na przykład wiersze hierarchiczne, przeciąganie kolumn w celu zmiany ich kolejności lub wybór zakresu przypominającego program Excel. Jeśli potrzebujesz zaawansowanych funkcji, których nie chcesz tworzyć samodzielnie, kontynuuj korzystanie z sieci innych firm.
Sortuj według kolumny
Składnik QuickGrid
może sortować elementy według kolumn. W Blazor Web App sortowanie wymaga, aby składnik przyjął tryb renderowania interaktywnego.
Dodaj Sortable="true"
(Sortable) do tagu PropertyColumn<TGridItem,TProp> :
<PropertyColumn Property="..." Sortable="true" />
W uruchomionej aplikacji posortuj kolumnę QuickGrid , wybierając tytuł renderowanej kolumny.
Elementy strony ze składnikiem Paginator
Składnik QuickGrid
może stronicować dane ze źródła danych. W Blazor Web App wymaga się, aby przy stronicowaniu składnik przyjął tryb renderowania interakcyjnego.
PaginationState Dodaj wystąpienie do bloku składnika@code
.
ItemsPerPage Ustaw wartość na liczbę elementów do wyświetlenia na stronę. W poniższym przykładzie wystąpienie ma nazwę pagination
, a ustawiono dziesięć elementów na stronę.
PaginationState pagination = new PaginationState { ItemsPerPage = 10 };
QuickGrid
Ustaw właściwość składnika Pagination na :pagination
<QuickGrid Items="..." Pagination="pagination">
Aby udostępnić interfejs użytkownika na potrzeby stronicowania, dodaj Paginator
składnik powyżej lub poniżej QuickGrid
składnika. Ustaw Paginator.State na pagination
.
<Paginator State="pagination" />
W uruchomionej aplikacji przejdź do strony elementów przy użyciu renderowanego Paginator
składnika.
QuickGrid renderuje dodatkowe puste wiersze, aby wypełnić ostatnią stronę danych w przypadku użycia ze składnikiem Paginator
. W programie .NET 9 lub nowszym puste komórki danych (<td></td>
) są dodawane do pustych wierszy. Puste wiersze służą ułatwieniu renderowania QuickGrid z zachowaniem stabilnej wysokości wierszy i stylizacji na wszystkich stronach.
Zastosuj style wierszy
Stosowanie stylów do wierszy z wykorzystaniem izolacji CSS, co może obejmować stylizowanie pustych wierszy dla składników QuickGrid
, które stronicują dane za pomocą składnika Paginator
.
Zawij komponent QuickGrid
w elemencie blokowym, na przykład jako <div>
.
+ <div>
<QuickGrid ...>
...
</QuickGrid>
+ </div>
Zastosuj styl wiersza przy użyciu ::deep
pseudo-elementu. W poniższym przykładzie wysokość wiersza jest ustawiona na 2em
, w tym dla pustych wierszy danych.
{COMPONENT}.razor.css
:
::deep tr {
height: 2em;
}
Alternatywnie należy użyć następującego podejścia do stylów CSS:
- Wyświetl komórki wierszy wypełnione danymi.
- Nie wyświetlaj pustych komórek w wierszach, aby uniknąć renderowania obramowań tych komórek, co wynika ze stylizacji Bootstrap.
{COMPONENT}.razor.css
:
::deep tr:has(> td:not(:empty)) > td {
display: table-cell;
}
::deep td:empty {
display: none;
}
Aby uzyskać więcej informacji na temat używania pseudoelementów ::deep
z izolacją CSS, zobacz ASP.NET Core Blazor CSS izolacja.
Atrybuty niestandardowe i style
QuickGrid obsługuje również przekazywanie atrybutów niestandardowych i klas stylów (Class) do renderowanego elementu tabeli:
<QuickGrid Items="..." custom-attribute="value" Class="custom-class">
Sformatuj wiersz tabeli na podstawie elementu wiersza
Zastosuj klasę arkusza stylów do wiersza siatki na podstawie elementu wiersza przy użyciu parametru RowClass
.
W poniższym przykładzie:
- Element wiersza jest reprezentowany przez rekord
Person
. RekordPerson
zawiera właściwośćFirstName
. - Metoda
GetRowCssClass
stosuje style klasyhighlight-row
do dowolnego wiersza, w którym imię osoby to "Julie
".
<QuickGrid ... RowClass="GetRowCssClass">
...
</QuickGrid>
@code {
private record Person(int PersonId, string FirstName, string LastName);
private string GetRowCssClass(Person person) =>
person.FirstName == "Julie" ? "highlight-row" : null;
}
Źródło danych programu Entity Framework Core (EF Core)
Użyj wzorca fabryki, aby rozpoznać EF Core kontekst bazy danych, który dostarcza dane do QuickGrid
składnika. Aby uzyskać więcej informacji, dlaczego wzorzec projektowy fabryki jest zalecany, zobacz ASP.NET Core Blazor z użyciem Entity Framework Core (EF Core).
Fabrykę kontekstu bazy danych (IDbContextFactory<TContext>) wstrzykuje się do składnika za pomocą dyrektywy @inject
. Podejście fabryczne wymaga usunięcia kontekstu bazy danych, więc składnik implementuje IAsyncDisposable interfejs z dyrektywą @implements
. Dostawca elementu dla składnika QuickGrid
jest DbSet<T>
uzyskanym z utworzonego kontekstu bazy danych (CreateDbContext) fabryki wstrzykniętego kontekstu bazy danych.
QuickGrid rozpoznaje wystąpienia IQueryable dostarczone przez platformę EF i wie, jak rozwiązywać zapytania asynchronicznie pod kątem wydajności.
Dodaj odwołanie do Microsoft.AspNetCore.Components.QuickGrid.EntityFrameworkAdapter
pakietu NuGet.
Uwaga
Aby uzyskać instrukcje dodawania pakietów do aplikacji .NET, zobacz artykuły w sekcji Instalowanie pakietów i zarządzanie nimi w temacie Przepływ pracy użycia pakietów (dokumentacja programu NuGet). Sprawdź prawidłowe wersje pakietów pod adresem NuGet.org.
Wywołaj AddQuickGridEntityFrameworkAdapter kolekcję usług w pliku w Program
celu zarejestrowania implementacji obsługującej IAsyncQueryExecutor platformę EF:
builder.Services.AddQuickGridEntityFrameworkAdapter();
W poniższym przykładzie użyto ExampleTable
DbSet<TEntity> (tabeli) z AppDbContext
kontekstu bazy danych (context
) jako źródła danych dla QuickGrid
składnika:
@using Microsoft.AspNetCore.Components.QuickGrid
@using Microsoft.EntityFrameworkCore
@implements IAsyncDisposable
@inject IDbContextFactory<AppDbContext> DbFactory
...
<QuickGrid ... Items="context.ExampleTable" ...>
...
</QuickGrid>
@code {
private AppDbContext context = default!;
protected override void OnInitialized()
{
context = DbFactory.CreateDbContext();
}
public async ValueTask DisposeAsync() => await context.DisposeAsync();
}
W bloku kodu (@code
) poprzedniego przykładu:
- Pole
context
zawiera kontekst bazy danych, wpisany jakoAppDbContext
. - Metoda
OnInitialized
cyklu życia przypisuje nowy kontekst bazy danych (CreateDbContext) do polacontext
pochodzącego z wstrzykniętej fabryki (DbFactory
). - Metoda asynchroniczna
DisposeAsync
usuwa kontekst bazy danych po usunięciu składnika.
Możesz również użyć dowolnego operatora LINQ obsługiwanego przez platformę EF do filtrowania danych przed przekazaniem ich do parametru Items .
Poniższy przykład filtruje filmy według tytułu filmu wprowadzonego w polu wyszukiwania. Kontekst bazy danych to BlazorWebAppMoviesContext
, a model jest Movie
. Właściwość filmu Title
jest używana do operacji filtrowania.
@using Microsoft.AspNetCore.Components.QuickGrid
@using Microsoft.EntityFrameworkCore
@implements IAsyncDisposable
@inject IDbContextFactory<BlazorWebAppMoviesContext> DbFactory
...
<p>
<input type="search" @bind="titleFilter" @bind:event="oninput" />
</p>
<QuickGrid ... Items="FilteredMovies" ...>
...
</QuickGrid>
@code {
private string titleFilter = string.Empty;
private BlazorWebAppMoviesContext context = default!;
protected override void OnInitialized()
{
context = DbFactory.CreateDbContext();
}
private IQueryable<Movie> FilteredMovies =>
context.Movie.Where(m => m.Title!.Contains(titleFilter));
public async ValueTask DisposeAsync() => await context.DisposeAsync();
}
Aby zapoznać się z działającym przykładem, zobacz następujące zasoby:
- Samouczek dotyczący tworzenia Blazor aplikacji bazy danych filmów
-
Blazor przykładowa aplikacja bazy danych filmów: wybierz folder najnowszej wersji w repozytorium. Przykładowy folder projektu samouczka nosi nazwę
BlazorWebAppMovies
.
Obsługa nazw wyświetlanych
Tytuł kolumny można przypisać przy użyciu ColumnBase<TGridItem>.Title w tagu PropertyColumn<TGridItem,TProp>. W poniższym przykładzie filmu kolumna dla danych daty premiery filmu ma nazwę "Release Date
".
<PropertyColumn Property="movie => movie.ReleaseDate" Title="Release Date" />
Jednak zarządzanie tytułami kolumn (nazwami) z powiązanych właściwości modelu jest zwykle lepszym wyborem do obsługi aplikacji. Model może kontrolować nazwę wyświetlaną właściwości za pomocą atrybutu [Display]
. W poniższym przykładzie model określa nazwę wyświetlaną daty wydania filmu "Release Date
" dla jego właściwości ReleaseDate
.
[Display(Name = "Release Date")]
public DateTime ReleaseDate { get; set; }
Aby umożliwić składnikowi QuickGrid
użycie właściwości DisplayAttribute.Name, utwórz podklasę PropertyColumn<TGridItem,TProp>, albo w składniku, albo w oddzielnej klasie. Wywołaj metodę GetName, aby zwrócić zlokalizowaną wartość DisplayAttribute.Name, jeśli nielokalizowany DisplayName ([DisplayName]
atrybut) nie zawiera wartości:
public class DisplayNameColumn<TGridItem, TProp> : PropertyColumn<TGridItem, TProp>
{
protected override void OnParametersSet()
{
if (Title is null && Property.Body is MemberExpression memberExpression)
{
var memberInfo = memberExpression.Member;
Title =
memberInfo.GetCustomAttribute<DisplayNameAttribute>().DisplayName ??
memberInfo.GetCustomAttribute<DisplayAttribute>().GetName() ??
memberInfo.Name;
}
base.OnParametersSet();
}
}
Użyj podklasy w składniku QuickGrid
. W poniższym przykładzie użyto poprzedzającego DisplayNameColumn
. Nazwa "Release Date
" jest dostarczana przez [Display]
atrybut w modelu, więc nie ma potrzeby określania elementu Title:
<DisplayNameColumn Property="movie => movie.ReleaseDate" />
Atrybut [DisplayName]
jest również obsługiwany:
[DisplayName("Release Date")]
public DateTime ReleaseDate { get; set; }
Jednak atrybut [Display]
jest zalecany, ponieważ udostępnia dodatkowe właściwości. Na przykład [Display]
atrybut oferuje możliwość przypisania typu zasobu do lokalizacji.
Dane zdalne
W Blazor WebAssembly aplikacjach pobieranie danych z internetowego interfejsu API opartego na formacie JSON na serwerze jest typowym wymaganiem. Aby pobrać tylko dane wymagane dla bieżącej strony/widoku danych i zastosować sortowanie lub filtrowanie na poziomie serwera, użyj parametru ItemsProvider.
ItemsProvider można również użyć w aplikacji po stronie Blazor serwera, jeśli aplikacja jest wymagana do wykonywania zapytań dotyczących zewnętrznego punktu końcowego lub w innych przypadkach, w których wymagania nie są objęte programem IQueryable.
Podaj wywołanie zwrotne zgodne z typem delegata GridItemsProvider<TGridItem>, gdzie TGridItem
jest typem danych wyświetlanych w tabeli. Wywołanie zwrotne otrzymuje parametr typu GridItemsProviderRequest<TGridItem>, który wskazuje na indeks początkowy, maksymalną liczbę wierszy oraz kolejność sortowania danych do zwrócenia. Oprócz zwracania pasujących elementów całkowita liczba elementów (totalItemCount
) jest również wymagana do poprawnego działania stronicowania i wirtualizacji.
Poniższy przykład pobiera dane z publicznej bazy OpenFDA Food Enforcement.
GridItemsProvider<TGridItem> konwertuje GridItemsProviderRequest<TGridItem> na zapytanie do bazy danych OpenFDA. Parametry zapytania są tłumaczone na określony format adresu URL obsługiwany przez zewnętrzny interfejs API JSON. Sortowanie i filtrowanie można wykonywać tylko za pomocą sortowania i filtrowania obsługiwanego przez zewnętrzny interfejs API. Punkt końcowy OpenFDA nie obsługuje sortowania, więc żadna z kolumn nie jest oznaczona jako sortowalna. Jednak obsługuje pomijanie rekordów (skip
parametru) i ograniczanie zwracania rekordów (limit
parametru), więc składnik może włączyć wirtualizację i szybko przewijać dziesiątki tysięcy rekordów.
FoodRecalls.razor
:
@page "/food-recalls"
@inject HttpClient Http
@inject NavigationManager Navigation
<PageTitle>Food Recalls</PageTitle>
<h1>OpenFDA Food Recalls</h1>
<div class="grid" tabindex="-1">
<QuickGrid ItemsProvider="@foodRecallProvider" Virtualize="true">
<PropertyColumn Title="ID" Property="@(c => c.Event_Id)" />
<PropertyColumn Property="@(c => c.State)" />
<PropertyColumn Property="@(c => c.City)" />
<PropertyColumn Title="Company" Property="@(c => c.Recalling_Firm)" />
<PropertyColumn Property="@(c => c.Status)" />
</QuickGrid>
</div>
<p>Total: <strong>@numResults results found</strong></p>
@code {
private GridItemsProvider<FoodRecall>? foodRecallProvider;
private int numResults;
protected override async Task OnInitializedAsync()
{
foodRecallProvider = async req =>
{
var url = Navigation.GetUriWithQueryParameters(
"https://api.fda.gov/food/enforcement.json",
new Dictionary<string, object?>
{
{ "skip", req.StartIndex },
{ "limit", req.Count },
});
var response = await Http.GetFromJsonAsync<FoodRecallQueryResult>(
url, req.CancellationToken);
return GridItemsProviderResult.From(
items: response!.Results,
totalItemCount: response!.Meta.Results.Total);
};
numResults = (await Http.GetFromJsonAsync<FoodRecallQueryResult>(
"https://api.fda.gov/food/enforcement.json"))!.Meta.Results.Total;
}
}
Aby uzyskać więcej informacji na temat wywoływania internetowych interfejsów API, zobacz Wywołanie interfejsu API z aplikacji ASP.NET CoreBlazor.
QuickGrid rusztowanie
Narzędzie QuickGrid jest używane do tworzenia szkieletów komponentów Razor za pomocą QuickGrid w celu wyświetlania danych z bazy danych.
Szkielet generuje podstawowe strony tworzenia, odczytu, aktualizacji i usuwania (CRUD) na podstawie modelu danych platformy Entity Framework Core. Można szkieletować poszczególne strony lub wszystkie strony CRUD. Wybierasz klasę modelu i DbContext
, opcjonalnie tworząc nowy DbContext
, jeśli to konieczne.
Składniki szkieletowe Razor są dodawane do projektu w wygenerowanym folderze o nazwie po klasie modelu. Wygenerowany Index
składnik używa QuickGrid
składnika do wyświetlania danych. Dostosuj wygenerowane składniki zgodnie z potrzebami i włącz interakcyjność, aby korzystać z interaktywnych funkcji, takich jak stronicowanie, sortowanie i filtrowanie .
Komponenty produkowane przez system rusztowań wymagają renderowania po stronie serwera (SSR), dlatego nie są obsługiwane na WebAssembly.
Kliknij prawym przyciskiem myszy na Components/Pages
folder i wybierz Dodaj>Nowy element szkieletowy.
Po otwarciu okna dialogowego
CRUD to skrót od tworzenia, odczytu, aktualizacji i usuwania. Szkieletor aplikacji tworzy komponenty do tworzenia, edytowania, usuwania, wyświetlania detali i indeksowania.
Ukończ okno dialogowe Dodawanie Razor składników przy użyciu programu Entity Framework (CRUD):
- Lista rozwijana Szablon zawiera inne szablony służące do tworzenia, edytowania, usuwania, wyświetlania szczegółów oraz organizowania listy składników. Ta lista rozwijana jest przydatna, gdy trzeba utworzyć tylko określony rodzaj szkieletu składnika dla klasy modelu. Pozostaw rozwijaną listę Szablon ustawioną na CRUD, aby utworzyć szkielet pełnego zestawu komponentów.
- Z listy rozwijanej Klasa modelu wybierz klasę modelu. Folder jest tworzony dla składników wygenerowanych z modelu o nazwie (jeśli klasa modelu nosi nazwę
Movie
, folder jest automatycznie nazywanyMoviePages
). - W przypadku klasy DbContext , zastosuj jedno z następujących podejść:
- Wybierz istniejącą klasę DbContext, która ma rejestrację dostawcy fabrycznego (AddDbContextFactory).
- Wybierz przycisk + (znak plus) i użyj modalnego okna dialogowego Dodaj kontekst danych, aby podać nową nazwę klasy DbContext, która rejestruje klasę przez dostawcę fabryki zamiast bezpośredniego używania typu kontekstu jako zarejestrowanie usługi.
- Po zamknięciu okna dialogowego modelu, lista rozwijana Dostawca bazy danych jest domyślnie ustawiona na SQL Server. Możesz wybrać odpowiedniego dostawcę dla używanej bazy danych. Dostępne opcje to SQL Server, SQLite, PostgreSQL i Azure Cosmos DB.
- Wybierz Dodaj.
Aby zapoznać się z przykładowym użyciem szkieletuQuickGrid, zobacz Tworzenie Blazor aplikacji bazy danych filmów (omówienie).
Wiele współbieżnych zapytań EF Core uruchamia System.InvalidOperationException
Wiele współbieżnych zapytań EF Core może wyzwolić następujące System.InvalidOperationException:
System.InvalidOperationException: Druga operacja została uruchomiona w tym wystąpieniu kontekstu przed zakończeniem poprzedniej operacji. Jest to zwykle spowodowane przez różne wątki, które współbieżnie używają tego samego wystąpienia DbContext. Aby uzyskać więcej informacji na temat unikania problemów z wątkami w dbContext, zobacz https://go.microsoft.com/fwlink/?linkid=2097913.
Ten scenariusz jest zaplanowany na poprawę w nadchodzącej wersji ASP.NET Core. Aby uzyskać więcej informacji, zobacz [Blazor] Ulepsz doświadczenie z QuickGrid i EF Core (dotnet/aspnetcore
#58716).
W międzyczasie możesz rozwiązać problem przy użyciu ItemsProvider z tokenem anulowania. Token anulowania uniemożliwia równoczesne zapytania, anulując poprzednie żądanie po wydaniu nowego żądania.
Rozważmy poniższy przykład, który jest oparty na komponencie bazy danych filmów Index
dla Zbuduj aplikację bazy danych filmów Blazor (Omówienie) samouczka. Wersję uproszczoną zintegrowaną w przykładowej aplikacji można zobaczyć w artykule . Składnik Index
osadzony w aplikacji jest zastępowany przez następujący element.
Components/Pages/MoviePages/Index.razor
:
@page "/movies"
@rendermode InteractiveServer
@using Microsoft.EntityFrameworkCore
@using Microsoft.AspNetCore.Components.QuickGrid
@using BlazorWebAppMovies.Models
@using BlazorWebAppMovies.Data
@inject IDbContextFactory<BlazorWebAppMovies.Data.BlazorWebAppMoviesContext> DbFactory
<PageTitle>Index</PageTitle>
<h1>Index</h1>
<div>
<input type="search" @bind="titleFilter" @bind:event="oninput" />
</div>
<p>
<a href="movies/create">Create New</a>
</p>
<div>
<QuickGrid Class="table" TGridItem="Movie" ItemsProvider="GetMovies"
ItemKey="(x => x.Id)" Pagination="pagination">
<PropertyColumn Property="movie => movie.Title" Sortable="true" />
<PropertyColumn Property="movie => movie.ReleaseDate" Title="Release Date" />
<PropertyColumn Property="movie => movie.Genre" />
<PropertyColumn Property="movie => movie.Price" />
<PropertyColumn Property="movie => movie.Rating" />
<TemplateColumn Context="movie">
<a href="@($"movies/edit?id={movie.Id}")">Edit</a> |
<a href="@($"movies/details?id={movie.Id}")">Details</a> |
<a href="@($"movies/delete?id={movie.Id}")">Delete</a>
</TemplateColumn>
</QuickGrid>
</div>
<Paginator State="pagination" />
@code {
private BlazorWebAppMoviesContext context = default!;
private PaginationState pagination = new PaginationState { ItemsPerPage = 5 };
private string titleFilter = string.Empty;
public async ValueTask<GridItemsProviderResult<Movie>> GetMovies(GridItemsProviderRequest<Movie> request)
{
using var context = DbFactory.CreateDbContext();
var totalCount = await context.Movie.CountAsync(request.CancellationToken);
IQueryable<Movie> query = context.Movie.OrderBy(x => x.Id);
query = request.ApplySorting(query).Skip(request.StartIndex);
if (request.Count.HasValue)
{
query = query.Take(request.Count.Value);
}
var items = await query.ToArrayAsync(request.CancellationToken);
var result = new GridItemsProviderResult<Movie>
{
Items = items,
TotalItemCount = totalCount
};
return result;
}
}