警告 CS0618:“ComplexTypeModelBinder”已过时

Nen*_*nad 5 asp.net-core-5.0

在 .NET Core 3 中,我扩展了ComplexTypeModelBinder类来为特定类创建自定义模型绑定器。

主要目标是通过方法覆盖模型实例的创建CreateModel

public MyModelBinder: ComplexTypeModelBinder
{
    // Constructor here...
    
    protected override object CreateModel(ModelBindingContext bindingContext)
    {
        // Create model instance based on custom condition.
    }

}
Run Code Online (Sandbox Code Playgroud)

升级到 .NET 5 后,我收到一条编译警告,需要替换ComplexTypeModelBinderComplexObjectModelBinder

警告 CS0618:“ComplexTypeModelBinder”已过时:“此类型已过时,将在未来版本中删除。请改用 ComplexObjectModelBinder。'

问题是ComplexObjectModelBinder密封类和CreateModel方法是internal密封的,因此子类方法不再起作用。

Nen*_*nad 5

我选择的解决方案是创建MyModelBinder实现IModelBinder接口并充当ComplexObjectModelBinder. ComplexObjectModelBinder作为构造函数参数传入MyModelBinder

MyModelBinderProvider和 也使用相同的方法ComplexObjectModelProvider

稍后,不要重写CreateMethodof ComplexObjectModelBinder(这在 .NET 5 中是不可能的),只需在传递 to 之前在的bindingContext.Model包装方法中进行赋值即可。这将使用传入的模型,而不是创建默认的新实例。BindAsyncModelMyModelBinderbindingContextComplexObjectModelBinderBindAsyncModelComplexObjectModelBinder

public class MyModelBinder: IModelBinder
{
    private readonly ComplexObjectModelBinder _binder;
    public MyModelBinder(ComplexObjectModelBinder binder)
    {
        _binder = binder;
    }

    public Task BindModelAsync(ModelBindingContext bindingContext)
    {
        MyModel myModel = // custom instantiation logic here
        bindingContext.Model = myModel;
        return _binder.BindModelAsync(bindingContext);
    }
}
Run Code Online (Sandbox Code Playgroud)

对于自定义模型绑定器提供程序的注册,首先我们找到现有的、自动注册的ComplexObjectBinderProvider,在 的 构造函数中使用它MyModelBinderProvider,然后插入MyModelBinderProvider到 的前面ComplexObjectBinderProvider

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllersWithViews(options => {
        // more configurations here...

        var bindingProvider = options.ModelBinderProviders.First(provider =>
            provider is ComplexObjectModelBinderProvider) as ComplexObjectModelBinderProvider;

        var indexOf = options.ModelBinderProviders.IndexOf(bindingProvider);

        options.ModelBinderProviders.Insert(indexOf, new MyModelBinderProvider(bindingProvider));
    }
}
Run Code Online (Sandbox Code Playgroud)