Dependency injection 用于ValidationAttribute的Autofac和DI

Dependency injection 用于ValidationAttribute的Autofac和DI,dependency-injection,autofac,validationattribute,test-project,Dependency Injection,Autofac,Validationattribute,Test Project,我有以下验证属性类: public class ZipCodeValidationAttribute : ValidationAttribute { private readonly IValidationRepository _repository; public override bool IsValid(object value) { var repository = _repository; return repository.

我有以下验证属性类:

public class ZipCodeValidationAttribute : ValidationAttribute
{
    private readonly IValidationRepository _repository;

    public override bool IsValid(object value)
    {
        var repository = _repository;

        return repository.IsPostalCodeValid((string) value);

    }
}
为了进行测试,我尝试使用Autofac作为IOC,并使用属性注入。我已按如下方式设置了测试:

 [TestMethod]
 public void When_PostalCodeAttribute_Given_ValidPostalCode_Then_SystemReturnsTrue()
 {
        // arrange
        var value = "53051";
        var containerBuilder = new ContainerBuilder();
        containerBuilder.RegisterType<ValidationRepository>().As<IValidationRepository>().InstancePerDependency();
        containerBuilder.RegisterType<ZipCodeValidationAttribute>().PropertiesAutowired();
        var container = containerBuilder.Build();

        var attrib = container.Resolve<ZipCodeValidationAttribute>();

        // act
        var result = attrib.IsValid(value);

        // assert
        Assert.IsTrue(result);
 }
[TestMethod]
当“PostalCode属性”被赋予“ValidPostalCode”然后“SystemReturnsTrue()时,公共无效
{
//安排
var value=“53051”;
var containerBuilder=新的containerBuilder();
containerBuilder.RegisterType().As().InstancePerDependence();
containerBuilder.RegisterType().PropertiesAutowired();
var container=containerBuilder.Build();
var attrib=container.Resolve();
//表演
var result=attrib.IsValid(值);
//断言
断言(结果);
}

在测试期间,未解析我的存储库。Autofac新手,希望有人能为我指出正确的方向。

您需要将
存储库声明为Autofac自动连接的属性

public class ZipCodeValidationAttribute : ValidationAttribute
{
    public IValidationRepository Repository { get; set; }

    public override bool IsValid(object value)
    {
        return Repository .IsPostalCodeValid((string) value);
    }
}

我在中解决了整个问题(在
Validator.TryValidate
etc/ASP.NET MVC等的控制下触发DI),使一个人能够编写:

class MyModel 
{
    ...
    [Required, StringLength(42)]
    [ValidatorService(typeof(MyDiDependentValidator), ErrorMessage = "It's simply unacceptable")]
    public string MyProperty { get; set; }
    ....
}

public class MyDiDependentValidator : Validator<MyModel>
{
    readonly IUnitOfWork _iLoveWrappingStuff;

    public MyDiDependentValidator(IUnitOfWork iLoveWrappingStuff)
    {
        _iLoveWrappingStuff = iLoveWrappingStuff;
    }

    protected override bool IsValid(MyModel instance, object value)
    {
        var attempted = (string)value;
        return _iLoveWrappingStuff.SaysCanHazCheez(instance, attempted);
    }
}

还是让我伤心。存储库仍然为null且未解析,因为该属性是私有的。一旦我把它公之于众,一切都是一致的。格拉齐!我也有同样的问题@mservais您需要取消接受此项,因为它具有误导性。Autofac没有办法注入参与模型的模型所承担的实际
ValidationAttribute
sbinding@Eranga虽然这个答案只是回答了这个问题,并且回答正确,但对于我来说,IRL的问题是实例化不是由Autofac完成的。因此,虽然我们有一个通过测试的解决方案,但胜利是没有意义的。对我来说,您的答案应该是或至少是这样的:请注意,通过此测试实际上不会让Autofac在任何有用的上下文中使用该属性
DataAnnotationsModelValidatorProvider.RegisterAdapterFactory(
    typeof(ValidatorServiceAttribute),
    (metadata, context, attribute) =>
        new DataAnnotationsModelValidatorEx(metadata, context, attribute, true));