What kind of security context do custom TFS release tasks get? - tfs

TFS 2018u1. I have a custom Powershell task that calls TFS services via the VSSConnection object:
$VSS = Get-VssConnection -TaskContext $distributedTaskContext
$Client = $VSS.GetClient(...)
Question: what kind of security context does the task get? It's definitely not the agent account. To make sure, I've set up a temporary agent instance that runs as me, the TFS admin, and the custom task running on that agent doesn't have the full admin.
The underlying problem is - I'm trying to get the current agent record from a task, and the task only sees one pool, even though we have several. See this answer.

I'm trying to get the current agent record from a task, and the task only sees one pool, even though we have several.
There is a Agent pool security roles concept, for example with Administrator Role, you can:
Rregister or unregister agents from the pool and manage membership
for all pools, as well as view and create pools. They can also use the agent pool when creating an agent queue in a team project. The
system automatically adds the user that created the pool to the
Administrator role for that pool.
The default rights of a build agent running a release task should be the same as build service account. Please add your build service account to Agent pool security roles to Administrator from the collection-level admin context, Agent Pools page. Then try it again.
Another possibility you are lacking of vso.agentpools scope in your customize release task.
Grants the ability to view tasks, pools, queues, agents, and
currently running or recently completed jobs for agents
More details please take a look at Supported scopes

First off, the distributedTaskContext doesn't connect to TFS with NTLM, like Patrick Lu's answer suggests. It connects with Authorization:Bearer and a token. I've used the same token to invoke the /_api/_common/GetUserProfile endpoint, which returns the current user, and got back the following identity record:
{
"IdentityType": "user",
"FriendlyDisplayName": "Project Collection Build Service (TEAM FOUNDATION)",
"DisplayName": "Project Collection Build Service (TEAM FOUNDATION)",
"SubHeader": "Build\\233e4ccc-d129-4ba4-9c5b-ea82c7ae1d15",
"TeamFoundationId": "7a3195ee-870e-4151-ba58-1e522732086c",
"EntityId": "vss.ds.v1.ims.user.7a3195ee870e4151ba581e522732086c",
"Errors": [],
"Warnings": [],
"Domain": "Build",
"AccountName": "233e4ccc-d129-4ba4-9c5b-ea82c7ae1d15",
"IsWindowsUser": false,
"MailAddress": ""
}
It looks like some kind of artificial identity that TFS creates just for this purpose. Looking in the TFS database in the tbl_Identity table, there are numerous user records with names like that - one per collection, it seems, and also some that are project specific.
This user belongs to a server-level group called "Security Service Group" (and also to a collection level group with the same name). Those groups belong, respectively, to Team Foundation Valid Users and Project Collection Valid Users and nothing else.
At least on the collection level, the "Security Service Group" is visible and contains a lot of accounts.
All those "Build Service" users belong to the domain called "Build". A domain is not a security principal though, you can't grant rights to a domain.
Speaking of OAuth scopes. I've used the same token to invoke the homegrown "what are this token's scopes" page, and it turns out the distributedTaskContext token has exactly one - app_token. It's a valid scope that opens up all endpoints and all methods (see the dynamic scope list). The scopes parameter in the extension manifest has no bearing on that; it only affects the client-side contributions.
When it comes to pool visibility, though, the story is tricky. Seems like all the "Project Collection Build Service" accounts belong to Valid Users, but granting the Reader role on all pools to Valid Users doesn't open them up to the REST API in tasks. Granting Reader explicitly to "Project Collection Build Service" does. However, there are numerous accounts like this (one per collection, it seems) - and granting Reader only opens the pools up to release definitions in the collection where it resides. In order to let tasks in releases in all collections read the pools, you need to go through all collections and grant Reader to the "Project Collection Build Service" from each.

Related

Additional Identities Plugin - how to configure?

I'm struggling with duplicated users in my Jenkins and Not sending mail to unregistered user ... problem.
I installed the plugin as per this answer but cannot configure it properly by reading the plugin documentation.
My jenkins collects data from Active Directory and some users have duplicated entry, e.g.:
john.doe, john.doe#mycompany.com -> duplicated user which is detected by Jenkins
doej, john.doe#mycompany.com -> correct user which is used when logging in
Jenkins after collecting responsible people from git changes in job ends with
Not sending mail to unregistered user john.doe#mycompany.com
I tried adding additional identity to user doej by setting:
Identity: john.doe#mycompany.com
Realm: <empty>
but it doesn't work.
How should I configure correctly the Additional Identities Plugin?
Seems it's not possible to configure the additional identity plugin in Jenkins for merge the duplicate user
As Jenkins is missing a way to ensure users unicity(unique) since they are created from various sources: authentication method (LDAP in my case), code commits (Subversion, Mercurial, Git, ...).
Depending on the way the user is retrieved by Jenkins (from a commit on a given SCM or its authentication), multiple identities are created for the same real user.
As a consequence, some features are not fully or badly working (login, notifications, user's builds, continuous integration game, ...) and configuration of users is a pain as it must be done multiple times for each real user.
Still the required features are:
a merging features. Allow to merge multiple Jenkins users into a single account.
a user pattern per SCM. Allow to choose how to extract a username from a commit for each SCM and how to optionally match existing one instead of creating a new user.
an id pattern per notification type. Allow to define how to generate the default id used for notification from the user data (from his jenkins id, his name, his scm id, ...): for instance, his mail or his jabber id, ...
Reference: [JENKINS-10258] Allow users unicity - Jenkins Jira
Solution is Jenkins 1.480 but this is still in Vulnerabilities state and have bug as well.
Jenkins 1.480 introduces an extension point to resolve jenkins user "canonical" ID when searching for user in Database by id or full name. This plugin uses this extension point to let user configure external identities as user properties.
You can reach out to Jenkins community or Support team to know the status or when they will final release

Gerrit/NoteDB User Management

I am in the process of switching the LDAP backend that we use to authenticate access to Gerrit.
When a user logs in via LDAP, a local account is created within Gerrit. We are running version 2.15 of Gerrit, and therefore our local user accounts have migrated from the SQL DB into NoteDB.
The changes in our infrastructure, mean that once the LDAP backend has been switched, user logins will appear to Gerrit as new users and therefore a new local account will be generated. As a result we will need perform a number of administrative tasks to the existing local accounts before and after migration.
The REST API exposes some of the functionality that we need, however two key elements appear to be missing:
There appears to be no way to retrieve a list of all local accounts through the API (such that I could then iterate through to perform the administrative tasks I need to complete). The /accounts/ endpoint insists on a query filter being specified, which does not appear to include a way to simply specify 'all' or '*'. Instead I am having to try and think of a search filter that will reliably return all accounts - I haven't succeeded yet.
There appears to be no way to delete an account. Once the migration is complete, I need to remove the old accounts, but nothing is documented for the API or any other method to remove old accounts.
Has anybody found a solution to either of these tasks that they could share?
I came to the conclusion that the answers to my questions were:
('/a/' in the below examples is accessing the administrative endpoint and so basic Auth is required and the user having appropriate permissions)
Retrieving all accounts
There is no way to do this in a single query, however combining the results of:
GET /a/accounts?q=is:active&n=<number larger than the number of users>
GET /a/accounts?q=is:inactive&n=<number larger than the number of users>
will give effectively the same thing.
Deleting an account
Seems that this simply is not supported. The only option appears to be to set an account inactive:
DELETE /a/accounts/<account_id>/active

How to limit access of Project Owner

is there a way in Gerrit to either:
Limit access of Project Owner to read-only
Make certain API calls while not being a Project Owner. To be more specific, I'm interested in two calls:
GET projects/<project_name>/branches/<branch>/reflog/
and
GET projects/<project_name>/commits/<commit>
We have a few developer teams in the company, that could really benefit from Gerrit API, but we are trying to limit the access for the obvious reasons. So far we've created a group, "Devs A", where we added all the developers and then added that group to Project Owner. Then we blocked refs/meta/config privilege for "Devs A", but the group members are still able to edit/delete repositories and branches. Any idea on what else should we block?
Thanks
Why did you grant "Project Owner" permission to the "Devs A" group? If you want to let the group GET branches and commits endpoints you only need to grant "Read" permission to "refs/*".

Access denied when creating TFS Release definition

I'm trying to setup a release definition on TFS but I'm running into an access denied message:
I thought I should have this permission, since I am part of the "Agent Pool Administrator" group:
I noticed however, that my queue has no roles, and that I can't add one for some reason, which I suspect to be the related to the problem:
My question is how do I correctly configure the permissions? I've already googled a bunch but I still couldn't pinpoint what exact permission I'm missing.
[[Update]]
This is TFS 2015 update 3
Apparently, I am myself a project collection administrator already, but still don't have queue permissions and don't know, or can't see where to add myself as a queue admin.
The said queue was created by me, but indirectly, I created the agent pool with the auto-provision queues checked, and that created the queue, however, if I try to directly create a queue, I run into another "Access Denied" error
[Update]
Trying to run tfssecurity /collection:http://wada-pc:8080/tfs/DefaultCollection /g+ "[Agent Queues]\Agent Queue Administrators" "domain\account"
Leads me into Error: Access Denied: Eduardo Wada needs the following permission(s) to perform this action: Edit collection-level information
However, I should have that permisison:
Yes, your issue is related to the agent queue roles. An agent queue provides access to a pool of agents. Usually, there are two groups under the Roles:
Agent Queue Administrators: People in this group can register new agents in that pool, add users to the Agent Pool Service Accounts and add other administrators to the pool.
Agent Queue Users: For Team Foundation Server the service account you specify for the agent (commonly Network Service) is automatically added when you register the agent.
Try to use the account that create this agent queue to check whether it can see the roles, and add your account into the two groups.
Or, try to create a new agent queue to see whether you can see the roles, and deploy a new agent.

Jenkins Pipeline (aka Workfow) security with nodes

I want to create a Groovy script using Pipeline plugin in Jenkins handling the security for only some users can enter to the node.
This would be the example:
node('master') {
//code..... more code
}
node('production') {
//more code.....
}
I want to be able that only some users can run succesful the production node without using the input step that ask for only specific users/groups can approve it.
Is there a configuration option where I can configure the security of a specific Node about what users (or group) can execute scripts on it.
Note: I am using only Jenkisn 1.6 (not Cloudbees which it is with more complex security options)
Edited 04/20/2016 reflecting discussions in comment:
Update: Goal: Preventing unauthorized user from executing jobs on a selection of Jenkins node.
Update: The Job Restrictions Plugin referred by luka5z would be a promising fit for the goal, when using it in conjunction with Role Strategy Plugin.
Give Matrix-based security a try with this plugin Role Strategy Plugin. First, you need to set users/anonymous group global role to have a very minimal access. Then you can set slave roles that only allow users to use node name in staring in a pattern e.g QA_Slave*, and only a small group, say admin, have all permissions on all slaves, which implies Production.
Update: Role Strategy Plugin can prevent user from modifying policy applied to node, but would not protect node from running a job it was tagged to. [unauthorized slave assignment in job configuration] where Job Restrictions Plugin would independently apply restrictions on the node level, without go extreme and taking all job configuration access away.

Resources