Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

we have some API which will be called either by client A, B, C or D

Current code

doSomething(String client){

if (client.equals("A")){
...
}
else if (client.equals("B")){
...
}

Proposed refactoring 1

separate into multiple methods and have each client call the dedicated method such as

doSomethingForClientA()

doSomethingForClientB()

we need this because internally each method will call other private methods defined in the same class

Proposed refactoring 2

Use strategy (or template) pattern and separate into multiple classes for the clients to call

the method call from client remains

doSomething()

Which approach is better in the long run? Is there any design pattern to help with option 1 ? or a 3rd option?

share|improve this question

4 Answers 4

up vote 7 down vote accepted

Proposed refactoring 2 is better in the long run.

This will allow you to extend additional functionality for additional (unforeseen ) client types later, without modifying tested parts of code, for already existing clients.

share|improve this answer
1  
+1: when you have "a list of things" you should be aware of "yet other things that you don't see now"... :-) –  Lorand Kedves Jul 19 '12 at 8:18

This is really good question with presented analysis!

If you look for a maintainable and extensible code, of course use the option 2!. It is one of the examples where Dependency Inversion Principle is applied.

As a reference i would suggest to look at S.O.L.I.D.principles. In addition, there is a good reply on somewhat similar question - Programming SOLID Principles

share|improve this answer

The second option is better. Use Strategy Pattern. Of course you can use still use doSomethingForClientX() in the private functions if you cant think of a better name. USe template pattern only if your sequence of operations(private function calls) remains the same.

share|improve this answer

[extending my previous comment]

You might move these special codes to wrapper classes assigned to the client types, create them when the client enters, and use their functions.

interface ClientWrapper {
  void doSomething();
}

class ClientWrapperForA implements ClientWrapper {
  void doSomething() {
    // do that something for client A
  }
}

You can create configurable, singleton ClientWrapperFactory, the config is a map with ["A" - "wrapper.class.name.for.clientA"] pairs, and creates the instance by calling Class.forName(cfgMap.get("A")).newInstance(), store the current wrapper instance in the session context (or "get" it all the time, and use lazy creation) - I suppose you talk about a web application. Adding a new client means only extending this map with a new item, and create the appropriate wrapper class.

share|improve this answer
    
yes we already using Spring - so idea is to inject diff implementation class for the same interface in the application-context.xml –  shinynewbike Jul 19 '12 at 9:19
    
Sure, Spring does all the factory and config stuff that I recommended - you only have to use them :) –  Lorand Kedves Jul 19 '12 at 11:25

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

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