2

Code

public interface IVehicle {
   string VehicleMake { get; }
   int MonthsSincePurchase { get; }
   bool IsApprovedUsed { get; }
   ...
}

public class WarrantyPopUpHandler {
   virtual bool ShouldShowPopup(IVehicle vehicle /* What should I pass in?*/) {
      return false; 
   }
}

public class VolvoWarrantyPopupHandler : WarrantyPopUpHandler {
   override bool ShouldShowPopup(IVehicle vehicle) {
      return vehicle.MonthsSincePurchase < 12;
   }
}

public class BMWWarrantyPopupHandler : WarrantyPopUpHandler {
   override bool ShouldShowPopup(IVehicle vehicle) {
      return vehicle.MonthsSincePurchase < 12;
   }
}

Explanation

Looking at the above pseudo-code there is a IVehicle type that exposes lots of properties of a vehicle. Now some customers want to show a popup for some vehicles and the programmer starts designing a WarrantyPopupHandler. Currently Volvo and BMW want the popup, and they both want it based on the vehicles age. The programmer implements the two derived classes as shown.

What should the ShouldShowPopup() method take as parameter. The only thing it needs from the current use cases is the int MonthsSincePurchase. Is it at present premature to supply the entire IVehicle, should it only take an int?

But there is a very good chance that during the demo another customer, say Ford, for example, will catch the idea and will want the same popup but maybe only for ApprovedUsed (IsApprovedUsed) vehicles in the future. The programmer knows this by experience.

Also there will be lots of other code written that will rely on calling WarrantyPopUpHandler::ShouldShowPopup.

Also note that the base class version ignores the incoming parameter and returns false all the time, so here it seems wasteful to supply a parameter at all.

Bonus question

Does the answer change if IVehicle is part of a larger interface.

interface VehicleInvoice
{
    IVehicle Vehicle { get; }
    ICustomer Customer { get; }
    ...
}

Should the programmer have rather supplied VehicleInvoice to ShouldShowPopup given that customer data may (a rare case by experience) also factor in the decision to show a popup in the future?

See Also

The question is a variation of my earlier question: Minimal design vs anticipated use. How should the answers there influence the design choice here?

Polite Note

I would like answers to try and focus on or discuss what design principles apply here and not treat this as a refactoring exercise that avoids the question being asked. Thanks.

  • Possible duplicate of Interface Implementation: A parameter I don't need – RubberChickenLeader Oct 14 '15 at 21:05
  • @WindRaven I have asked both questions, I don't think they are duplicates. This is about passing a more generic variant of a parameter, while the other is about differing use of an existing interface. They are close but I do not think they are duplicates. – Ali Oct 14 '15 at 21:08
5

Making the parameter an IVehicle is better. You're essentially using your WarrantyPopupHandler hierarchy to add a method with a default implementation to IVehicle. Making the parameter an int wouldn't make sense because ShouldShowPopup is assuming a certain "meaning" for the int (ie. that the int holds IVehicle.MonthsSincePurchase). Since it would be a logic error to call ShouldShowPopup with an int that means something else, the parameter might as well be an IVehicle. Using an IVehicle also improves encapsulation since the caller of ShouldShowPopup doesn't have to examine the internal structure of IVehicle.

As for the VehicleInvoice interface, that comes down to domain knowledge. It seems to me that a warranty is associated with a particular transaction, which seems to be what VehicleInvoice represents. So in the particular case of your "bonus" question, I'd be inclined to make it ShouldShowPopup(VehicleInvoice). Obviously if you carry this thinking too far you end up with global variables, so you have to use your best judgment.

  • I agree, but I am unable to reconcile this with the minimal design folks who say pass in no more then you absolutely need. – Ali Oct 15 '15 at 9:08
  • So what is stopping you from creating a IWarrantyPopup interface that contains only the information you need? – Dunk Oct 15 '15 at 14:35
  • @Dunk Nothing. Can you elaborate your solution as an answer please. – Ali Oct 15 '15 at 16:27

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.