I'm having object structure with depth of inheritance of 3. Object is implementing single particular interface. The depth of inheritance for interface is 4. My final object is being constructed via unity IoC. I need to intercept every public method in this object (means no matter in which of interfaces it is defined), though whatever interceptor type I use (InterfaceInterceptor/TransparentProxyInterceptor/VirtualMethodInterceptor ) it always intercepts only methods defined in the final class of inheritance tree. Please see the illustration of object structure below:
public interface IDevice {
void Connect();
}
public interface ISerialDevice {
void WriteCommand();
}
public interface IProtocolSerialDevice {
void ExecuteProtocolCommand();
}
[MyHandler]
public interface ICustomSerialDevice {
void ExecuteMyCommand();
}
public abstract class AbstractSerialDevice {
public virtual void WriteCommand() {
//omitted
}
}
public abstract class AbstractProtocolSerialDevice : AbstractSerialDevice {
public virtual void ExecuteProtocolCommand() {
//omitted
}
}
public class CustomSerialDevice : AbstractProtocolSerialDevice, ICustomSerialDevice {
public virtual void ExecuteMyCommand() {
//omitted
}
}
public class MyHandlerAttribute : HandlerAttribute {
public override ICallHandler CreateHandler(IUnityContainer container) {
//omitted
}
}
Object is registered into unity container as follows:
container.RegisterType<ICustomSerialDevice, CustomSerialDevice>(
new ContainerControlledLifetimeManager(), new InjectionMethod(postConstructMethodName));
container.Configure<Interception>()
.SetInterceptorFor<ICustomSerialDevice>(new TransparentProxyInterceptor());
Unfortunately my interceptor always gets invoked only for ExecuteMyCommand() method. Is it possible to do such interception I'm striving for via unity container? I'm slowly thinking of trying to achieve it via Spring.NET AOP library.
First off, I would recommend you use the InterfaceInterceptor wherever possible. It will give you the best flexibility and performance. Fall back to using VirtualMethodInterceptor when you can't use InterfaceInterceptor. And as a last resort, use TransparentProxyInterceptor. See here.
For interfaces, the handler attribute only applies to the methods defined on that interface (not inherited). So you can achieve what you are after by decorating all 4 interfaces with the [MyHandler] attribute.
For concrete classes, the handler attribute applies to all inherited types. So you can achieve what you are after by decorating the top AbstractSerialDevice with the [MyHandler] attribute. You could also decorate individual methods on either the interface or the concrete class level.
Also, in my opinion, decorating a concrete method is a bit more discoverable than decorating a type. Though it is a bit more verbose.
Option 1
// No MyHandler on any of the concrete classes
[MyHandler]
public interface IDevice
{ /* omitted */ }
[MyHandler]
public interface ISerialDevice : IDevice
{ /* omitted */ }
[MyHandler]
public interface IProtocolSerialDevice : ISerialDevice
{ /* omitted */ }
[MyHandler]
public interface ICustomSerialDevice : IProtocolSerialDevice
{ /* omitted */ }
Option 2
// No MyHandler on any of the interfaces nor derived classes
[MyHandler]
public abstract class AbstractSerialDevice : ISerialDevice
{ /* omitted */ }
Option 3
// No MyHandler on any of the interfaces nor abstract classes
public class CustomSerialDevice : AbstractProtocolSerialDevice, ICustomSerialDevice
{
[MyHandler]
public override void Connect()
{ base.Connect(); }
[MyHandler]
public override void WriteCommand()
{ base.WriteCommand(); }
[MyHandler]
public override void ExecuteProtocolCommand()
{ base.ExecuteProtocolCommand(); }
[MyHandler]
public void ExecuteMyCommand()
{ /*omitted*/ }
}
Any of those options work for you?
Related
I am currently refactoring some code and am dealing with reorganizing a collection of about a dozen classes with some common methods into a set of derived classes with the shared code in the base, which implements an interface exposing the methods. So far the new structure is fairly straightforward and can be summarised as follows:
public interface IContract
{
public bool MethodA();
}
public abstract class BaseClass : IContract
{
// Default implementation
public virtual bool MethodA() { return true; }
}
public class DerivedClassA : BaseClass
{
private readonly SomeServiceA service;
// Class-specific implementation (if required)
public override bool MethodA() { return service.CheckA(); }
}
Problem is that there is one derived class that contains a public method shared by no other derived class:
public class DerivedClassB : BaseClass
{
private readonly SomeServiceB service;
public override bool MethodA() { return service.CheckB(); }
public void MethodB() { service.PerformAnotherAction(); }
}
This method is currently invoked elsewhere in the codebase as below:
// Factory initialises a class of a type specified in config settings
IContract instance = ClassFactory.GetInstance();
bool ClientMethodA()
{
return instance.MethodA();
}
void ClientMethodB()
{
if (instance.GetType() == typeof(DerivedClassB))
{
((DerivedClassB)instance).MethodB();
}
}
I'd rather the invoking code not know anything about DerivedClassB but I'm not sure how to avoid the casting. My question is whether this design structure is the most optimal given this workflow, and if not, how could it be improved while adhering to SOLID principles?
I have a base interface that looks like this
public interface IBaseWidget<T> where T: IBaseConfiguration
{
void Configure(T configuration);
}
I then have child interfaces that look like this:
public interface ISpecificWidget : IBaseWidget<IChildSpecificConfiguration>
{
}
IChildSpecificConfiguration implements IBaseConfiguration I then have classes that look like this
public class SomeClass : ISpecificWidget
{
public void Configure(IChildSpecificConfiguration configuration)
{
//do stuff
}
}
This all works fine and we will come back to this.
Where it starts to break down is that there are several different extensions of IBaseWidget<T> which means that there are several different SomeClass. Additionally SomeClass is only ever accessed via a facade so, based on a bunch of rules, I have a base facade that actually creates an instance of the necessary SomeClass. Prior to making IBaseWidget generic as shown above, my base facade looked like the following:
public abstract class BaseFacade<T> where T IBaseWidget
{
T Widget {get;set;}
private void Init()
{
Widget = (T)Activator.CreateInstance("type");
}
}
Facades for each implementation of IBaseFoo look like so:
public sealed class SomeFacade : BaseFacade<ISpecificWidget>
{
private void DoSomething()
{
Widget.DoSomething();
}
}
Again, this works fine. My problem is this: after making IBaseWidget generic I modified the base facade like so:
public abstract class BaseFacade<T> where T : IBaseWidget<IBaseConfiguration>
{
T Widget {get;set;}
IBaseConfiguration configuration; //IChildSpecificConfiguration passed in via constructor and assigned to variable
private void Init()
{
Widget = (T)Activator.CreateInstance("type");
Widget.Configure(configuration)
}
}
This breaks the above implmentation of SomeFacade with the message:
ISpecificWidget must be convertible to IBaseWidget<IBaseConfiguration>
My expectation is that when I defined ISpecificWidget like so:
public interface ISpecificWidget : IBaseWidget<IChildSpecificConfiguration>
{
}
it would be convertible to IBaseWidget but that is not the case. I know that I could solve this by having bases for each specific implementation of a widget, but I am trying to keep this as generic as possible. Any feedback would be greatly appreciated.
Maybe this could answer to your problem.
Add this interface:
public interface IBaseWidget
{
void Configure(IBaseConfiguration configuration);
}
Then inherits from it:
public interface IBaseWidget<T> : IBaseWidget
where T : IBaseConfiguration
{
void Configure(T configuration);
}
And finally:
public abstract class BaseFacade<T> where T : IBaseWidget
{
T Widget { get; set; }
IBaseConfiguration configuration; //IChildSpecificConfiguration passed in via constructor and assigned to variable
private void Init()
{
Widget = (T)Activator.CreateInstance(typeof());
Widget.Configure(configuration);
}
}
and:
public class SomeClass : ISpecificWidget
{
void IBaseWidget.Configure(IBaseConfiguration configuration)
{
throw new NotImplementedException();
}
public void Configure(IChildSpecificConfiguration configuration)
{
//do stuff
}
}
I have a situation similar to the one that follows :
interface IAbstractPaymentService { void ProcessPayment(); }
interface IPaymentGateway1Service : IAbstractPaymentService { } // Do not define extra methods but needed for IoC container configuration
interface IPaymentGateway2Service : IAbstractPaymentService { } // Do not define extra methods but needed for IoC container configuration
public abstract class PaymentProcessor
{
protected abstract void ThisMethodNeedsASpecializedService(IAbstractPaymentService abstractPaymentService);
}
public class PaymentGateway1Processor : PaymentProcessor
{
protected override void ThisMethodNeedsASpecializedService(IAbstractPaymentService abstractPaymentService)
{
return ThisMethodNeedsASpecializedService(abstractPaymentService as IPaymentGateway1Service) // Don't worry, I do security checks
}
public void ThisMethodNeedsASpecializedService(IPaymentGateway1Service paymentGateway1Service)
{
paymentGateway1Service.ProcessPayment();
}
}
public class PaymentGateway2Processor : PaymentProcessor
{
protected override void ThisMethodNeedsASpecializedService(IAbstractPaymentService abstractPaymentService)
{
return ThisMethodNeedsASpecializedService(abstractPaymentService as IPaymentGateway2Service) // Don't worry, I do security checks
}
public void ThisMethodNeedsASpecializedService(IPaymentGateway2Service paymentGateway2Service)
{
paymentGateway2Service.ProcessPayment();
}
}
I'm not really happy with this abstraction, because the idea of polymorphism is that you don't care about the underlying type, you just want a certain behaviour to be applied. But here, even if I create a factory of PaymentProcessor, every time the consumer will need to call ThisMethodNeedsASpecializedService(), he will need to know the underlying type to inject the correct service.
I was thinking of storing the Service in an internal property, so that I could create a Factory that would inject the service at creation time and the consumer wouldn't need to know about the service used - and therefore, wouldn't care about the underlying type. But I have always seen the fact of storing a service instance in a property a bad practice, and am not sure if I should go that way.
What do you think about it, and would you do it differently ?
A better way to impement your structure is to inject IAbstractPaymentService via PaymentProcessor costructor. For example:
public abstract class PaymentProcessor
{
protected abstract void ThisMethodNeedsASpecializedService();
}
public class PaymentGateway1Processor : PaymentProcessor
{
private IPaymentGateway1Service paymentGateway1Service;
public PaymentGateway1Processor(IPaymentGateway1Service paymentGateway1Service){
this.paymentGateway1Service = paymentGateway1Service;
}
public void ThisMethodNeedsASpecializedService()
{
this.paymentGateway1Service.ProcessPayment();
}
}
This question already has answers here:
Interface vs Base class
(38 answers)
Closed 8 years ago.
I'm a bit new to OO programming and I'm trying to understand all facets of this kind of practice : inheritance, polymorphism and such, but there's a thing my brain DOESN'T WANT to fully understand: Interfaces.
I can understand the benefits of using interfacing instead of class-inheritance (mostly because a class can't inherit from multiple parents) but here's where I'm stuck:
Let's say I have something like this:
/** a bunch of interfaces **/
public interface IMoveable
{
void MoveMethod();
}
public interface IKilleable()
{
void KillMethod();
}
public interface IRenderable()
{
void RenderMethod();
}
/** and the classes that implement them **/
public class ClassOne : IMoveable
{
public void MoveMethod() { ... }
}
public class ClassTwo: IMoveable, IKilleable
{
public void MoveMethod() { ... }
public void KillMethod() { ... }
}
public class ClassThree: IMoveable, IRenderable
{
public void MoveMethod() { ... }
public void RenderMethod() { ... }
}
public class ClassFour: IMoveable, IKilleable, IRenderable
{
public void MoveMethod() { ... }
public void KillMethod() { ... }
public void RenderMethod() { ... }
}
By using interfaces here, I would have to declare MoveMethod, KillMethod and RenderMethod each time, in each classes... That means duplicating my code. There must be something wrong, because I don't find this really practical.
So should I implement interfaces only on a few classes? Or should I find a way to mix inheritance and interfaces?
Interfaces are like a contract to a class.. If some class states that it supports such an interface, it must have it's method defined as you properly sampled. Interfaces are great to expose common things that don't easily cross different class implementations.
Now, from your samples, you may be best to do a combination to prevent duplicate code by subclassing from a class and ALSO an interface. So you can get parent-structure code constant and expand as needed.
/** Based on same interfaces originally provided... and the classes that implement them **/
public class ClassOne : IMoveable
{
public void MoveMethod() { ... }
}
public class ClassTwo: ClassOne, IKilleable
{
// Move Method is inherited from ClassOne, THEN you have added IKilleable
public void KillMethod() { ... }
}
public class ClassThree: ClassOne, IRenderable
{
// Similar inherits the MoveMethod, but adds renderable
public void RenderMethod() { ... }
}
public class ClassFour: ClassTwo, IRenderable
{
// Retains inheritance of Move/Kill, but need to add renderable
public void RenderMethod() { ... }
}
I am writing a library and I want to have an interface
public interface ISkeleton
{
IEnumerable<IBone> Bones { get; }
void Attach(IBone bone);
void Detach(IBone bone);
}
The Attach() and Detach() implementation actually should be the same for every ISkeleton. Thus, it could essentially be:
public abstract class Skeleton
{
public IEnumerable<IBone> Bones { get { return _mBones; } }
public List<IBone> _mBones = new List<IBone>();
public void Attach(IBone bone)
{
bone.Transformation.ToLocal(this);
_mBones.add();
}
public void Detach(IBone bone)
{
bone.Transformation.ToWorld(this);
_mBones.Remove(bone);
}
}
But C# doesn't allow multiple inheritance. So among various issues, users have to remember to inherit from Skeleton every time they want to implement Skeleton.
I could use extension methods
public static class Skeleton
{
public static void Attach(this ISkeleton skeleton, IBone bone)
{
bone.Transformation.ToLocal(skeleton);
skeleton.Bones.add(bone);
}
public static void Detach(this ISkeleton skeleton, IBone bone)
{
bone.Transformation.ToWorld(this);
skeleton.Bones.Remove(bone);
}
}
But then I need to have
public interface ISkeleton
{
ICollection<IBone> Bones { get; }
}
Which I do not want, because it is not covariant and users can bypass the Attach() and Detach() methods.
Question: Must I really use an abstract Skeleton class or are there any or tricks and methods?
If you need to expose the Attach and Detach methods in your interface, there is always a way to bypass your intended implementations, as all objects implementing the interface can implement them on their own style.
You can let the abstract class Skeleton implement ISkeleton and all classes which are Skeletons do inherit from Skeleton, thus they implement ISkeleton as well.
public interface ISkeleton { ... }
public abstract class Skeleton : ISkeleton { ... } // implement attach and detach
public class SampleSkeleton : Skeleton { ... }
This way you can use your SampleSkeleton as ISkeleton, you don't have to implement these functions as long as you inherit from Skeleton and marking the methods as sealed does not allow overriding them (as long as they are instance methods).
On a side node: Do name your abstract class with Base at the end or mark the base class somehow else (but this is surely up to you).
I would make bones a special type that implements IEnumerable<T>. That way it doesn't violate the single responsibility principle.
public interface ISkeleton
{
AttachableEnumerable<IBone> Bones { get; }
}
public class AttachableEnumerable<T> : IEnumerable<T>
{
// implementation needed.
void Attach(T item);
void Detach(T item);
}
If you want to wrap ISkeleton behaviour, you could always make it a composite object instead of inheriting the behaviour:
public class Body : ISkeleton
{
private SkeletonImpl _skeleton = new SkeletonImpl;
public IEnumerable<IBone> Bones { get { return _skeleton.Bones; } }
public void Attach(IBone bone)
{
_skeleton.Attach(bone);
}
public void Detach(IBone bone)
{
_skeleton.Detach(bone);
}
}
May be you just have to use sealed methods on abstract Skeleton class?
This way they can't be overriden.
http://msdn.microsoft.com/en-us/library/aa645769(v=vs.71).aspx
You can create a wrapper class which implements the 'Attach' and 'Detach' methods and inject this Functionality to your Interface.