Question

I have a financial application that processes 'bonds'. I need to

  1. Model the application to avoid an anaemic model (which i understand is bad).
  2. Instantiate different implementations depending on the type of bond.

The system gets instructions from an external system, and applies the instructions to the specified bond. hence i have an Instruction entity

Instruction[Id,BondReference,Action,Value]

e.g. of an instruction to vote 'yes' for a resolution passed on the bond

Instruction
{
    BondReference: Bond1,
    Action: Vote
    Value: VoteYes
    ResolutionReference: Resolution1
}

and a Bond entity

Bond
{
    Id: 1,
    Reference: Bond1
    Resolutions: [
                     {Resolution1: We have resolved to increase our stake in Google},
                     {Resolution2: We have resolved to fire the CEO}
                     ...
                 ]
    Instructions: [Inst1,Inst2,Inst3...]
}

However, an instruction usually does more than just one thing (it is effectively many instructions in one), e.g. an instruction to cancel a previous instruction, that would mean, firstly, it cancels a previous transaction, then certain values need to be recalculated. Also, a single instruction can come overloaded, it can be to cancel a previous instruction as well as vote for a resolution.

I have been advised to use a domain service to process a new instruction.

BondService
{
    public void Apply(Instruction newInstruction)
    {
        var bond = _bondRepository.GetByReference(newInstruction);
        bond
            .RecalculateNominalValue(newInstruction)
            .CalculateInterest(newInstruction)
            .CancelInstruction(newInstruction)
            .Approve(newInstruction);
    }
}

The problem i see with this structure is that for each instruction, all methods are called even if the method is not relevant. I could use some if statements but then the code would look untidy.

Now my question is,

  1. Is this the best way to model?
  2. And for the calculation, depending on the bond type the calculation differs. So i want to implement polymorphism. I have been told that i need to use a factory to instantiate the correct implementation. Is this the best approach?

For BondType 1,3,5 i use calculationA, for bondType 2,7... i need to use Calculation B. how do i INSTANTIATE the different calc types??? NB, i am well versed with polymorphism, however, i have been unable to find solid examples of how to instantiate the correct implementation. thnx for reading this far...

Was it helpful?

Solution

A few thoughts:

  • Instruction seems like it serves the purpose of a command DTO and a value object used to store an audit trail. Decouple these two concepts.

  • The Bond entity, as is typical for financial domains, calls for event sourcing. In effect, you're already there by storing all instructions and resolutions. Make it explicit. You may not need to store all the instructions if you instead make any changes to a bond explicit as domain events. A single instruction can result in multiple events.

  • The example of a domain service is actually an application service or a command handler. An application services coordinates repositories and delegates to domain objects. To best implement an application service, delegate as much business logic to domain objects, a Bond in this case. Therefore, have the Bond entity decide exactly which sub-behaviors to call so that the application service only calls a single method on the entity.

  • To provide polymorphism, create a value object to allow representation of different bond types. Have the Bond entity delegate to this polymorphic bond type value. You may need a factory to initially instantiate this bond type VO, but once it is associated with the Bond entity, you no longer need to call the factory, the Bond simply references the bond type VO.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top