在 Team Foundation Server 或 VSTS 中设置和检索团队管理员

Set and retrieve the Team Administrator in Team Foundation Server or VSTS

TFS 2012 及更高版本以及 VSTS 具有团队管理员的概念。我在整个 API 中寻找一种通过代码设置和检索值的简单方法,以便更轻松地提供这些设置,但找不到它。

通过 Web 的服务器对象模型进行反射 UI 给出了如何进行反射的提示,但它依赖于许多私有方法来完成此操作。尤其是计算Security Scope Token的部分更是隐藏魔法

我花了很多时间才找到 this old blogpost from 2013 which details how to do this,我似乎不是唯一被私有方法难倒的人。最后他们也结束了使用Reflection调用私有方法来获取token:

此功能现在可通过 TFS 团队工具获得:

检索

找到与团队匹配的安全组,用它来计算团队的令牌,得到属于该特殊安全命名空间的人:

public List<string> ListTeamAdministrators(string team, out string message)
{
    // Retrieve the default team.
    TeamFoundationTeam t = this.teamService.ReadTeam(this.projectInfo.Uri, team, null);
    List<string> lst = null;
    message = "";

    if (t == null)
    {
        message = "Team [" + team + "] not found";
    }
    else
    {
        // Get security namespace for the project collection.
        ISecurityService securityService = this.teamProjectCollection.GetService<ISecurityService>();
        SecurityNamespace securityNamespace =
            securityService.GetSecurityNamespace(FrameworkSecurity.IdentitiesNamespaceId);

        // Use reflection to retrieve a security token for the team.
        var token = GetTeamAdminstratorsToken(t);

        // Retrieve an ACL object for all the team members.
        var allMembers = t.GetMembers(this.teamProjectCollection, MembershipQuery.Expanded)
            .ToArray();
        AccessControlList acl =
            securityNamespace.QueryAccessControlList(token, allMembers.Select(m => m.Descriptor), true);

        // Retrieve the team administrator SIDs by querying the ACL entries.
        var entries = acl.AccessControlEntries;
        var admins = entries.Where(e => (e.Allow & 15) == 15).Select(e => e.Descriptor.Identifier);

        // Finally, retrieve the actual TeamFoundationIdentity objects from the SIDs.
        var adminIdentities = allMembers.Where(m => admins.Contains(m.Descriptor.Identifier));

        lst = adminIdentities.Select(i => i.DisplayName).ToList();
    }
    return lst;
}

private static string GetTeamAdminstratorsToken(TeamFoundationTeam team)
{
    return IdentityHelper.CreateSecurityToken(team.Identity);
}

设置

设置以类似的方式工作。获取令牌,然后将用户唯一标识符添加到访问控制列表:

IdentityDescriptor descriptor = GetMemberDescriptor(memberId);
securityNamespace.SetPermissions(token, descriptor, 15, 0, false);

删除

然后从列表中删除一个人当然很容易猜到;

IdentityDescriptor descriptor = GetMemberDescriptor(memberId);
securityNamespace.RemovePermissions(token, descriptor, 15);