test plan azure devops test

Shyam Kumar 846 Reputation points
2025-05-17T11:58:40.9+00:00

test 123 456test 123 456test 123 456test 123 456test 123 456test 123 456test 123 456

Azure DevOps
{count} votes

1 answer

Sort by: Most helpful
  1. Sina Salam 22,031 Reputation points Volunteer Moderator
    2025-05-19T12:29:54.5666667+00:00

    Hello Diptesh Kumar,

    Welcome to the Microsoft Q&A and thank you for posting your questions here.

    I understand that you would like to grant the "Manage Delivery Plans" permission across all projects in an Azure DevOps organization for only two specific groups by using PowerShell with Azure DevOps CLI or REST API or Direct REST API calls via scripting.

    To grant the "Manage Delivery Plans" permission across all projects in an Azure DevOps organization for only two specific groups, you can use either:

    • PowerShell with Azure DevOps CLI or REST API, or
    • Direct REST API calls via scripting.

    The steps below will guide you and it is PowerShell with Azure DevOps REST API:

    1. Prerequisites:
      • Azure DevOps PAT (Personal Access Token) with Organization-level permissions.
      • PowerShell installed.
      • The two Azure DevOps group descriptors (not just names).
      • Organization URL (e.g., https://dev.azure.com/your-org).
    2. Based on the official Microsoft documentation - https://learn.microsoft.com/en-us/azure/devops/organizations/security/namespace-reference?view=azure-devops - the "Manage Delivery Plans" permission is part of the Delivery Plans security namespace, which is object-level and managed per plan or per project. However, the exact bitmask value for this permission is not explicitly documented. To retrieve the correct permission bitmask, you can use the Security Namespaces API:
         GET https://dev.azure.com/{organization}/_apis/securitynamespaces/33344d9c-fc72-4d6f-aba5-fa317101a7e9?api-version=7.1-preview.1
      
      This will return a list of permissions and their corresponding bitmask values for the Delivery Plans namespace.
    3. PowerShell Script:
         # ============================
         # Configuration
         # ============================
         $organization = "DevOrgName"
         $pat = "PATForAzAdOps"  # Replace with your actual PAT
         $groupNames = @("GP1name", "GP2Name")
         $securityNamespaceId = "33344d9c-fc72-4d6f-aba5-fa317101a7e9"
         # Base64-encoded PAT for authentication
         $base64AuthInfo = [Convert]::ToBase64String([Text.Encoding]::ASCII.GetBytes(":$pat"))
         # ============================
         # Helper: Get Group Descriptor
         # ============================
         function Get-GroupDescriptor {
             param ([string]$groupName)
             $url = "https://vssps.dev.azure.com/$organization/_apis/graph/groups?api-version=7.1-preview.1"
             $response = Invoke-RestMethod -Uri $url -Headers @{Authorization=("Basic $base64AuthInfo")} -Method Get
             $group = $response.value | Where-Object { $_.displayName -eq $groupName }
             if ($group) { return $group.descriptor }
             else { throw "Group '$groupName' not found." }
         }
         # ============================
         # Step 1: Get All Projects
         # ============================
         $projectsUrl = "https://dev.azure.com/$organization/_apis/projects?api-version=7.1-preview.4"
         try {
             $projects = Invoke-RestMethod -Uri $projectsUrl -Headers @{Authorization=("Basic $base64AuthInfo")} -Method Get
         } catch {
             Write-Error "Failed to retrieve projects: $_"
             exit
         }
         # ============================
         # Step 2: Get Group Descriptors
         # ============================
         $groupDescriptors = @{}
         foreach ($groupName in $groupNames) {
             try {
                 $descriptor = Get-GroupDescriptor -groupName $groupName
                 $groupDescriptors[$groupName] = $descriptor
             } catch {
                 Write-Warning $_
             }
         }
         # ============================
         # Step 3: Apply Permissions
         # ============================
         foreach ($project in $projects.value) {
             $projectId = $project.id
             $token = "vstfs:///Classification/TeamProject/$projectId"
             foreach ($groupName in $groupDescriptors.Keys) {
                 $descriptor = $groupDescriptors[$groupName]
                 $body = @{
                     accessControlEntries = @(@{
                         descriptor = $descriptor
                         allow = 16  # Placeholder: Replace with actual bitmask after confirmation
                         deny = 0
                         token = $token
                     })
                 } | ConvertTo-Json -Depth 10
                 $url = "https://dev.azure.com/$organization/_apis/accesscontrolentries/$securityNamespaceId?api-version=7.1-preview.1"
                 try {
                     $response = Invoke-RestMethod -Uri $url -Headers @{
                         Authorization = "Basic $base64AuthInfo"
                         "Content-Type" = "application/json"
                     } -Method Post -Body $body
                     Write-Host "Permission applied for '$groupName' on project '$($project.name)'" -ForegroundColor Green
                 } catch {
                     Write-Warning "Failed to apply permission for '$groupName' on project '$($project.name)': $_"
                 }
             }
         }
      
      This script includes:
      • Bitmask retrieval placeholder
      • Group descriptor resolution
      • Eror handling
      • Logging
      • Idempotency check
      • NOTICE: You have to change bitmask and the following $organization = "DevOrgName" $pat = "PATForAzAdOps" # Replace with your actual PAT $groupNames = @("GP1name", "GP2Name") Replace with actual Group name.

    I hope this is helpful! Do not hesitate to let me know if you have any other questions or clarifications.


    Please don't forget to close up the thread here by upvoting and accept it as an answer if it is helpful.


Your answer

Answers can be marked as Accepted Answers by the question author, which helps users to know the answer solved the author's problem.