I'm sorry this question is going to be a bit vague because I'm not entirely sure what I'm looking for.
Basically in my (Asp.net MVC) web app I have some basic (manually coded) workflow triggered by my various user inputs.
I need to send email configurable notifications when certain events happen.
For example, there is an update status method in my controller, which I could write something like this:
public ActionResult UpdateStatus(int id, Status status)
{
Orders order = _orders.GetById(id);
order.Status = status;
if (status = Status.AwaitingApproval)
{
SendAwaitingApprovalNotification(_roles.GetApproverForDept(order.Department));
}
else if (status = Status.Approved && order.Department = someDept) { ... }
else if (status = Status.Approved && order.Department = someOtherDept) { ... }
else if // ... etc
}
As you can see, this is all going to get messy very quickly. And also, the logic for when/what notifications are sent is coded into the controller, which doesn't feel right to me.
Also, there are various other actions which can change the state without specifically calling the UpdateStatus
method. eg
public ActionResult ChangeOrderCost(int id, decimal newCost)
{
Orders order = _orders.GetById(id);
order.Cost = newCost;
order.Status = Status.AwaitingCustomerApproval;
}
These are just made up examples but I hope you get the idea.
What I'm really thinking is that all my notification rules should be self-contained in some kind of configurable notication class, which basically monitors state changes on my object and does whatever it needs to do, so it acts like a plugin to the main application and maintains loose coupling. At the same time, I don't really feel like my underlying data objects should have dependencies on things like notification services, I kind of think this should plug-in to my main controller classes.
I can't really think how to achieve this, but I'm guessing it must be a common problem. Is there a specific design pattern I can read up on to give some clues? Has anyone done something like this before? Am I even thinking about this problem correctly? I'm pretty new to all this stuff but trying to think and code the correct way.