Strategy

Strategy

Old forum URL: forums.lhotka.net/forums/t/311.aspx


PitDog posted on Wednesday, June 07, 2006

I have a question about building a strategy pattern with CSLA. Here is my problem.

I have 3 different types of products that I need to model. So following the standard practice of Abstracting the things that are similar and implementing the things that are different I have come up with a Strategy pattern to model it.

Here are the classes involved.

AbstractProduct : ReadOnlyBase

ConcreteProductA:AbstractProduct

ConcreteProductB:AbstractProduct

ConcreteProductC:AbstractProduct

 

With this design you really cant use a standard static FactoryMethod because Static methods in a Abstract base class can not be overriden. So I am wondering if anyone here has done this and can give me a quick over view of how to handle object creation. As well as object initialization.

Thanks,

PD

Pradeep replied on Thursday, June 08, 2006

I had a similar situation and have implemented as follows. Not sure if this is the the right way. If there is any better way, I would be happy to know about it.
 
I have an Order object which has a Deal object as Child. This Deal object can be of three types. DealA, DealB or DealC. What I did was created an abstract class called Deal and inherit DealA, DealB and DealC from it. You would not have any static methods in Deal (since it is abstract and you cannot create an object of that type.
 
I have another factory class which has static method for deal creation and that takes in DealType as parameter and then calls in appropriate Deal's static creation methods. So in my Order object when I want to create/get a deal object I would call DealFactory.NewDeal(DealType).
 
My NewDeal method in factory class looks like this.
 
public static Deal NewDeal(DealType type)

{

   switch(type)

   {

      case DealType.TypeA:

         return DealA.NewDeal();

      case DealType.TypeB:

         return DealB.NewDeal();

      case DealType.TypeC:

         return DealC.NewDeal();

      default:

         throw new NotSupportedException("Invalid deal Source. Cannot get Deal from the given type");

   }

}

 
Apart from this, my Deal class has all the necessary abstract methods (DataPortal_Create, Fetc, etc), just to make sure all my dealType classes implement them.
 
HTH
Pradeep
 
 
 

PitDog replied on Thursday, June 08, 2006

Thanks Pradeep,

Looks like we both did the same thing :-)... I think it is a good solution. In fact some OOP folks may argue that this is the best way. That perhaps object creation is not a role that a business object should worry about.

Anyone care to chime in with other possible ways?

 

PD

RockfordLhotka replied on Thursday, June 08, 2006

This is one reason I give strong preference to using factory methods over calling a constructor directly - you get this kind of flexibility.

razorkai replied on Thursday, August 10, 2006

I have just hit a very similar situation but can't quite seem to get it to work like this.

I have a class based on BusinessListBase defined as follows

public abstract class Notification<T, C> : BusinessListBase<T, C>
where T : BusinessListBase<T, C>
where C : Csla.Core.IEditableBusinessObject

I then have other classes defined as follows

public class NotificationTypeA : Notification<NotificationTypeA, NotificationTypeAChild>
public class NotificationTypeB : Notification<NotificationTypeB, NotificationTypeBChild>

Then I have a method defined in Notification like this

public static Notification<T, C> GetNotifications(NotificationTypeEnum notificationType)
{
switch (notificationType)
{
   
case NotificationTypeEnum.TypeA:
      
return NotificationTypeA.GetNotifications();
      
break;
   case NotificationTypeEnum.TypeB:
      
return NotificationTypeB.GetNotifications();
      
break;
}

And then an example of the actual GetNotifications implementation is

public static NotificationTypeA GetNotifications()
{
   return DataPortal.Fetch<NotificationTypeA>(new Criteria());
}

This won't compile and generates the exception

Error 1 Cannot implicitly convert type 'NotificationTypeA' to 'Notification<T,C>'

What am I doing wrong here?  I am still getting to grips with generics and can't figure it out.

TIA.

John.

Copyright (c) Marimer LLC