我自己一直在使用 unity 和 MVC 4 研究这个问题。
我所看到的是,如果您将它们保留为瞬态对象。 FluentValidation 将为每个已验证的属性创建一个新的验证对象。所以需要一些缓存。
对于我的缓存,我查看了验证器的每个请求缓存。这很好用,因为所有依赖组件都是 Per Request。 (每个请求是自定义代码,它在 HttpContext.Current.Items 集合上存储一个子 Unity 容器,并带有一个在请求结束时销毁/处置子容器的 HTTP 模块)
要在验证器的 Per Request 和 Singleton 瞬间之间进行选择,取决于您如何使用它、它具有什么类型的依赖项以及 IoC Continer 的功能。
通过统一,您可以创建一个单例验证器并使用函数(即 Func serviceFunc)注入服务工厂。
就我而言,每次调用 serviceFunc 时,都会检索 Unity ChildContiner“服务”。因此,我仍然可以使用 ContainerControlledLifetimeManager(singleton) 定义我的“验证器”,并使用 HierarchicalLifetimeManager(Per Request) 定义“服务”。
这样的缺点是每次调用 serviceFunc 时,它都需要检查并从子容器中检索服务。这将是我将返回“每个请求”的最可能原因)
我刚刚更新了我的代码以使用 serviceFunc,今天将对其进行测试。我相信为您的应用找到正确的解决方案将是一次尝试。
下面是我正在使用的验证工厂——我没有使用统一容器(就像网络上的大多数示例一样),而是将IDependencyResolver 注入其中并使用它来解析我的验证器对象。
public class ValidatorFactory : IValidatorFactory
{
private readonly IDependencyResolver _dependencyResolver;
// taken from the attribute Validation factory
public ValidatorFactory(IDependencyResolver dependencyResolver)
{
_dependencyResolver = dependencyResolver;
}
/// <summary>
/// Gets a validator for the appropriate type.
///
/// </summary>
public IValidator<T> GetValidator<T>()
{
return (IValidator<T>)this.GetValidator(typeof(T));
}
/// <summary>
/// Gets a validator for the appropriate type.
///
/// </summary>
public virtual IValidator GetValidator(Type type)
{
if (type == (Type)null)
return (IValidator)null;
var validatorAttribute = (ValidatorAttribute)Attribute.GetCustomAttribute((MemberInfo)type, typeof(ValidatorAttribute));
if (validatorAttribute == null || validatorAttribute.ValidatorType == (Type) null)
{
return (IValidator) null;
}
else
{
return _dependencyResolver.GetService(validatorAttribute.ValidatorType) as IValidator;
}
}
}