diff --git a/src/Extensions/DataGrid.EntityFrameworkAdapter/EntityFrameworkAdapterServiceCollectionExtensions.cs b/src/Extensions/DataGrid.EntityFrameworkAdapter/EntityFrameworkAdapterServiceCollectionExtensions.cs index cadf2921ef..536e832413 100644 --- a/src/Extensions/DataGrid.EntityFrameworkAdapter/EntityFrameworkAdapterServiceCollectionExtensions.cs +++ b/src/Extensions/DataGrid.EntityFrameworkAdapter/EntityFrameworkAdapterServiceCollectionExtensions.cs @@ -1,7 +1,13 @@ +// ------------------------------------------------------------------------ +// MIT License - Copyright (c) Microsoft Corporation. All rights reserved. +// ------------------------------------------------------------------------ + using Microsoft.FluentUI.AspNetCore.Components.DataGrid.EntityFrameworkAdapter; using Microsoft.FluentUI.AspNetCore.Components.DataGrid.Infrastructure; +#pragma warning disable IDE0130 // Namespace does not match folder structure namespace Microsoft.Extensions.DependencyInjection; +#pragma warning restore IDE0130 // Namespace does not match folder structure /// /// Provides extension methods to configure on a . @@ -12,8 +18,9 @@ public static class EntityFrameworkAdapterServiceCollectionExtensions /// Registers an Entity Framework aware implementation of . /// /// The . - public static void AddDataGridEntityFrameworkAdapter(this IServiceCollection services) + /// A function to determine whether to ignore exceptions. + public static void AddDataGridEntityFrameworkAdapter(this IServiceCollection services, Func? ignoreException = null) { - services.AddScoped(); + services.AddScoped(sp => new EntityFrameworkAsyncQueryExecutor(ignoreException)); } } diff --git a/src/Extensions/DataGrid.EntityFrameworkAdapter/EntityFrameworkAsyncQueryExecutor.cs b/src/Extensions/DataGrid.EntityFrameworkAdapter/EntityFrameworkAsyncQueryExecutor.cs index 614abccad4..e99ab9d97e 100644 --- a/src/Extensions/DataGrid.EntityFrameworkAdapter/EntityFrameworkAsyncQueryExecutor.cs +++ b/src/Extensions/DataGrid.EntityFrameworkAdapter/EntityFrameworkAsyncQueryExecutor.cs @@ -1,19 +1,29 @@ +// ------------------------------------------------------------------------ +// MIT License - Copyright (c) Microsoft Corporation. All rights reserved. +// ------------------------------------------------------------------------ + using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore.Query; using Microsoft.FluentUI.AspNetCore.Components.DataGrid.Infrastructure; namespace Microsoft.FluentUI.AspNetCore.Components.DataGrid.EntityFrameworkAdapter; -internal class EntityFrameworkAsyncQueryExecutor : IAsyncQueryExecutor, IDisposable +/// +/// An implementation for Entity Framework Core. +/// +internal class EntityFrameworkAsyncQueryExecutor(Func? ignoreException = null) : IAsyncQueryExecutor, IDisposable { private readonly SemaphoreSlim _lock = new(1); + /// public bool IsSupported(IQueryable queryable) => queryable.Provider is IAsyncQueryProvider; + /// public Task CountAsync(IQueryable queryable, CancellationToken cancellationToken) => ExecuteAsync(() => queryable.CountAsync(cancellationToken)); + /// public Task ToArrayAsync(IQueryable queryable, CancellationToken cancellationToken) => ExecuteAsync(() => queryable.ToArrayAsync(cancellationToken)); @@ -36,6 +46,10 @@ private async Task ExecuteAsync(Func> operation) { return default!; } + catch (Exception ex) when (ignoreException?.Invoke(ex) == true) + { + return default!; + } } void IDisposable.Dispose() => _lock.Dispose(); diff --git a/src/Extensions/DataGrid.EntityFrameworkAdapter/README.md b/src/Extensions/DataGrid.EntityFrameworkAdapter/README.md index 2cdec74d6d..fc5a732b29 100644 --- a/src/Extensions/DataGrid.EntityFrameworkAdapter/README.md +++ b/src/Extensions/DataGrid.EntityFrameworkAdapter/README.md @@ -28,13 +28,27 @@ Install the package by running the command: ``` dotnet add package Microsoft.FluentUI.AspNetCore.Components.DataGrid.EntityFrameworkAdapter ``` - ## Usage -In your Program.cs file you need to add the following: +When using the provided implementation, you need to add add the following in the `Program.cs` file: + ``` builder.Services.AddDataGridEntityFrameworkAdapter(); ``` +## Changing the adapter's behavior +Starting with v4.11.4, the `EntityFrameworkAsyncQueryExecutor` exposes a way to ignore exceptions which may occur during query execution. +This can be useful when you want to handle exceptions in a custom way, for example, by logging them. To ignore exceptions, you can +supply a `Func` to the `IgnoreException` property of the `EntityFrameworkAsyncQueryExecutor` instance. The function +should return `true` if the exception should be ignored and `false` otherwise. An example: +```csharp +builder.Services.AddFluentUIComponents() + .AddDataGridEntityFrameworkAdapter(ex => ex is SqlException sqlEx + && sqlEx.Errors.OfType().Any(e => (e.Class == 11 && e.Number == 0) || (e.Class == 16 && e.Number == 3204))); +``` + +For more information see also https://github.com/microsoft/fluentui-blazor/issues/3269. + + ## Support The Microsoft Fluent UI Blazor library is an open source project and is **not** an official part of ASP.NET Core, which means it’s **not** officially supported and isn’t committed to ship updates as part of any official .NET updates. It is built and maintained by Microsoft employees (**and** other contributors) diff --git a/src/Extensions/DataGrid.ODataAdapter/ODataAdapterServiceCollectionExtensions.cs b/src/Extensions/DataGrid.ODataAdapter/ODataAdapterServiceCollectionExtensions.cs index 9115d25956..08acd41336 100644 --- a/src/Extensions/DataGrid.ODataAdapter/ODataAdapterServiceCollectionExtensions.cs +++ b/src/Extensions/DataGrid.ODataAdapter/ODataAdapterServiceCollectionExtensions.cs @@ -1,7 +1,13 @@ -using Microsoft.FluentUI.AspNetCore.Components.DataGrid.ODataAdapter; +// ------------------------------------------------------------------------ +// MIT License - Copyright (c) Microsoft Corporation. All rights reserved. +// ------------------------------------------------------------------------ + using Microsoft.FluentUI.AspNetCore.Components.DataGrid.Infrastructure; +using Microsoft.FluentUI.AspNetCore.Components.DataGrid.ODataAdapter; +#pragma warning disable IDE0130 // Namespace does not match folder structure namespace Microsoft.Extensions.DependencyInjection; +#pragma warning restore IDE0130 // Namespace does not match folder structure /// /// Provides extension methods to configure on a . diff --git a/src/Extensions/DataGrid.ODataAdapter/ODataAsyncQueryExecutor.cs b/src/Extensions/DataGrid.ODataAdapter/ODataAsyncQueryExecutor.cs index 4ca709a4b4..433e791757 100644 --- a/src/Extensions/DataGrid.ODataAdapter/ODataAsyncQueryExecutor.cs +++ b/src/Extensions/DataGrid.ODataAdapter/ODataAsyncQueryExecutor.cs @@ -1,15 +1,25 @@ -using Microsoft.OData.Client; +// ------------------------------------------------------------------------ +// MIT License - Copyright (c) Microsoft Corporation. All rights reserved. +// ------------------------------------------------------------------------ + using Microsoft.FluentUI.AspNetCore.Components.DataGrid.Infrastructure; +using Microsoft.OData.Client; namespace Microsoft.FluentUI.AspNetCore.Components.DataGrid.ODataAdapter; +/// +/// An implementation for Microsoft.OData.Client. +/// internal class ODataAsyncQueryExecutor : IAsyncQueryExecutor { + /// public bool IsSupported(IQueryable queryable) => queryable.Provider is DataServiceQueryProvider; + /// public async Task CountAsync(IQueryable queryable, CancellationToken cancellationToken) => (int)(await ExecuteAsync(((DataServiceQuery)queryable.Take(0)).IncludeCount(), cancellationToken)).Count; + /// public async Task ToArrayAsync(IQueryable queryable, CancellationToken cancellationToken) => [.. await ExecuteAsync(queryable, cancellationToken)];