我需要为特定的类Foo
自定义模型绑定(bind),该模型涉及通过一些附加的后处理来扩展常规绑定(bind)逻辑(例如,有条件地将null集合字段设置为空集合)。我想将此逻辑添加到模型绑定(bind)中,以便结果可用于操作过滤器等。
最直接的方法是从ComplexTypeModelBinder
派生并覆盖BindModelAsync
。但是,不幸的是,该方法不是虚拟的。
下一个选择是合成。我正在尝试创建一个具有或获取FooModelBinder
实例的ComplexTypeModelBinder
类。但是,我不知道如何注入(inject)或解析ComplexTypeModelBinder
。这可能吗?有没有更好的方法来扩展ComplexTypeModelBinder
的功能?
最佳答案
我终于意识到,模型联编程序是从模型联编程序提供程序获得的,而不是通过依赖项注入(inject)获得的。为了正确地实例化FooModelBinder
,我需要创建一个FooModelBinderProvider
。为了正确获取ComplexTypeModelBinder
实例进行组合,我的提供者需要访问ComplexTypeModelBinderProvider
。换句话说,要组成模型联编程序,还需要组成模型联编程序提供者。
这是提供者。注意,我们不需要指定注入(inject)的提供程序的确切类型,因为我们只是包装了另一个模型绑定(bind)程序的现有功能。
public class FooModelBinderProvider : IModelBinderProvider
{
private readonly IModelBinderProvider workerProvider;
public FooModelBinderProvider(IModelBinderProvider workerProvider)
{
this.workerProvider = workerProvider;
}
public IModelBinder GetBinder(ModelBinderProviderContext context)
{
if (context == null)
{
throw new ArgumentNullException(nameof(context));
}
if (context.Metadata.ModelType == typeof(Foo))
{
return new FooModelBinder(this.workerProvider.GetBinder(context));
}
return null;
}
}
这是活页夹。请注意,我们在
BindModelAsync
中所做的第一件事是将蹦床放入“ worker ”活页夹中。public class FooModelBinder : IModelBinder
{
private readonly IModelBinder worker;
public FooModelBinder(IModelBinder worker)
{
this.worker = worker;
}
public async Task BindModelAsync(ModelBindingContext bindingContext)
{
await this.worker.BindModelAsync(bindingContext);
if (!bindingContext.Result.IsModelSet)
{
return;
}
var foo = bindingContext.Result.Model as Foo;
if (foo == null)
{
throw new InvalidOperationException($"Expected {bindingContext.ModelName} to have been bound by ComplexTypeModelBinder");
}
// NOW DO SOME INTERESTING POST-PROCESSING
}
}
最后,这是注册自定义资料夹的方法:
services.AddMvc(options =>
{
var workerProvider = options.ModelBinderProviders.First(p => p.GetType() == typeof(ComplexTypeModelBinderProvider));
options.ModelBinderProviders.Insert(options.ModelBinderProviders.IndexOf(workerProvider), new FooModelBinderProvider(workerProvider));
})
关于c# - 如何扩展ComplexTypeModelBinder,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/47643025/