2015-02-09 45 views
0

当创建TFS通过API构建的定义,我需要先删除,如果定义预先存在:删除构建定义

if (BuildServer.QueryBuildDefinitions(teamProject).Any(d => d.Name == buildDefinitionName)) 
{ 
    buildDefinition = BuildServer.GetBuildDefinition(teamProject, buildDefinitionName); 
    var builds = BuildServer.QueryBuilds(buildDefinition); 
    if (builds != null && builds.Any()) 
    { 
     Console.WriteLine("delete {0} builds for build definition: {1}", builds.Count(), buildDefinition.Name); 
     BuildServer.DeleteBuilds(builds); 
    } 
    if (buildDefinition.Workspace.Mappings.Any()) 
    { 
     var mappings = buildDefinition.Workspace.Mappings.Select(m => m.ServerItem).ToArray(); 
     foreach (var mapping in mappings) 
     { 
      Console.WriteLine("remove workspace mapping: {0}", mapping); 
      buildDefinition.Workspace.RemoveMapping(mapping); 
     } 
    } 
    Console.WriteLine("delete build definition: {0}", buildDefinition.Name); 
    BuildServer.DeleteBuildDefinitions(new[] { buildDefinition }); 
} 

这个工程一样后续:

buildDefinition = BuildServer.CreateBuildDefinition(teamProject); 
buildDefinition.Name = buildDefinitionName; 

然而,当第一次构建获取运行,它会引发冲突的有关工作区的错误:

Exception Message: Unable to create the workspace 'some-new-workspace' due to a mapping conflict. You may need to manually delete an old workspace. You can get a list of workspaces on a computer with the command 'tf workspaces /computer:%COMPUTERNAME%'. 
Details: The path C:\some-path is already mapped in workspace some-old-workspace. (type MappingConflictException) 

一您可以在第一个代码段中看到,我尝试删除工作空间为.Workspace.RemoveMapping(),但没有任何效果。工作区仍然存在于构建控制器上。我可以手动删除它们,但是当我删除构建定义时,它们确实应该被删除。 API中有其他一些DeleteWorkspace()机制吗?

更完整的代码要点是在这里:https://gist.github.com/grenade/cce374cb4e27e366bc5b

回答

1

事实证明,它是复杂的原因是,通过构建创建的各种工作区的所有者可能是一些其他用户(即生成代理下运行) 。 我发现了一种方法,依靠其在工作区的命名约定[build definition id]_[build agent id]_[workspace host]使用以前的版本定义ID做到这一点:

var workspaceNamePrefix = string.Concat(buildDefinition.Id, '_'); 
var workSpaces = VersionControlServer.QueryWorkspaces(null, null, null).Where(w => w.Name.StartsWith(workspaceNamePrefix)).ToArray(); 
for (var i = workSpaces.Count() - 1; i > -1; i--) 
{ 
    try 
    { 
     workSpaces[i].Delete(); 
     Console.WriteLine("delete workspace: {0}", workSpaces[i].Name); 
    } 
    catch (ResourceAccessException rae) 
    { 
     Console.ForegroundColor = ConsoleColor.Yellow; 
     Console.WriteLine(rae.Message); 
     Console.ForegroundColor = ConsoleColor.Red; 
     Console.WriteLine("workspace needs to be deleted by an administrator using the following command:"); 
     Console.ForegroundColor = ConsoleColor.Green; 
     Console.WriteLine("tf workspace /delete {0};{1}", workSpaces[i].Name, workSpaces[i].OwnerName); 
     Console.ResetColor(); 
    } 
} 

我已经更新要点:https://gist.github.com/grenade/cce374cb4e27e366bc5b