Conditionally block method override - c#

I have an application where the parent object has a method to perform validations and every child overrides the method to perform extra validations. Something like:
class Parent {
virtual void DoValidations (Delegate addErrorMessage) {
//do some validations
}
}
class Child : Parent {
override void DoValidations (Delegate addErrorMessage) {
base.DoValidations(addErrorMessage); //the parent method is always called
//do some extra validations
}
}
I added a new "IsDisabled" property that when true the method will not perform any validations.
class Parent {
boolean IsDisabled;
virtual void DoValidations (Delegate addErrorMessage) {
if (IsDisabled)
return;
//do some validations
}
}
I also want that for every child, if the "IsDisabled" property is true, the extra verifications aren't performed. What is the better pattern to use here?

I would split that functionality off in a separate method:
private void DoValidations(Delegate addErrorMessage)
{
if (!this.IsDisabled)
{
this.OnDoValidations(addErrorMessage);
}
}
virtual void OnDoValidations(Delegate addErrorMessage) { }
Now, OnDoValidations can be overridden at will. The IsDisabled check will be done inside the base class.

Well, this is related to SOLID 'L' (Liskou substitution principle). I suggest you to use the following approach:
1) Create interface, for example:
public IValidator {
void Validate(Delegate addErrorMessage);
}
2) Create abstract base class with abstract DoValidations() method:
public abstract class BaseValidator : IValidator {
public void Validate(Delegate addErrorMessage) {
DoValidations(addErrorMessage);
}
protected abstract DoValidations(Delegate addErrorMessage);
}
3) Inherit Parent from BaseValidator (or make your Parent as base class instead of BaseValidator):
public class Parent: ValidatorBase {
public override void DoValidations(Delegate addErrorMessage) {
// do validation
}
}
4) Inherit Child from Parent:
public class Child : Parent {
public override void DoValidations(Delegate addErrorMessage) {
// do validation
}
}
5) Now it's time to add IsDisabled property. We just need to modify ValidatorBase and IValidator:
public interface IValidator {
bool IsDisabled {get; set; }
void Validate(Delegate addErrorMessage);
}
public abstract class BaseValidator : IValidator {
public bool IsDisabled { get; set; }
public void Validate(Delegate addErrorMessage) {
if(!IsDisabled) {
DoValidations(addErrorMessage);
}
}
protected abstract DoValidations(Delegate addErrorMessage);
}
6) Now use your IValidator validator = _factory.Create():
validator.IsDisabled = false;
validator.Validate();
Good luck!

Related

design pattern for the case of abstract class with inheriting classes with empty implementation methods

Can you please recommend of a good practice pattern for the following scenario:
I have a base abstract class that defines the common behavior and two inheriting classes that each defines set of methods that differ the one implementation from the other.
Then in the creation code (let's say by configuration) I choose which implementation I desire for each case of the configuration setting and call "doWork", my issue is how to avoid the "empty" implementations in the inheriting classes in case the inheriting class chooses not to implement the method.
abstract class CommonParentClass{
public void doWork()
{
commonA();
commonB();
uniqueA();
uniqueB();
}
internal void commonA()
{
//do work which is same for inheriting classes
}
internal void commonB()
{
//do work which is same for inheriting classes
}
abstract void uniqueA();
abstract void uniqueB();
abstract void uniqueC();
}
class FirstChildClass:CommonParentClass
{
protected void uniqueA()
{
//implementation specific to first child
}
protected void uniqueB()
{
//EMPTY
}
protected void uniqueC()
{
//implementation specific to first child
}
}
class SecondChildClass:CommonParentClass
{
protected void uniqueA()
{
EMPTY
}
protected void uniqueB()
{
//implementation specific to second child
}
protected void uniqueC()
{
//implementation specific to second child
}
}
I have about 5/6 methods which are empty in one of the inheriting classes.
What Design Pattern should I use in order to overcome this and avoid code repetition?
Given that all these functions seem to have the same signature, you could conceivably use a list of Actions.
abstract class CommonParent
{
private readonly List<Action> _funcs = new List<Action>();
private void CommonA() { }
private void CommonB() { }
protected void AddAction(Action action) => _funcs.Add(action);
protected CommonParent()
{
_funcs.Add(CommonA);
_funcs.Add(CommonB);
}
internal void Execute()
{
foreach(Action action in _funcs)
action();
}
}
class FirstChildClass : CommonParent
{
private void UniqueA() { }
private void UniqueB() { }
private void UniqueC() { }
public FirstChildClass()
{
AddAction(UniqueA);
AddAction(UniqueB);
AddAction(UniqueC);
}
}
class SecondChildClass : CommonParent
{
private void UniqueD() { }
private void UniqueE() { }
private void UniqueF() { }
public SecondChildClass()
{
AddAction(UniqueD);
AddAction(UniqueE);
AddAction(UniqueF);
}
}

How to invoke method in parent class from child class using reflection?

I create child objects (Customer, Product, ...) and invoke method ApplyChange in parent class (AggregateRoot), from that method I would like to call method Apply in child class for passed event. Is it possible using reflection or I should change something?
public abstract class AggregateRoot
{
public void ApplyChange(IEvent #event)
{
Apply(#event); // how to call this method?
}
}
public class Customer : AggregateRoot
{
private void Apply(CustomerCreatedEvent e)
{
Console.WriteLine("CustomerCreatedEvent");
}
}
public class Product : AggregateRoot
{
private void Apply(ProductCreatedEvent e)
{
Console.WriteLine("ProductCreatedEvent");
}
}
public interface IEvent
{
}
public class CustomerCreatedEvent : IEvent
{
}
public class ProductCreatedEvent : IEvent
{
}
class Program
{
static void Main(string[] args)
{
Customer customer = new Customer();
customer.ApplyChange(new CustomerCreatedEvent());
Product product = new Product();
product.ApplyChange(new ProductCreatedEvent());
}
}
Is it possible using reflection or I should change something?
I focused for now on the non-reflection, as IMO reflection should be the last resort here.
Option 1: abstract method
You could make Apply an abstract method en then you could call it from AggregateRoot.
e.g.
using System;
public abstract class AggregateRoot
{
public void ApplyChange(IEvent #event)
{
Apply(#event); // how to call this method?
}
protected abstract void Apply(IEvent e);
}
public class Customer : AggregateRoot
{
protected override void Apply(IEvent e)
{
if (e is CustomerCreatedEvent)
{
Console.WriteLine("CustomerCreatedEvent");
}
}
}
public class Product : AggregateRoot
{
protected override void Apply(IEvent e)
{
if (e is ProductCreatedEvent)
{
Console.WriteLine("ProductCreatedEvent");
}
}
}
public interface IEvent
{
}
public class CustomerCreatedEvent : IEvent
{
}
public class ProductCreatedEvent : IEvent
{
}
But please note, it has it downsides as:
methods needs to non-private
the should have the same parameter type for Apply. (IEvent parameter) - so I've added the type check inside the Apply methods.
Option 2: abstract method and generic AggregateRoot
Another option is to make AggregateRoot generic for the type IEvent, e.g. something like this.
using System;
public abstract class AggregateRoot<TEvent>
where TEvent : IEvent
{
public void ApplyChange(TEvent #event)
{
Apply(#event); // how to call this method?
}
protected abstract void Apply(TEvent e);
}
public class Customer : AggregateRoot<CustomerCreatedEvent>
{
protected override void Apply(CustomerCreatedEvent e)
{
Console.WriteLine("CustomerCreatedEvent");
}
}
public class Product : AggregateRoot<ProductCreatedEvent>
{
protected override void Apply(ProductCreatedEvent e)
{
Console.WriteLine("ProductCreatedEvent");
}
}
public interface IEvent
{
}
public class CustomerCreatedEvent : IEvent
{
}
public class ProductCreatedEvent : IEvent
{
}
Note I've changed also ApplyChange in this case.
If those things won't solve your problem, please elaborate what you are trying to archive, otherwise this will be a XY problem

Is it possible to have an override method call its abstract virtual method?

My goal is to have the Abstract class update on its own once Consume is called on one of the derived classes.
Imagine this:
public interface IConsumable
{
void Consume();
}
public abstract class AbstractConsumable : IConsumable
{
private bool _consumed = false;
public virtual void Consume()
{
_consumed = true;
}
}
public class HealthyConsumable: AbstractConsumable
{
public override void Consume()
{
// Do something healthy and ...
base.Consume(); // Would like to avoid this...
}
}
public class PoisonousConsumable: AbstractConsumable
{
public override void Consume()
{
// Do something poisonous and ...
base.Consume(); // Would like to avoid this...
}
}
What I would like to achieve here is not having to call base.Consume() on the override methods, but still have the abstract class set _consumed once the derived classes call their Consume() methods.
You could make Consume none virtual and within it you called another protected virtual (or abstract method) that can contain code that be change by sub classes. Consumers of your class can only call the public Consume method but this will intern call the sub class implementation specific code
public interface IConsumable
{
void Consume();
}
public abstract class AbstractConsumable : IConsumable
{
private bool _consumed = false;
public void Consume()
{
_consumed = true;
InternalConsumerBehaviour();
}
protected virtual void InternalConsumeBehaviour()
{
//default do nothing could potentially mark this method abstract rather than virtual its up to you
}
}
public class HealthyConsumable: AbstractConsumable
{
protected override void InternalConsumeBehaviour()
{
// Do something healthy and ...
}
}
public class PoisonousConsumable: AbstractConsumable
{
protected override void InternalConsumeBehaviour()
{
// Do something poisonous and ...
}
}
If I get what you're asking right you could do something like this:
public interface IConsumable
{
void Consume();
}
public abstract class AbstractConsumable : IConsumable
{
private bool _consumed = false;
public abstract void ConsumeEffects();
public void Consume()
{
this.ConsumeEffects();
_consumed = true;
}
}
public class HealthyConsumable: AbstractConsumable
{
public override void ConsumeEffects()
{
// Do something healthy and ...
// Consume will get called in the base
}
}
public class PoisonousConsumable: AbstractConsumable
{
public override void ConsumeEffects()
{
// Do something poisonous and ...
// Consume will get called in the base
}
}

Inheritance and classes within classes

Here's some pseudo code to illustrate what I'm looking at.
public class Loader
{
public Execute()
{
var currentPage = new ItemPageDocumentBuilder();
while(reader.Read())
{
currentPage.Add(reader.XmlDoc);
}
}
private class ItemsToLoad
{
private XmlDocument _page
public void Add(XmlElement itemelement)
{
_page.DocumentElement.AppendChild(itemElement);
}
}
}
I need to derive a class from Loader, and then override the Add method of the ItemsToLoad class inside it, and then call base.Execute(). In other words I want the Execute() method of my derived class to be exactly the same as that of Loader, but to use the overridden Add method of ItemsToLoad to to its work.
I suspect the neatest way to do this would be to remove ItemsToLoad from inside Loader, and make it abstract, correct?
If I couldn't do that, out of interest, what's the best solution?
If I understand your requirement, you have two responsabilities: executing something (which is always the same), and adding something (which differs).
I would do it much simpler, without inheritance and inner classes.
For the adding task, you define an interface:
public interface IItemAdder
{
void Add();
}
And one ore more implementations:
public class ItemAdder1 : IItemAdder
{
public void Add()
{
// specific implementation here
}
}
Then, you have a Loader, in which you inject a specific instance of item adder:
public class Loader : ILoader
{
private IItemAdder _itemAdder;
public Loader(IItemAdder itemAdder)
{
_itemAdder = itemAdder;
}
public void Execute()
{
// use injected item adder to do work
_itemAdder.Add();
}
}
public interface ILoader
{
void Execute();
}
And so usage is:
var loader = new Loader(new ItemAdder1());
loader.Execute();
This way everything is injected, can be replaced and mocked easily; and you clearly separate concerns.
Here is a suggestion (Syntax might not be correct though):
public class Loader
{
ItemsToLoad item;
public Loader(ItemsToLoad item) {
this.item = item;
}
public Execute()
{
// do things using item like item.add();
}
}
interface ItemsToLoad
{
void add();
}
class ItemsToLoad1: ItemsToLoad
{
void add(){
// implementation
}
}
class ItemsToLoad2: ItemsToLoad
{
void add(){
// implementation
}
}
And here is how to use them;
ItemsToLoad item;
if (some condition) {
item = new ItemsToLoad1()
} else {
item = new ItemsToLoad2()
}
Loader loader = new Loader(item);
loader.execute();
You can inherit both classes and inject child sub-class object to its parent.
class Loader
{
public void Execute(ItemsToLoad argObj)
{
if(argObj == null)
argObj = new ItemsToLoad();
argObj.Add(19);
}
public class ItemsToLoad
{
public virtual void Add(int a)
{
Console.WriteLine("Reached ItemsToLoad.");
}
}
}
class ChildLoader:Loader
{
public void Execute(ItemsToLoad argObjLoader)
{
if (argObjLoader == null)
argObjLoader = new ChildItemsToLoad();
base.Execute(argObjLoader);
}
class ChildItemsToLoad : Loader.ItemsToLoad
{
public override void Add(int b)
{
Console.WriteLine("Reached ChildItemsToLoad.");
}
}
}
And can start with
ChildLoader obj999 = new ChildLoader();
obj999.Execute(null);
I need to derive a class from Loader, and then override the Add method of the ItemsToLoad class inside it, and then call base.Execute(). In other words I want the Execute() method of my derived class to be exactly the same as that of Loader, but to use the overridden Add method of ItemsToLoad to to its work.
You need to override Loader, not ItemsToLoad. You haven't shown the code that uses ItemsToLoad, so it's difficult to be specific - but at the very least, you would need to override the new ItemsToLoad to point to your subclass. Also, ItemsToLoad is private - meaning you can't use it except from within Loader. As it is now, you'd need a completely rewritten ItemsToLoad and to override every method in Loader that uses ItemsToLoad.
If you control the Loader class, the easiest changes would probably be to abstract out the creating of ItemsToLoad and open up ItemsToLoad so it can be subclassed. Something like:
public class Loader {
private ItemsToLoad Items { get; set; }
protected virtual ItemsToLoad CreateItemsToLoad() {
return new ItemsToLoad();
}
protected class ItemsToLoad {
public virtual void Add() {
}
}
}
public class MyOtherLoader : Loader {
protected override ItemsToLoad CreateItemsToLoad() {
return new MyOtherItemsToLoad();
}
private class MyOtherItemsToLoad : ItemsToLoad {
public override void Add() {
}
}
}

"Base class params are not always used" code smell

Suppose you had such code:
public Base
{
abstract void Register();
}
public Registrator1: Base
{
override void Register()
{
//uses the current state of the object to populate the UI captions
}
}
public Registrator2: Base
{
override void Register()
{
//uses the current state of the object to populate the UI captions
}
}
But When you receive a new business rule asking you to write Registrator3 which actually registers based on some parameter and you change your code base to the next:
public Base
{
abstract void Register(externalParam);
}
public Registrator1: Base
{
override void Register(externalParam)
{
//uses the current state of the object to populate theUI
}
}
public Registrator2: Base
{
override void Register(externalParam)
{
//uses the current state of the object to populate the UI
}
}
public Registrator3: Base
{
override void Register(externalParam)
{
//uses a DDD - service passed in the params to populate the UI
}
}
But Registrator1 and Registrator2 do not need that param and the code becomes smelly. What are the ways to re-write this code?
You could use an object as a parameter here; which is commonly used in scenarios where the number of parameters can vary depending on the call being used.
struct RegistrationInfo
{
public static readonly RegistrationInfo Empty = new RegistrationInfo();
public string Username;
public string CustomerName;
public string Validity;
}
abstract class Base
{
public abstract void Register(RegistrationInfo info);
// If you want to retain the paramaterless call:
public void Register()
{
Register(RegistrationInfo.Empty);
}
}
class Registrar1 : Base
{
public override void Register(RegistrationInfo info)
{
if (info.Username == null) throw new ArgumentNullException("info.Username");
}
}
class Registrar2 : Base
{
public override void Register(RegistrationInfo info)
{
if (info.CustomerName == null) throw new ArgumentNullException("info.CustomerName");
}
}
This has the advantage that you don't need to change method parameters (which is breaking interface) each time a parameter is added. The usage also becomes somewhat self-documenting:
var r = new Registrar1();
r.Register(new RegistrationInfo(){ Username = "JimJoe" });
r.Register(RegistrationInfo.Empty);
It's like air freshener for this type of code smell, while it's still smelly; you can make it smell nicer.
Finally you can make the call-site cleaner by making it a params argument (this has a small amount of overhead); in all honesty though it is more smelly because it's a language hack. Finally you could improve it with generics:
class RegistrationInfo
{
}
class RegistrationInfo1 : RegistrationInfo
{
public string Arg;
}
class RegistrationInfo2 : RegistrationInfo
{
public int Arg;
}
interface IBase<in TRegistration>
where TRegistration : RegistrationInfo
{
void Register(TRegistration registration);
}
class Base : IBase<RegistrationInfo>
{
public void Register(RegistrationInfo registration)
{
}
}
class Registrar1 : IBase<RegistrationInfo1>
{
public void Register(RegistrationInfo1 arg)
{
}
}
class Registrar2 : IBase<RegistrationInfo2>
{
public void Register(RegistrationInfo2 arg)
{
}
}
Is it not possible to contain the logic for externalParam in Registrator3?
In other words, Registrator3 uses the param, then calls the unmodified parameterless base?
A lot really depends on where the logic belongs. If it is something intrinsic to the base, then put it in the base, and either overload the Register() function or supply a default value for the param so that sub classes don't need to provide it.
Assuming you want to reuse the registration logic from the base class, you could update the code as follows:
public class Base
{
public virtual void Register(object externalParam)
{
// base registration logic goes here
}
}
public class Registrator1: Base
{
public override void Register(object externalParam)
{
base.Register(null);
// custom registration logic goes here
}
}
public class Registrator2: Base
{
public override void Register(object externalParam)
{
base.Register(null);
// custom registration logic goes here
}
}
public class Registrator3: Base
{
public override void Register(object externalParam)
{
base.Register(externalParam);
// custom registration logic goes here
}
}
HTH,
Cosmin
EDIT: Updated code to compile.

Categories

Resources