首页 > 解决方案 > 带有实体框架的 Blazor 大量性能问题

问题描述

我正在使用 Radzen 控件和代码优先实体框架构建 Blazor 应用程序。我有客户,他们的订单有 OrderLines。在我的页面上,我想显示三个网格;

网格 1 显示客户。

网格 2 显示了客户的订单。

网格 3 显示所选订单的行项目。

客户和订单一切顺利,我的两个网格完美运行。当我添加 OrderLines 时出现问题。然后它似乎挂起,当我通过 Visual Studio 运行它并在它“挂起”时暂停时,代码位于 Program.cs 的 CreateHostBuilder(args).Build().Run();

这是我的三个对象类(为简洁起见)

public class Customer
{
    [Required, Key, DatabaseGenerated(DatabaseGeneratedOption.None)]
    public Int32 invoice_account { get; set; }
    public List<Order> Orders { get; set; }
}

public class Order
{
    [Required, Key, DatabaseGenerated(DatabaseGeneratedOption.None)]
    public Int32 int_order_ref { get; set; }
    public Int32 invoice_account { get; set; }
    
    public List<OrderLine> OrderLines { get; set; }
    public Customer Customer { get; set; }
}

    public class OrderLine
{
    [Key]
    public Int32 id { get; set; }
    public Int32? line_no { get; set; }
    public string product_code { get; set; }

    public Order Order { get; set; }

}

从 ApplicationDbContext.cs 中提取;

    public class ApplicationDbContext : IdentityDbContext
    {
        public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options)
            : base(options)
        {
        }
        public DbSet<Customer> Customers { get; set; }
        public DbSet<Order> Orders { get; set; }
        public DbSet<OrderLine> OrderLines { get; set; }
    }

    protected override void OnModelCreating(ModelBuilder builder)
    {
        base.OnModelCreating(builder);

        builder.Entity<Order>()
            .HasOne(o => o.Customer)
            .WithMany(c => c.Orders)
            .HasForeignKey(o => o.invoice_account)
            .HasPrincipalKey(c => c.invoice_account);

        builder.Entity<OrderLine>()
            .HasOne(o => o.Order)
            .WithMany(ol => ol.OrderLines)
            .HasForeignKey(o => o.int_order_ref)
            .HasPrincipalKey(o => o.int_order_ref);
    }

从我的服务 CustomerServiceList.cs 中提取

public interface ICustomerListService
{
    Task<List<Customer>> Get();
}
public class CustomerListService : ICustomerListService
{
    private readonly ApplicationDbContext _context;

    public CustomerListService(ApplicationDbContext context)
    {
        _context = context;
    }

    public async Task<List<Customer>> Get()
    {
        // added in the where clause to try to get back just one record;
        return await _context.Customers.Where(c => c.invoice_account == 1320).ToListAsync();
    }
}

最后是我的页面;

@page "/customerorders"

@using BlazorApp.Data
@using Microsoft.EntityFrameworkCore

@inject ApplicationDbContext dbContext
@inject BlazorApp.Services.CustomerListService service

<h3>Customer Orders</h3>

@if (customers == null && order == null)
{
<p><em>Loading...</em></p>
}
else
{
<div class="row">
    <div class="col-md-4">
        <RadzenGrid ColumnWidth="400px" AllowFiltering="true" AllowPaging="true" PageSize="20" 
            AllowSorting="true" Data="@customers" TItem="Customer" Value="@customer" RowSelect="@(args => customer = args)">
            <Columns>
                <RadzenGridColumn Width="100px" TItem="Customer" Property="invoice_account" Title="Account No" />
                <RadzenGridColumn Width="300px" TItem="Customer" Property="account_name" Title="Customer" />
            </Columns>
        </RadzenGrid>
    </div>
    <div class="col-md-6">
        <RadzenCard Style="margin-bottom:20px">
            Company:
            <b>@customer.account_name</b>
        </RadzenCard>
        <RadzenTabs>
        <Tabs>
            <RadzenTabsItem Text="Order Details">
                <RadzenGrid AllowFiltering="true" AllowPaging="true" PageSize="8" AllowSorting="true" Data="@customer.Orders" TItem="Order" FilterCaseSensitivity="FilterCaseSensitivity.CaseInsensitive">
                    <Columns>
                        <RadzenGridColumn TItem="Order" Property="int_order_ref" Title="Order No" />
                        <RadzenGridColumn TItem="Order" Property="when_placed" Title="Placed On">
                            <Template Context="ord">
                                @String.Format("{0:dd'-'MMM'-'yy}", ord.when_placed)
                            </Template>
                        </RadzenGridColumn>
                        <RadzenGridColumn TItem="Order" Property="town" Title="Town" />
                        <RadzenGridColumn TItem="Order" Property="placed_by" Title="Placed By" />

                    </Columns>
                </RadzenGrid>
            </RadzenTabsItem>
        </Tabs>
    </RadzenTabs>
</div>
<div class="col-md-6">
    <RadzenGrid AllowFiltering="true" AllowPaging="true" PageSize="5" AllowSorting="true"Data="@order.OrderLines" TItem="OrderLine"  FilterCaseSensitivity="FilterCaseSensitivity.CaseInsensitive">
            <RadzenGridColumn TItem="OrderLine" Property="product_code" Title="Product Code"></RadzenGridColumn>
        </RadzenGrid>
    </div>
</div>
}

@code {

    Customer customer;
    List<Customer> customers;
    Order order;

    protected override async Task OnInitializedAsync()
    {
    
        customers = await service.Get();
    
        customer = customers.FirstOrDefault();

    }
}

在我的客户表中,只有 10k 多行。在我的 Orders 表中,大约有 120k 行。我还没有填充 OrderLines 表,这让我相信这是我的代码中的某些东西,而不是导致问题的数据量。

更新 我使用 NavMenu 链接到我的 CustomerOrders 页面,但它什么也没做,这让我相信它挂了。但是,当我直接使用 URL 时,我实际上看到了一个错误;

An unhandled exception occurred while processing the request.
InvalidOperationException: Cannot provide a value for property 'service' on type 'BlazorApp.Pages.CustomerOrders'. There is no registered service of type 'BlazorApp.Services.CustomerListService'.
Microsoft.AspNetCore.Components.ComponentFactory+<>c__DisplayClass5_0.<CreateInitializer>g__Initialize|2(IServiceProvider serviceProvider, IComponent component)

但是,我已经在 Startup.cs 中注册了该服务;

public void ConfigureServices(IServiceCollection services)
{
    services.AddTransient<ICustomerListService, CustomerListService>();
}

更新 2 使用 Navlink 选项,当我单击链接时没有任何反应。直到我刷新页面才显示错误。这不可能吧?

标签: c#entity-framework-coreblazor

解决方案


像往常一样,答案是 PICNIC 错误。我没有将 ICustomerListService 注入我的页面,而是注入了 CustomerListService。关闭,但没有雪茄。为浪费您的时间向所有人道歉。


推荐阅读