Let us learn Chain of Responsibility Design Pattern

Niladri.Biswas
Posted by in Design Pattern & Practices category on for Beginner level | Points: 250 | Views : 4988 red flag
Rating: 5 out of 5  
 1 vote(s)

In this article we will learn the Chain of Responsibility Design pattern with an example


 Download source code for Let us learn Chain of Responsibility Design Pattern

Introduction

We have come across many situations where a particular request is being handled by one handler since it has the capacity limited to that and if it goes beyond that then the request pass on to the next handler as it is meant for that. If the second level of handler fails to sort out that, then it passes on to the next level and so on.

If the statement is not so clear, then let us try to understand what we are talking about.

Say we are going for an interview with the hard copy of interview letter being send by HR. Generally what happens is that, initially we are being greeted by the receptionist whose job is to ask about the purpose of our presence in that company.We inform her about the purpose(obviously interview) and will show her the call letter. So she will ask us to have a seat and in the meantime will inform the HR (who in turn will inform the interviewer) about our presence.

Next the interviewer will appear and will conduct the interview followed by HR round(considering the fact that we have clear the interview) where the HR will ask about the salary, how soon we can join etc.Considering the case that we have cleared every round of interview, the HR will finally roll out the offer letter to us.

Now let us analyze as what role all these actors has played

Actor Roles
Receptionist
  1. Greet the interviewee.
  2. Inform the HR about the presence of the interviewee.
Interviewer Conducted the technical interview
HR
  1. Conducted HR related interview
  2. Roll out the offer letter

So it is very much clear that every one has got their own role to play and no one's job is being handled by some one else in the chain of this hierarchical process.Means, the Interviewer never asked HR questions or roll out the offer letter neither the Receptionist conducted technical interview round or the HR greeted the interviewee when he came in the office premise.

So the proper request has reached out to the proper handler to satisfy it.

When such a situation appears where we need to chain multiple handlers to handle an incoming request, we look for Chain Of Responsibility.

What is the purpose of Chain Of Responsibility (COR)?

Handles various requests at different levels.

Who are the active participants in COR?

  1. Handler: It exposes handler interface. That is, it defines an interface for handling the requests which the concrete handler will implement. Later on, the client will register to the intended interface to facilitate the request. It establishes the communication channel for handling the request between the client and the concrete handler.
  2. Concrete Handler : This class will be responsible for handling the specific requests (in the above scenario, the Receptionist,HR,Interviewer are all concrete handler actors).
  3. Client : Initiates the requests to a concrete handler (e.g. Interviewee in the example) through the Handler interface.

What is the process for doing so?How it works?

  1. Requests are handled at every level through the Concrete Handler classes.
  2. The Concrete Handler Classes will handle the client request till the time it will be within the purview of the specified handler class.
  3. When it goes beyond that, the current handler will pass it on to the next handler in the chain.
  4. This chain of handling requests by the handler(s) [ hence the name COR ] will go on till it reaches to the final Concrete Handler Class.
  5. If the ultimate concrete handler class fails to resolve the client request, then that will be notified properly to the client.

Scenario where it is applicable

Hierarchical model

Case study

Without a proper implementation, the theory seems to be hazy.Henceforth, we will have a case study where we will implement this pattern.

A patient is suffering from throat pain for some time and hence forth, he went to a Hospital where he stated the same to the receptionist. After listening to the problem the receptionist confirmed him to consult a General Physician. However, after being communicated the same to the General Physician, he confirmed that he is not the right person to look after this problem and asked him to meet an ENT specialist for a proper treatment.

How COR will fit into this problem?

Let us categorize the doctors(mentioned in the example) into two parts

  1. General Physician
  2. ENT Specialist

-ENT Specialist is at a more specialized level than the General Physician.

-If the General Physician fails to diagnose the problem, he will pass on the same to the ENT Specialist.

-If the ENT Specialist has to do so, then he will communicate the same to the client(which is the patient here).

The UML class diagram will be as under

First let us have the DoctorCheckUpRequestHandler.cs file

public

abstract class DoctorCheckUpRequestHandler

{

protected DoctorCheckUpRequestHandler nextHandler;

public abstract void HandleCheckUpRequest(Patient patient);

public void SetUpHandler(DoctorCheckUpRequestHandler nextHandler)

{

this.nextHandler = nextHandler;

}

}

It has a property nextHandler of type DoctorCheckUpRequestHandler, an abstract HandleCheckUpRequest method that the concrete handlers will override and a SetUpHandler method. Initially when the client registers to the concrete handler, then this SetUpHandler gets activated and the nextHandler property gets set.

The two concrete handler classes are GeneralCheckUpRequestHandler and ENTCheckUpRequestHandler.

The implementation of GeneralPhysician.cs file for GeneralCheckUpRequestHandler concrete handler class is as under

public class GeneralCheckUpRequestHandler : DoctorCheckUpRequestHandler

{

public override void HandleCheckUpRequest(Patient patient)

{

if (patient.DiseaseName == Disease.GeneralCheckUp)

Console.WriteLine("Genral physician is handling the problem");

else nextHandler.HandleCheckUpRequest(patient);

}

}

If the patient disease is of General type, then this doctor will handle it else, it will pass it on to the next handler

The implementation of ENTSpecialist.cs file for ENTCheckUpRequestHandler concrete handler class is as under

public

class ENTCheckUpRequestHandler : DoctorCheckUpRequestHandler

{

public override void HandleCheckUpRequest(Patient patient)

{

if (patient.DiseaseName == Disease.EntCheckUp)

Console.WriteLine("ENT doctor is handling the problem");

else Console.WriteLine("Problem is out of reach");

}

}

If the patient disease is of EntCheckUp type, then this kind of patient will be taken care by this doctor(s). Else,they are helpless.

Next comes the PatientCheckupManager (PatientCheckupManager.cs)

public

class PatientCheckupManager

{

//Build the Doctor's hierarchy

DoctorCheckUpRequestHandler generalPhysician = new GeneralCheckUpRequestHandler();

DoctorCheckUpRequestHandler entSpecialist = new ENTCheckUpRequestHandler();

public void PostPartientInformation(Patient patient)

{

NextHandler();

CheckUpPatient(patient);

}

 

private void NextHandler()

{

generalPhysician.SetUpHandler(entSpecialist);

}

 

private void CheckUpPatient(Patient patient)

{

generalPhysician.HandleCheckUpRequest(patient);

}

}

In this class, first of all we are instantiating the concrete handlers.The constructor accepts the Patient information, and then invokes the NextHandler() method where the handler is being set. Then we pass the Patient information to the CheckUpPatient method which accepts the Patient information.

Since, all the requests will go through the General Physician (at least in this case study) and then an appropriate decision will be taken to move on to the next handler level,henceforth we are invoking the HandleCheckUpRequest method of GeneralCheckUpRequestHandler class, where depending on the condition the next level handler is being set

Finally the client code is as below

class Program

{

static void Main(string[] args)

{

PatientCheckupManager checkupManager = new PatientCheckupManager();

checkupManager.PostPartientInformation(

new Patient { PatientName = "Niladri Biswas", DiseaseName = Disease.EntCheckUp });

Console.ReadKey(true);

}

}

Needless to say, that the client is passing on the information about the client to the PatientCheckupManager and it is the responsibility of the PatientCheckupManager to delegate the request to the appropriate handler in the chain (hence the name Chain Of Responsibility).

The final output if we run the application si as under

References

Chain of Responsibility

Conclusion

This idea I got when I went for a treatment recently in a hospital and thought of writing in computer language and put it in a pattern which will help others (mainly beginners) to learn about the Chain of Responsibility

Hope, this article will serve the purpose of teaching as when should we go ahead with COR pattern.Zipped file is attached herewith.Thanks for reading

Page copy protected against web site content infringement by Copyscape

About the Author

Niladri.Biswas
Full Name: Niladri Biswas
Member Level: Platinum
Member Status: Member
Member Since: 10/25/2010 11:04:24 AM
Country: India
Best Regards, Niladri Biswas
http://www.dotnetfunda.com
Technical Lead at HCL Technologies

Login to vote for this post.

Comments or Responses

Login to post response

Comment using Facebook(Author doesn't get notification)