TFS 2010 API - 从合并中获取工作项

har*_*don 5 version-control merge team-build tfs2010

我需要在完成TFS 2010中的构建时发送一封电子邮件,其中详细说明了与作为此构建的一部分编译的签入相关联的工作项.通过使用associatedChangesets构建工作流中可用的变量,这没有问题.

但是,在生产环境中,我们会将更改从Development分支合并到Release分支.在这一点上,构建认为那里只有一个变化 - 这就是前面提到的开发与发布的合并.显然,这是相当无用的,因为我们需要找出在合并的分支中所做的更改以及相关的工作项.

有谁知道如何使用TFS 2010 API实现这一目标?从API的角度来看,它似乎相当糟糕.我知道你可以扩展VS2010中的合并历史节点,但显然这并不好,因为这些数据需要以编程方式收集,以便发送报告电子邮件.

har*_*don 7

好的...我觉得我找到了解决方案,虽然它很笨重而且说实话我不确定它是如何工作的.但是这里 - 也许它会指向一个正确方向的人.

var associatedWorkItems = new List<WorkItem>();

//Passed in from the build workflow (this variable is available under the 'Run On Agent' sequence as 'associatedChangesets'
IList<Changeset> associatedChangesets = context.GetValue(BuildAssociatedChangesets);

if (associatedChangesets.Count > 0)
{
    var projectCollection =
        new TfsTeamProjectCollection(new Uri("http://localhost:8080/tfs/DefaultCollection"));
    VersionControlServer versionControlServer = projectCollection.GetService<VersionControlServer>();

    foreach (var changeset in associatedChangesets)
    {
        //In order to view the individual changes, load the changeset directly from the VCS.
        Changeset localChangeset = versionControlServer.GetChangeset(changeset.ChangesetId);

        foreach (Change change in localChangeset.Changes)
        {
            //Find out what was merged in.
            ChangesetMerge[] mergedChangesets = versionControlServer.QueryMerges(
                null,
                null,
                change.Item.ServerItem,
                new ChangesetVersionSpec(localChangeset.ChangesetId),
                new ChangesetVersionSpec(localChangeset.ChangesetId),
                null,
                RecursionType.Full);

            //Extract work item information from changesets being identified as merged.
            foreach (var changesetMerge in mergedChangesets)
            {
                Changeset actualChange = versionControlServer.GetChangeset(changesetMerge.SourceVersion);

                foreach (WorkItem item in actualChange.WorkItems)
                {
                    if (!associatedWorkItems.Exists(w => w.Id == item.Id))
                    {
                        associatedWorkItems.Add(item);
                    }
                }
            }
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

不要问我究竟是如何QueryMerges工作的,但是我在这里所做的就是告诉我什么是作为变更集的一部分合并的内容.你会注意到参数ChangesetVersionSpec是相同的 - 这意味着我们只是看着从这一个变更集合并.

你将从中获取一系列ChangesetMerge对象QueryMerges().在ChangesetMerge类中有一个名为SourceVersion- 这是ChangesetId合并的原始变更集的属性.一旦我们得到它,我们可以使用该VersionControlServer.GetChangeset()方法加载单个集并提取WorkItem.然后将其添加到WorkItems可以以任何方式操作的列表中(在我的情况下是电子邮件).我还使用了.Exists()检查以确保WorkItem不会记录两次.

请注意,即使您有associatedChangesets构建工作流中的集合,由于某种原因(至少对我来说),Changes[]内部属性associatedChangesets从未填充(因此使用该VersionControlServer.GetChangeset()方法加载每个单独的变更集,因为这似乎实际上填充了我们需要的所有字段.

就像我说的,1.这是一个笨重的解决方案(许多循环 - 其中一些可能是不必要的),2.我不完全理解这是如何工作的,虽然它似乎产生了所需的结果 - 我得出这个结论做了很多测试和调试)最后 - 根据微软提供的糟糕文档,这是我能想到的最好的.

希望它可以帮到某人!