MudBlazor Autocomplete自定义对象加载时触发NullReferenceException问题
问题描述
使用MudBlazor的Autocomplete组件实现自定义对象(MailboxUser)的下拉选择功能,功能运行符合预期,但首次加载时,列表中的每个对象都会触发一次System.NullReferenceException错误,之后组件可正常工作。需明确:
- 遗漏了哪些配置?
- 首次加载时为何会出现user对象为空的情况?
- 是否存在该组件的其他配置方式?
代码示例
<MudGrid> <MudItem xs="12" sm="6" md="4"> <MudAutocomplete T="MailboxUser" Label="Select Forward From Mailbox" @bind-Value="SelectedForwardFrom" SearchFunc="@SearchUsers" ToStringFunc="user => user.DisplayName" ResetValueOnEmptyText="false" /> </MudItem> </MudGrid> @code { private List<MailboxUser> ActiveForwards { get; set; } private List<MailboxUser> AllUsers { get; set; } private MailboxUser SelectedForwardFrom { get; set; } private MailboxUser SelectedForwardTo { get; set; } private bool SendToBoth { get; set; } private IOrderedEnumerable<MailboxUser> SortedUsers { get; set; } private string SelectedForwardFromString { get; set; } protected override async Task OnInitializedAsync() { AllUsers = await PowerRun.GetAllUsersAsync(); if (AllUsers != null) { SortedUsers = AllUsers.OrderBy(x => x.DisplayName); } ActiveForwards = await PowerRun.GetActiveForwardsAsync(); } private async Task<IEnumerable<MailboxUser>> SearchUsers(string value) { // if text is null or empty, show complete list if (string.IsNullOrEmpty(value)) { return SortedUsers; } return SortedUsers.Where(x => x.DisplayName.Contains(value, StringComparison.InvariantCultureIgnoreCase)); } }
问题原因与解决方案
问题原因
- 异步加载导致的空引用:
OnInitializedAsync是异步执行的,组件首次渲染时SortedUsers仍为默认的null值。此时Autocomplete组件会调用SearchUsers方法,返回null集合,组件尝试遍历该集合时触发空引用错误。 - ToStringFunc未处理空值:
ToStringFunc="user => user.DisplayName"未对传入的user做空值判断,若组件在数据未就绪时传入null(比如初始选中值SelectedForwardFrom为null时),会直接触发空引用。
解决方案
方案1:初始化SortedUsers为空集合
在声明SortedUsers时直接初始化为空集合,避免返回null:
private IOrderedEnumerable<MailboxUser> SortedUsers = Enumerable.Empty<MailboxUser>();
这样即使数据未加载完成,SearchUsers返回的是空集合而非null,组件不会触发空引用。
方案2:给ToStringFunc添加空值保护
修改ToStringFunc,对null用户返回空字符串:
ToStringFunc="user => user?.DisplayName ?? string.Empty"
方案3:数据加载完成前禁用组件
通过Disabled属性在数据未就绪时禁用Autocomplete,避免组件提前触发逻辑:
<MudAutocomplete T="MailboxUser" Label="Select Forward From Mailbox" @bind-Value="SelectedForwardFrom" SearchFunc="@SearchUsers" ToStringFunc="user => user?.DisplayName ?? string.Empty" ResetValueOnEmptyText="false" Disabled="@(SortedUsers.Count() == 0)" />
替代配置方式:直接绑定Items属性
如果用户数据量不大,可直接使用Items属性绑定数据源,由组件内部处理搜索逻辑,简化代码:
<MudAutocomplete T="MailboxUser" Label="Select Forward From Mailbox" @bind-Value="SelectedForwardFrom" Items="@SortedUsers" ToStringFunc="user => user?.DisplayName ?? string.Empty" ResetValueOnEmptyText="false" />
此方式无需手动实现SearchFunc,组件会自动根据输入过滤Items集合。
内容的提问来源于stack exchange,提问作者Tom Gordon
相关产品推荐
相关产品推荐

