Вопрос

I believe that this is more of an inheritency question, but since I am trying to grasp it better by implementing a pattern that uses it, I thought I would ask my question related to get a better grasp.

If you use the Specification Pattern, having a number of specifications all deriving from Specification, and you wrap them with a wrapper specification class:

Example :

public class CustomerCreditCheck : Specification<Customer> {
    private readonly UnlimitedCreditLimitSpecification unlimitedCreditLimitSpec = new UnlimitedCreditLimitSpecification();
    private readonly SufficientCustomerCreditAmountSpec sufficientCustCreditAmtSpec = new SufficientCustomerCreditAmountSpec();
    private readonly AcceptableCustomerCreditStatusSpecification acceptCustCreditStatusSpec = new AcceptableCustomerCreditStatusSpecification();

    public override bool IsSatisfiedBy(Customer customer) {

        return acceptCustCreditStatusSpec
               .And(unlimitedCreditLimitSpec.Or(sufficientCustCreditAmtSpec))
               .IsSatisfiedBy(customer);
    }
}

My question is: since you are passing the customer Entity into the IsSatisfiedBy method of acceptCustCreditStatusSpec (first assumption), how does the customer entity get passed to the IsSatisifedBy method of both unlimitedCreditLimitSpec and SufficientCustCreditAmtSpec specifications?

Thanks,

Это было полезно?

Решение

The Specification<T>.And and Specification<T>.Or methods build a Specification<T> that takes an instance of T and tests it against the logically-defined specification.

So Specification<T>.And would look something like:

public Specification<T> And(Specification<T> left, Specification<T> right) {
    return new SpecificationFromPredicate(
        t => left.IsSatisfiedBy(t) && right.IsSatisfiedBy(t)
    );
}

public class SpecificationFromPredicate<T> : Specification<T> {
    private readonly Func<T, bool> predicate;

    public SpecificationFromPredicate(Func<T, bool> predicate) {
        this.predicate = predicate;
    }

    public bool IsSatisfiedBy(T t) { return this.predicate(t); }
}

Similarly for Specification<T>.Or.

So the whole point is that

acceptCustCreditStatusSpec
           .And(unlimitedCreditLimitSpec.Or(sufficientCustCreditAmtSpec))

is a specification, and given t it returns

acceptCustCreditStatusSpec.IsSatisfiedBy(t) &&
    (unlimitedCreditLimitSpec.IsSatisfiedBy(t) ||
         sufficientCustCreditAmtSpec.IsSatisifedBy(t)
    );
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top