예제 #1
0
        internal SessionWorker(
            Guid sessionId,
            ManualResetEvent sessionEvent,
            AnalysisEngine analysisEngine,
            MigrationEngine migrationEngine,
            LinkEngine linkEngine,
            Guid leftMigrationSourceId,
            Guid rightMigrationSourceId,
            WorkFlowType workFlowType,
            int secondsSyncWaitInterval,
            string threadName)
        {
            SessionId              = sessionId;
            Event                  = sessionEvent;
            AnalysisEngine         = analysisEngine;
            MigrationEngine        = migrationEngine;
            LinkEngine             = linkEngine;
            LeftMigrationSourceid  = leftMigrationSourceId;
            RightMigrationSourceid = rightMigrationSourceId;
            WorkFlowType           = workFlowType;
            m_threadName           = threadName;

            SqlSyncStateManager manager = SqlSyncStateManager.GetInstance();

            m_syncStateManager = manager;
            m_syncCommandQueue = manager;

            m_syncStateMachine = new SyncStateMachine(PipelineState.Default, new SyncStateTransitionAlgorithm(),
                                                      OwnerType.Session, sessionId, m_syncStateManager);
            m_orchPolicy = new SessionOrchestrationPolicy(WorkFlowType, m_syncStateMachine);

            try
            {
                checked
                {
                    MilliSecondsSyncWaitInterval = secondsSyncWaitInterval * 1000;
                }
            }
            catch (OverflowException)
            {
                MilliSecondsSyncWaitInterval = int.MaxValue;
                TraceManager.TraceInformation(
                    "The speicified interval of {0} minutes is too long for the system to handle. The interval is now changed to {1} minutes.",
                    secondsSyncWaitInterval / 60,
                    (int)(MilliSecondsSyncWaitInterval / 1000 / 60));
            }
        }
        internal void Migrate(Guid targetSideSourceId, SessionOrchestrationPolicy orchPolicy)
        {
            try
            {
                Debug.Assert(m_serviceContainers.ContainsKey(targetSideSourceId), string.Format(MigrationToolkitResources.UnknownSourceId, targetSideSourceId));

                ChangeGroupService changegroupService = (ChangeGroupService)m_serviceContainers[targetSideSourceId].GetService(
                    typeof(ChangeGroupService));
                Debug.Assert(changegroupService != null, string.Format("Change group service on {0} is not loaded", targetSideSourceId));

                changegroupService.DemoteInProgressActionsToPending();

                int pageNumber = 0;
                IEnumerable <ChangeGroup> changeGroups = null;

                long?firstConflictedChangeGroupId = null;
                if (StopMigrationEngineOnBasicConflict)
                {
                    firstConflictedChangeGroupId = changegroupService.GetFirstConflictedChangeGroup(ChangeStatus.Pending);
                }

                do
                {
                    // NOTE: we do not increment pageNumber here, because the processed ChangeGroups are marked "Complete" and no longer
                    //       appear in the table
                    TraceManager.TraceInformation("Loading {0} ChangeGroup(s)", m_pageSize);
                    changeGroups = changegroupService.NextMigrationInstructionTablePage(pageNumber, m_pageSize, false, false);

                    foreach (ChangeGroup nextChangeGroup in changeGroups)
                    {
                        if (firstConflictedChangeGroupId.HasValue &&
                            firstConflictedChangeGroupId <= nextChangeGroup.ChangeGroupId)
                        {
                            // we should not process any conflicted change group or the following ones
                            // if StopMigrationEngineOnBasicConflict is the policy
                            return;
                        }

                        //ToDo Session.OnMigratingChangeStarting(args);
                        TraceManager.TraceInformation("Processing ChangeGroup #{0}", nextChangeGroup.ChangeGroupId);
                        ProcessMigrInstructionTableEntry(nextChangeGroup, targetSideSourceId);
                        nextChangeGroup.UpdateStatus(ChangeStatus.InProgress);

                        if (NoActiveMigrationInstructionInChangeGroup(nextChangeGroup))
                        {
                            nextChangeGroup.Complete();
                            continue;
                        }

                        ConversionResult result;
                        try
                        {
                            result = m_migrationProviders[targetSideSourceId].ProcessChangeGroup(nextChangeGroup);
                        }
                        catch (MigrationUnresolvedConflictException)
                        {
                            // We have already created an unresolved conflict, just return.
                            return;
                        }
                        catch (Exception e)
                        {
                            ConflictManager manager = m_serviceContainers[targetSideSourceId].GetService(typeof(ConflictManager)) as ConflictManager;
                            ErrorManager.TryHandleException(e, manager);
                            return;
                        }

                        if (!result.ContinueProcessing)
                        {
                            return;
                        }

                        if (!string.IsNullOrEmpty(result.ChangeId))
                        {
                            FinishChangeGroupMigration(nextChangeGroup, result);
                            InvokePostChangeGroupMigrationAddins(targetSideSourceId, nextChangeGroup);
                        }
                        orchPolicy.Check();
                    }
                }while (changeGroups.Count() == m_pageSize);
            }
            catch (Microsoft.TeamFoundation.Migration.Toolkit.SessionOrchestrationPolicy.StopSingleTripException)
            {
                throw;
            }
            catch (Microsoft.TeamFoundation.Migration.Toolkit.SessionOrchestrationPolicy.StopSessionException)
            {
                throw;
            }
            catch (Exception e)
            {
                ConflictManager manager = m_serviceContainers[targetSideSourceId].GetService(typeof(ConflictManager)) as ConflictManager;
                ErrorManager.TryHandleException(e, manager);
            }
        }