private FlowBuilder <T> HandleSubElements <T>(FlowBuilder <T> builder, IXmlStepContainer container)
        {
            foreach (var xmlElement in container.JobElements)
            {
                XmlFlow  xmlSubFlow = xmlElement as XmlFlow;
                XmlStep  xmlStep    = xmlElement as XmlStep;
                XmlSplit xmlSplit   = xmlElement as XmlSplit;

                if (xmlElement.Next != null)
                {
                    Next(From(builder, xmlStep, xmlSubFlow, xmlSplit), xmlElement.Next);
                }
                else if (xmlElement.Transitions.Any())
                {
                    foreach (var transition in xmlElement.Transitions)
                    {
                        var transitionBuilder = From(builder, xmlStep, xmlSubFlow, xmlSplit).On(transition.On);
                        var xmlNext           = transition as XmlNext;
                        if (xmlNext != null)
                        {
                            To(transitionBuilder, xmlNext.To);
                        }
                        else if (transition is XmlEnd)
                        {
                            transitionBuilder.End();
                        }
                        else if (transition is XmlFail)
                        {
                            transitionBuilder.Fail();
                        }
                    }
                }
            }
            return(builder);
        }
        private IFlow LoadFlow(XmlFlow xmlFlow)
        {
            string flowId = xmlFlow.Id;

            if (_flowMap.ContainsKey(flowId))
            {
                return(_flowMap[flowId]);
            }

            FlowBuilder <IFlow> flowBuilder  = new FlowBuilder <IFlow>(flowId);
            XmlJobElement       firstElement = xmlFlow.JobElements.First();

            if (firstElement is XmlStep)
            {
                flowBuilder.Start(_stepsMap[firstElement.Id]);
            }
            else
            {
                XmlFlow  xmlSubFlow = firstElement as XmlFlow;
                XmlSplit xmlSplit   = firstElement as XmlSplit;

                flowBuilder.Start(xmlSubFlow != null ? LoadFlow((XmlFlow)firstElement) : LoadSplit(xmlSplit));
            }

            HandleSubElements(flowBuilder, xmlFlow);

            IFlow flow = flowBuilder.End();

            _flowMap[xmlFlow.Id] = flow;
            return(flow);
        }
        private IJob LoadJob(XmlJob xmlJob, JobBuilder jobBuilder)
        {
            FlowBuilder <FlowJobBuilder> jobFlowBuilder;
            XmlJobElement xmlElement = xmlJob.JobElements.First();

            if (xmlElement is XmlStep)
            {
                jobFlowBuilder = jobBuilder.Flow(_stepsMap[xmlElement.Id]);
            }
            else
            {
                XmlFlow  xmlFlow  = xmlElement as XmlFlow;
                XmlSplit xmlSplit = xmlElement as XmlSplit;

                jobFlowBuilder = jobBuilder.Start(xmlFlow != null ? LoadFlow(xmlFlow) : LoadSplit(xmlSplit));
            }

            HandleSubElements(jobFlowBuilder, xmlJob);
            return(jobFlowBuilder.End().Build());
        }
        private FlowBuilder <T> From <T>(FlowBuilder <T> builder, XmlStep xmlStep, XmlFlow xmlFlow, XmlSplit xmlSplit)
        {
            if (xmlStep != null)
            {
                return(builder.From(_stepsMap[xmlStep.Id]));
            }

            if (xmlFlow != null)
            {
                return(builder.From(LoadFlow(xmlFlow)));
            }

            if (xmlSplit != null)
            {
                return(builder.From(LoadSplit(xmlSplit)));
            }

            // Won't happen
            return(null);
        }