【问题标题】:TFS - Get latest code in a folderTFS - 获取文件夹中的最新代码
【发布时间】:2017-12-02 07:36:06
【问题描述】:

我正在使用 TFS API 来获取 TFS 绑定文件夹下的最新代码文件、目录、.csproj 文件等。

同样,我使用类似以下的内容:

var tfs = TfsTeamProjectCollectionFactory.GetTeamProjectCollection(new 
Uri(ConfigurationManager.AppSettings["TFSUrl"]));
tfs.EnsureAuthenticated();
var vsStore = tfs.GetService<VersionControlServer>();
string workingFolder = @"C:\TFS\SolutionFolder";
Workspace wsp = vsStore.TryGetWorkspace(workingFolder); 
if (wsp != null)
{
    ItemSet items = vsStore.GetItems(workingFolder, VersionSpec.Latest, RecursionType.Full);
    string relativePath = workingFolder + @"/";
    foreach (Item item in items.Items)
    {
        string relativePath1 = item.ServerItem.Replace("$/TFS/SolutionFolder", relativePath);
        if (item.ItemType == ItemType.Folder)
        {
            Directory.CreateDirectory(relativePath1);
        }
        else
        {
            item.DownloadFile(relativePath1);
        }
    }
}

现在,我获取要下载的项目,然后开始下载。但是,我希望它像 VS 处理它的方式一样 - 如果(且仅当)文件/文件夹发生更改,则只下载相同的内容。使用此代码,我总是会在该文件夹中获得“n”个文件/文件夹,然后我会覆盖它们。错误的方法,我知道。但是,我可以修改此代码以检查文件夹或文件的上次更改时间,然后选择覆盖它或忽略它。这是一种选择,尽管那是一个糟糕的选择。

现在,我希望仅获取实际需要更改的文件/文件夹列表,即增量更改。之后,我可以选择覆盖/忽略该列表中的每个项目。因此,在目前的情况下,如果创建了一个新文件/文件夹(或现有文件/文件夹之一在 $/TFS/SolutionFolder 中发生更改,即在服务器中),那么我只想在文件列表中提取该项目/要更改的文件夹(并在 C:\TFS\SolutionFolder 中决定我想用它做什么)。

另外,是否使用 VersionControlServer.QueryHistory() 的重载选项之一?我有这样的事情:

(latestVersionIdOf $/TFS/SolutionFolder) - (existingVersionIdOf C:\TFS\SolutionFolder) = (Versions that I'd go out and get back from the server, for that folder) 

记住。

任何指针都会很有帮助。谢谢!

【问题讨论】:

  • 为什么不使用 vsStore.Get() 方法将文件获取到工作区?它只会获取过期的文件。
  • 谢谢,埃迪!我会检查这种方法。另外,我刚刚发布了我目前所拥有的更新答案。让我知道你的想法。干杯!

标签: c# visual-studio tfs


【解决方案1】:

只需使用Workspace.Get() 或重载方法(wsp.Get()),它只是更新更新的文件。

【讨论】:

  • 谢谢,斯塔林!我尝试了 Workspace.Get() 的默认版本,它需要很长时间才能完成,所以我中途停止了它。你有什么具体的想法吗?另外,我发布了一个更新的方法。如果可能的话,请告诉我你的想法以及如何改进它。
  • @NabakamalDas 需要多少时间?如果你得到部分文件,结果是什么? wsp.Get(new string[] { "$/ScrumStarain/CustomCode/Properties" }, VersionSpec.Latest, RecursionType.Full, GetOptions.None);另一方面,你使用Microsoft Team Foundation Server Extended Client package
  • 让我试一试。所以,假设我在一个文件夹下有 1000 个文件,Get() 调用总是尝试每次“下载”这 1000 个文件。就像您在此处指出的那样,我猜如果我在第一个参数中传递文件的名称,那么我可以避免使用“全部”选项。我还没有尝试过 GetOptions 中的所有选项,但我想我现在应该为此开枪。想法?也许重映射选项适合我..我得给这个更好看。
  • 好的。所以,我尝试了 wsp.Get(new string[] { "$/TFS/FolderX/item.cs" }, VersionSpec.Latest, RecursionType.Full, GetOptions.None);我仍然看到文件被“签出”:(
  • @NabakamalDas 你怎么知道文件被“签出”?另一方面,也可以直接指定路径,如$/TFS/FolderX
【解决方案2】:

我认为我们无法做到这一点。如果将文件下载到没有源代码管理的文件夹,则文件夹内没有版本比较,即使文件夹在源代码管理中,行为也只是下载也没有版本比较操作。因此,它将每次下载所有文件,然后覆盖相同的文件。

在 VS 中,文件都在 TFS 源代码控制系统中,所以当我们获取最新版本时,更改/添加的文件将从 TFS 中检索。如果要获得与 VS 句柄相同的行为,可以使用 tf get 命令。见Get Command

您可以参考这篇文章来使用 tf get 命令: get-latest-version-of-specific-files-with-tfs-power-tools

【讨论】:

  • 谢谢,安迪!我正在尝试使用 wsp.GetExtendedItems() 并根据 VersionLatest 和 VersionLocal 过滤该列表中的每个项目。我认为通过一些调整,我应该能够得到一些工作。再次感谢!
  • 没问题!我将很快发布更新(以及我在该解决方案中看到的其他问题)。谢谢!
【解决方案3】:

更新:-

var tfs = TfsTeamProjectCollectionFactory.GetTeamProjectCollection(new Uri(ConfigurationManager.AppSettings["TFSUrl"]));
tfs.EnsureAuthenticated();
var vsStore = tfs.GetService<VersionControlServer>();
string workingFolder = ConfigurationManager.AppSettings["LocalPathToFolder"]; // C:\TFS\SolutionFolder
string tfsPathToFolder = ConfigurationManager.AppSettings["TFSPathToFolder"]; // $/TFS/SolutionFolder
Workspace wsp = vsStore.GetWorkspace(workingFolder);
if (wsp != null)
{
     ItemSpec[] specs = { new ItemSpec(tfsPathToFolder, RecursionType.Full) };
     ExtendedItem[][] extendedItems = wsp.GetExtendedItems(specs, DeletedState.NonDeleted, ItemType.Any);
     ExtendedItem[] extendedItem = extendedItems[0];
     var itemsToDownload = extendedItem.Where(itemToDownload => itemToDownload.IsLatest == false);
     foreach (var itemToDownload in itemsToDownload)
     {
          try
          {
               switch (itemToDownload.ItemType)
               {
                   case ItemType.File:
                   if (itemToDownload.LocalItem != null)
                   {
                          vsStore.DownloadFile(itemToDownload.SourceServerItem, itemToDownload.LocalItem);
                   }
                   else
                   {
                          string localItemPath = itemToDownload.SourceServerItem.Replace(tfsPathToFolder,
                                    workingFolder);
                          vsStore.DownloadFile(itemToDownload.SourceServerItem, localItemPath);
                   }
                   break;
                   case ItemType.Folder:
                   string folderName = itemToDownload.SourceServerItem.Replace(tfsPathToFolder, workingFolder);
                   if ((!string.IsNullOrEmpty(folderName)) && (!Directory.Exists(folderName)))
                   {
                         Directory.CreateDirectory(folderName);
                   }
                   break;
                }
          }
          catch (Exception e)
          {
               File.AppendAllText(@"C:\TempLocation\GetLatestExceptions.txt", e.Message);
          }
     }
}

这段代码运行良好,除了:

一个。每当它下载一个文件的最新副本时,它都会在 TFS 中“检查”:(

b.对于某些项目,它会引发错误,例如“在版本 T 的源代码管理中找不到项目 $/TFS/SolutionFolder/FolderX/abc.cs”。 - 不过,我必须找出导致此问题的确切原因。

关于如何解决这两个问题或您在此代码中看到的任何其他问题的任何想法?谢谢!

【讨论】:

  • 一个。它替换文件(类似于粘贴文件),因此将检查状态。湾。这些文件更新了吗?你总是得到错误吗?
  • 谢谢,斯塔林!是的,它替换了文件的内容并因此将其检出。我总是有“检查”的东西,但几天前我才看到第二个错误......猜它是一个非常具体的错误。
猜你喜欢
  • 1970-01-01
  • 2017-03-31
  • 2020-07-21
  • 1970-01-01
  • 2016-12-16
  • 2023-02-22
  • 2017-01-02
  • 2017-03-16
  • 2011-12-16
相关资源
最近更新 更多