/// <summary>
        /// Creates opportunity in stage.
        /// </summary>
        /// <param name="oppData">Opportunity in stage data</param>
        /// <param name="isIntermediateStage">Is stage for creation is intermediate stage</param>
        protected virtual void  CreateOpportunityInStage(OpportunityInStageData oppData, bool isIntermediateStage = false)
        {
            var    currentDate = oppData.Date.HasValue? oppData.Date.Value : UserConnection.CurrentUser.GetCurrentDateTime();
            Entity newEntity   = OppInStageSchema.CreateEntity(UserConnection);

            newEntity.SetColumnValue("Id", Guid.NewGuid());
            newEntity.SetColumnValue("OpportunityId", oppData.OpportunityId);
            newEntity.SetColumnValue("OwnerId", oppData.OwnerId);
            newEntity.SetColumnValue("StageId", oppData.StageData.StageId);
            newEntity.SetColumnValue("StartDate", currentDate);
            if (oppData.StageData.End || isIntermediateStage)
            {
                newEntity.SetColumnValue("DueDate", currentDate);
            }
            newEntity.Save();
        }
        /// <summary>
        /// Synchronizes stages for opportunity.
        /// </summary>
        /// <param name="oldStageId">Last opportunity stage identifier</param>
        /// <param name="opportunity">Current opportunity state</param>
        protected virtual void SynchronizeStage(Guid oldStageId, Entity opportunity)
        {
            List <OpportunityStageData> stages = GetStagesCollection();
            var oppId           = opportunity.GetTypedColumnValue <Guid>("Id");
            var newStageId      = opportunity.GetTypedColumnValue <Guid>("StageId");
            var newStageOwnerId = opportunity.GetTypedColumnValue <Guid>("OwnerId");
            OpportunityStageData newStageData = stages.FirstOrDefault(s => s.StageId == newStageId);
            OpportunityStageData oldStageData = stages.FirstOrDefault(s => s.StageId == oldStageId);

            if (newStageData == null)
            {
                return;
            }
            if (oldStageData != null)
            {
                UpdateDueDateForLastStage(oldStageId, oppId);
            }
            bool isStagePrevious = oldStageData != null && newStageData.Number < oldStageData.Number;

            if (isStagePrevious)
            {
                UpdateIntermediateStages(newStageData.Number, oppId);
            }
            else
            {
                var intermStages = GetIntermediateStages(stages, oldStageData, newStageData);
                CreateIntermediateStages(oppId, newStageOwnerId, intermStages);
            }
            var currentDate = UserConnection.CurrentUser.GetCurrentDateTime();
            OpportunityInStageData oppData = new OpportunityInStageData {
                OpportunityId = opportunity.GetTypedColumnValue <Guid>("Id"),
                StageData     = newStageData,
                OwnerId       = newStageOwnerId,
                Date          = currentDate.AddSeconds(newStageData.Number)
            };

            CreateOpportunityInStage(oppData);
        }