In the process of trying to implement a new feature earlier this week I hit a wall (one I knew was there). I'm looking for guidance on how to resolve this one.
Features, Scenarios and Steps naturally form a tree structure. Plans that act on features, scenarios and steps also naturally form a tree structure (although arguably these could be flattened into a list). The reports that the plans produce also naturally form a tree structure (and then frequently flattened for display). I feel as if we are recreating the same tree 3 times for every run. It's making adding new stuff into the tree quite awkward.
So the options as I see it are:
1) Leave it as is but only store the actual tree links in one place. Navigate through those and use Iterators to provide the same info as before
Example:
If we have the following
Feature: Feature A
+- Scenario: Scenario 1
| +- Given some step
| +- When something happens
| +- Then something else happens
+- Scenario: Scenario 2
+- Given some other step
+- When something else happens
+- Then blah
When we add the plan we add it directly to this tree structure
Feature: Feature A -> ExecuteFeaturePlan
+- Scenario: Scenario 1 -> ExecuteScenarioPlan
| +- Given some step -> ExecuteStepPlan
| +- When something happens -> ExecuteStepPlan
| +- Then something else happens -> ExecuteStepPlan
+- Scenario: Scenario 2 -> ExecuteScenarioPlan
+- Given some other step -> ExecuteStepPlan
+- When something else happens -> ExecuteStepPlan
+- Then blah -> ExecuteStepPlan
Then if we want plans we can do a generic Pre-order tree traversal and ask for the plan element from each.
2) Take the generic tree approach and use dictionaries as the nodes. This is going to get messy with figuring out the data is
3) Take the generic tree approach but use a concrete object for the nodes. These would act as glue for each of the other items. I think this is the better approach. Especially if the nodes have an inheritance hierarchy allowing us to add differing behavior for features, scenarios and steps
This whole area is a tangled mess. The enumerations seems like they could be refactored into an inheritance hierarchy and I can feel a Bridge in here but I just can't quite get it. I might restart the whole Planning/Executing/Reporting area using TDD on a separate branch but if anyone has any thoughts or suggestions I'd love to hear them.
P.S. For reference the feature I was trying to implement was Backgrounds. The Fluent Interface and Parser support the idea easily. Adding it to the plan is awkward and getting it to report correctly is even more awkward.