コード例 #1
0
        /// <summary>
        /// The list of merge targets
        /// </summary>
        public IEnumerable <ITfsBranch> GetPossibleMergeTargetBranches(ITfsBranch sourceBranch, BranchSearchOptions searchOptions = BranchSearchOptions.Both)
        {
            if (sourceBranch.IsSubBranch)
            {
                return(sourceBranch.ChildBranches.AsEnumerable());
            }

            var result = new ObservableCollection <ITfsBranch>();

            var listOfForeignBranchesReferencingSourceBranch
                = (searchOptions == BranchSearchOptions.Both || searchOptions == BranchSearchOptions.Upwards)
                    ? CompleteBranchList
                  .Where(item => item.ChildBranchNames.Any(cb => cb == sourceBranch.Name))
                    : Enumerable.Empty <ITfsBranch>();

            var listOfSourceBranchChildren
                = (searchOptions == BranchSearchOptions.Both || searchOptions == BranchSearchOptions.Downwards)
                    ? sourceBranch.ChildBranchNames
                  .Select(cb => CompleteBranchList.Where(item => item.Name == cb).FirstOrDefault())
                    : Enumerable.Empty <ITfsBranch>();

            return(listOfForeignBranchesReferencingSourceBranch
                   .Union(listOfSourceBranchChildren)
                   .Where(item => item != null)
                   .OrderBy(item => item.Name));
        }
コード例 #2
0
        /// <summary>
        /// Acquires the list of possible merge candidates from the given source to destination branch
        /// </summary>
        /// <param name="source">The source branch</param>
        /// <param name="destination">The target branch</param>
        /// <returns>List of changesets</returns>
        public IEnumerable <ITfsChangeset> GetMergeCandidatesForBranchToBranch(ITfsBranch source, ITfsBranch destination, string sourcePathFilter = null)
        {
            string sourcePath = null, targetPath = null;

            if (sourcePathFilter != null)
            {
                sourcePath = sourcePathFilter;
            }
            else
            {
                sourcePath = source.ServerPath;
            }

            if (sourcePath != source.ServerPath)
            {
                targetPath = GetPathInTargetBranch(destination, sourcePath);
                if (targetPath == null)
                {
                    sourcePath = source.ServerPath;
                    targetPath = destination.ServerPath;
                }
            }
            else
            {
                targetPath = destination.ServerPath;
            }

            return
                (VersionControlServer.GetMergeCandidates(sourcePath, targetPath, RecursionType.Full)
                 .Select(item => new TfsChangeset(item.Changeset)));
        }
コード例 #3
0
 public IEnumerable <TfsChangesetWrapper> QueryChangesets(ITfsBranch sourceBranch, ITfsBranch targetBranch, string sourcePathFilter = null)
 {
     return
         (Model.Repository.Instance.TfsBridgeProvider
          .GetMergeCandidatesForBranchToBranch(sourceBranch, targetBranch, sourcePathFilter)
          .Select(item => UpdateChangesetFromCache(new TfsChangesetWrapper(item))));
 }
コード例 #4
0
        private ITfsChangeset FindChangeset(ITfsChangeset source, ITfsBranch where)
        {
            if (source.GetAffectedBranchesForActiveProject().Contains(where))
            {
                return(source);
            }


            var foundLinks
                = AllAssociatedChangesetsIncludingMerges.Where(link => link.Source != null && link.Source.TfsChangeset.Changeset.ChangesetId == source.Changeset.ChangesetId);

            // This could be more optimized.
            foreach (var foundLink in foundLinks)
            {
                if (foundLink.Target.TfsChangeset.GetAffectedBranchesForActiveProject().Contains(where))
                {
                    return(foundLink.Target.TfsChangeset);
                }
            }
            foreach (var foundLink in foundLinks)
            {
                var found = FindChangeset(foundLink.Target.TfsChangeset, where);
                if (found != null)
                {
                    return(found);
                }
            }
            return(null);
        }
コード例 #5
0
 public void PrepareRefresh()
 {
     _availableSourceBranches = null;
     _sourceBranch            = null;
     _targetBranches          = null;
     _targetBranch            = null;
     _selectedQuery           = null;
 }
コード例 #6
0
        public IReadOnlyList <ITfsChange> GetChangesForBranch(ITfsBranch branch)
        {
            BuildChangePerBranchDictionary();
            List <ITfsChange> changes;

            if (_changesPerBranch.TryGetValue(branch.Name, out changes) == false)
            {
                return(null);
            }
            return(changes);
        }
コード例 #7
0
        /// <summary>
        /// Tries to find the matching item in the target branch.
        /// </summary>
        /// <param name="targetBranch">The target branch</param>
        /// <param name="serverItem">The item</param>
        /// <returns>The serverItem path in the target branch if found, null otherwise</returns>
        public string GetPathInTargetBranch(ITfsBranch targetBranch, string serverItem)
        {
            var res        = VersionControlServer.GetBranchHistory(new ItemSpec[] { new ItemSpec(serverItem, RecursionType.None) }, LatestVersionSpec.Latest);
            var targetTo   = res[0].SelectMany(item => item.Children.Cast <BranchHistoryTreeItem>()).Where(item => item.Relative.BranchToItem.ServerItem.StartsWith(targetBranch.Name, StringComparison.InvariantCultureIgnoreCase)).FirstOrDefault();
            var targetFrom = res[0].SelectMany(item => item.Children.Cast <BranchHistoryTreeItem>()).Where(item => item.Relative.BranchFromItem.ServerItem.StartsWith(targetBranch.Name, StringComparison.InvariantCultureIgnoreCase)).FirstOrDefault();

            return(targetTo != null
                ? targetTo.Relative.BranchToItem.ServerItem
                : (targetFrom != null
                   ? targetFrom.Relative.BranchFromItem.ServerItem
                   : null));
        }
コード例 #8
0
ファイル: TfsChangeset.cs プロジェクト: alexbegh/vmerge
        public IEnumerable <MergedChangeset> FindMergesForActiveProject(ITfsBranch source, IEnumerable <ITfsBranch> potentialMergeSourceBranches = null)
        {
            var branches = GetAffectedBranchesForActiveProject().ToList();

            if (!branches.Contains(source))
            {
                yield break;
            }
            if (potentialMergeSourceBranches == null)
            {
                potentialMergeSourceBranches = branches;
            }

            ExtendedMerge[] results = null;
            try
            {
                results =
                    Repository.Instance.TfsBridgeProvider.VersionControlServer
                    .TrackMerges(
                        new int[] { Changeset.ChangesetId },
                        source.BranchObject.Properties.RootItem,
                        potentialMergeSourceBranches.Select(branch => branch.BranchObject.Properties.RootItem).ToArray(),
                        null);
            }
            catch (Exception)
            {
                yield break;
            }

            var tempDictionary = new Dictionary <int, ITfsChangeset>();

            foreach (var item in results)
            {
                ITfsChangeset sourceCS, targetCS;
                if (tempDictionary.TryGetValue(item.SourceChangeset.ChangesetId, out sourceCS) == false)
                {
                    sourceCS = new TfsChangeset(Repository.Instance.TfsBridgeProvider.VersionControlServer.GetChangeset(item.SourceChangeset.ChangesetId));
                    tempDictionary[item.SourceChangeset.ChangesetId] = sourceCS;
                }
                if (tempDictionary.TryGetValue(item.TargetChangeset.ChangesetId, out targetCS) == false)
                {
                    targetCS = new TfsChangeset(Repository.Instance.TfsBridgeProvider.VersionControlServer.GetChangeset(item.TargetChangeset.ChangesetId));
                    tempDictionary[item.TargetChangeset.ChangesetId] = targetCS;
                }

                yield return(new MergedChangeset()
                {
                    Source = sourceCS,
                    Target = targetCS
                });
            }
        }
コード例 #9
0
        /// <summary>
        /// Creates a temporary workspace
        /// </summary>
        /// <returns>Temporary workspace</returns>
        public ITfsTemporaryWorkspace GetTemporaryWorkspace(ITfsBranch source, ITfsBranch target)
        {
            lock (_locker)
            {
                if (_temporaryWorkspaces == null)
                {
                    _temporaryWorkspaces = new Dictionary <ITfsBranch, Dictionary <ITfsBranch, ITfsTemporaryWorkspace> >();
                }
                if (!_temporaryWorkspaces.ContainsKey(source))
                {
                    _temporaryWorkspaces[source] = new Dictionary <ITfsBranch, ITfsTemporaryWorkspace>();
                }
                if (_temporaryWorkspaces[source].ContainsKey(target))
                {
                    try
                    {
                        var existingWs = _temporaryWorkspaces[source][target];
                        var ws         = VersionControlServer.QueryWorkspaces(existingWs.TfsWorkspace.Name, TfsTeamProjectCollection.ConfigurationServer.AuthorizedIdentity.UniqueName, Environment.MachineName);
                        if (ws.Any())
                        {
                            return(existingWs);
                        }
                    }
                    catch (Exception)
                    {
                    }
                }

                string randomWorkspaceName;
                string localMapping;
                bool   found = false;
                do
                {
                    randomWorkspaceName = "vMerge" + Process.GetCurrentProcess().Id.ToString() + "." + Guid.NewGuid().ToString().Replace("-", "").Replace("{", "").Replace("}", "").Substring(0, 6);
                    var ws = VersionControlServer.QueryWorkspaces(randomWorkspaceName, TfsTeamProjectCollection.ConfigurationServer.AuthorizedIdentity.UniqueName, Environment.MachineName);
                    found = ws.Any();

                    localMapping = Path.Combine(GetBasePath(), randomWorkspaceName);
                    if (Directory.Exists(localMapping))
                    {
                        found = false;
                    }
                } while (found);

                var tfsWorkspace = VersionControlServer.CreateWorkspace(randomWorkspaceName);
                tfsWorkspace.Map("$/", localMapping);
                var workspace = new TfsTemporaryWorkspace(this, tfsWorkspace, source, localMapping, target.Name);
                _temporaryWorkspaces[source][target] = workspace;
                return(workspace);
            }
        }
コード例 #10
0
        public static void ShowNoMergeCandidatesMessageBox(ITfsBranch from, ITfsBranch to)
        {
            var mbvm = new MessageBoxViewModel(
                "No merge candidates",
                String.Format(
                    "There are no pending merges from branch\r\n" +
                    "{0}\r\n" +
                    "to branch\r\n" +
                    "{1}",
                    from.Name, to.Name),
                MessageBoxViewModel.MessageBoxButtons.OK);

            Repository.Instance.ViewManager.ShowModal(mbvm);
        }
コード例 #11
0
        private void LoadChangesets(ITfsBranch sourceBranch, ITfsBranch targetBranch, string sourcePathFilter, BackgroundTask task)
        {
            task.TrackProgress.ProgressInfo = "Loading merge candidates ...";
            var changesets = new ObservableCollection <TfsChangesetWrapper>(TfsItemCache.QueryChangesets(sourceBranch, targetBranch, sourcePathFilter));

            Repository.Instance.BackgroundTaskManager.Post(
                () =>
            {
                if (!task.Cancelled.IsCancellationRequested)
                {
                    SetContent(changesets);
                }
                return(true);
            });
        }
コード例 #12
0
        internal TfsTemporaryWorkspace(TfsBridgeProvider host, Workspace tfsWorkspace, ITfsBranch sourceBranch, string mappedFolder, string targetFolder)
        {
            TfsBridgeProvider = host;
            SourceBranch      = sourceBranch;
            MappedFolder      = mappedFolder;
            TargetFolder      = targetFolder;
            Conflicts         = new List <ITfsMergeConflict>();
            PendingChanges    = new List <ITfsPendingChange>();

            TfsWorkspace = tfsWorkspace;

            //TfsWorkspace.VersionControlServer.ResolvedConflict += VersionControlServer_ResolvedConflict;
            //TfsWorkspace.VersionControlServer.Conflict += VersionControlServer_Conflict;

            //TfsWorkspace.VersionControlServer.NewPendingChange += VersionControlServer_NewPendingChange;
            //TfsWorkspace.VersionControlServer.PendingChangeCandidatesChanged += VersionControlServer_PendingChangeCandidatesChanged;
            //TfsWorkspace.VersionControlServer.PendingChangesChanged += VersionControlServer_PendingChangesChanged;
        }
コード例 #13
0
        private ITfsBranch GetSpecificSubBranch(string serverPath)
        {
            ITfsBranch    subBranch = null;
            WeakReference cachedSubBranchWeak;

            lock (_locker)
            {
                if (CachedSubBranches.TryGetValue(serverPath, out cachedSubBranchWeak))
                {
                    // Intentionally null?
                    if (cachedSubBranchWeak == null)
                    {
                        return(null);
                    }
                    subBranch = cachedSubBranchWeak.Target as ITfsBranch;
                }
            }
            if (subBranch != null)
            {
                return(subBranch);
            }

            subBranch = CompleteBranchList.FirstOrDefault(cb => cb.ServerPath == serverPath);
            if (subBranch == null)
            {
                subBranch = new TfsBranch(VersionControlServer, serverPath, true);
                if (subBranch.ChildBranches.Count == 0)
                {
                    subBranch = null;
                }
            }

            cachedSubBranchWeak = subBranch != null ? new WeakReference(subBranch) : null;
            lock (_locker)
            {
                if (false == CachedSubBranches.ContainsKey(serverPath))
                {
                    CachedSubBranches[serverPath] = cachedSubBranchWeak;
                }
            }
            return(subBranch);
        }
コード例 #14
0
        private void LoadWorkItems(ITfsBranch sourceBranch, ITfsBranch targetBranch, string pathFilter, BackgroundTask task)
        {
            task.TrackProgress.ProgressInfo = "Loading merge candidates ...";
            var changesets = new List <TfsChangesetWrapper>(TfsItemCache.QueryChangesets(sourceBranch, targetBranch, pathFilter));

            task.TrackProgress.ProgressInfo = "Loading work items ...";
            task.TrackProgress.MaxProgress  = changesets.Count;
            var workItems
                = new ObservableCollection <TfsWorkItemWrapper>(
                      TfsItemCache.QueryWorkItems(changesets, task.TrackProgress, task.Cancelled.Token));

            Repository.Instance.BackgroundTaskManager.Post(
                () =>
            {
                if (!task.Cancelled.IsCancellationRequested)
                {
                    SetContent(workItems);
                }
                return(true);
            });
        }
コード例 #15
0
        public bool Merge(ITfsBranch targetBranch, string pathFilter, IEnumerable <ITfsChangeset> changesetsAsEnumerable, ITrackProgress trackProgress = null)
        {
            SimpleLogger.Checkpoint("Merge: {0}, {1}", targetBranch != null ? targetBranch.Name : null, pathFilter);
            if (pathFilter != null && !SourceBranch.Name.StartsWith(pathFilter, StringComparison.InvariantCultureIgnoreCase))
            {
                throw new ArgumentException("If a PathFilter is provided, it needs to be below the SourceBranch");
            }

            var changesets = new List <ITfsChangeset>(changesetsAsEnumerable);
            var files      = new List <string>();

            if (trackProgress != null)
            {
                trackProgress.MaxProgress     = changesets.Count * 2 + 2;
                trackProgress.CurrentProgress = 0;
                trackProgress.ProgressInfo    = "Acquiring file list ...";
            }

            foreach (var changeset in changesets)
            {
                SimpleLogger.Checkpoint("Merge: Processing changeset #{0}", changeset != null ? changeset.Changeset.ChangesetId : -1);
                foreach (var change in changeset.Changes.Select(c => c.Change))
                {
                    SimpleLogger.Checkpoint("Merge: change {0}, filter {1}", change.Item.ServerItem, pathFilter);
                    if (pathFilter != null && change.Item.ServerItem.StartsWith(pathFilter, StringComparison.InvariantCultureIgnoreCase) == false)
                    {
                        continue;
                    }

                    files.Add(change.Item.ServerItem);
                }
                ++trackProgress.CurrentProgress;
            }

            GetRequest[] getRequests =
                files.Distinct().Select(file => new GetRequest(file, RecursionType.None, VersionSpec.Latest)).ToArray();

            if (trackProgress != null)
            {
                trackProgress.ProgressInfo = "Getting files ...";
                ++trackProgress.CurrentProgress;
            }

            SimpleLogger.Checkpoint("Merge: Getting files");
            GetStatus gs = TfsWorkspace.Get(getRequests, GetOptions.None);

            if (trackProgress != null)
            {
                trackProgress.ProgressInfo = "Performing merges ...";
                ++trackProgress.CurrentProgress;
            }

            var resultingConflicts = new List <ITfsMergeConflict>();

            foreach (var changeset in changesets)
            {
                if (trackProgress != null)
                {
                    ++trackProgress.CurrentProgress;
                }
                var csvs = new ChangesetVersionSpec(changeset.Changeset.ChangesetId);

                SimpleLogger.Checkpoint("Merge: Performing merge on CS# {0}", changeset != null ? changeset.Changeset.ChangesetId : -1);
                var mergeResult = TfsWorkspace.Merge(
                    pathFilter ?? SourceBranch.Name,
                    targetBranch.Name,
                    csvs, csvs, LockLevel.None, RecursionType.Full, MergeOptions.ForceMerge);

                if (mergeResult.NumFailures > 0)
                {
                    foreach (var failure in mergeResult.GetFailures())
                    {
                        if (failure.Code == "TF14078" || failure.Message.Contains("TF14078"))
                        {
                            throw new LocalPathTooLongException(failure.Message);
                        }
                        throw new InvalidOperationException(failure.Message);
                    }
                }
            }

            if (trackProgress != null)
            {
                trackProgress.CurrentProgress = trackProgress.MaxProgress;
            }

            SimpleLogger.Checkpoint("Merge: Refreshing conflicts");
            RefreshConflictsWorker(default(CancellationToken));

            SimpleLogger.Checkpoint("Merge: Finished");
            return(Conflicts.Count != 0);
        }
コード例 #16
0
        private void FindMergesForChangesetAndBranch(List <MergedChangesetLink> results, ITfsChangeset changeset, ITfsBranch rootBranch)
        {
            var merges
                = changeset.FindMergesForActiveProject(rootBranch, _potentialMergeSourceBranches)
                  .Select(
                      item => new MergedChangesetLink()
            {
                Source = TfsItemCache.UpdateChangesetFromCache(new TfsChangesetWrapper(item.Source)),
                Target = TfsItemCache.UpdateChangesetFromCache(new TfsChangesetWrapper(item.Target))
            });

            results.Add(
                new MergedChangesetLink()
            {
                Source = null,
                Target = TfsItemCache.UpdateChangesetFromCache(new TfsChangesetWrapper(changeset))
            });
            results.AddRange(merges);
        }
コード例 #17
0
 /// <summary>
 /// Acquires the full list of changesets from the given branch
 /// </summary>
 /// <param name="branch">The branch</param>
 /// <returns>List of changesets</returns>
 public IEnumerable <ITfsChangeset> GetAllChangesetsForBranch(ITfsBranch branch)
 {
     throw new NotImplementedException();
 }
コード例 #18
0
ファイル: TfsChangeset.cs プロジェクト: alexbegh/vmerge
 public ITfsChangeset HasBeenMergedInto(ITfsBranch target)
 {
     throw new NotImplementedException();
 }