GovernanceGroup Report

Below script will help in Downloading Governance group Report from ISC. This report Contains Governance Group Name, Description, Members, Owner Name and Members Count.

$CurrentDate = Get-Date
$CurrentDates = $CurrentDate.ToString(‘MM-dd-yyyy_hh-mm-ss’)

---- Config ----

$Tenant = “” # e.g., contoso
$TokenEndpoint = “https://$Tenant.api.my.com/oauth/token”
$ClientId = “”
$ClientSecret = “”

---- Token Request ----

$tokenBody = @{
grant_type = “client_credentials”
client_id = $ClientId
client_secret = $ClientSecret
}

$tokenResponse = Invoke-RestMethod -Method POST -Uri $TokenEndpoint
-Body $tokenBody `
-ContentType “application/x-www-form-urlencoded”

Validate we actually got a token

if (-not $tokenResponse.access_token) {
throw “Token request failed. Response: $($tokenResponse | ConvertTo-Json -Depth 5)”
}

$Token = $tokenResponse.access_token
$Headers = @{ Authorization = “Bearer $Token” }

Set your SailPoint API details

$baseUrl = “https://tenant.api.my.com
$token = “$Token”

Headers for authentication

$headers = @{
“Authorization” = “Bearer $token”
“Content-Type” = “application/json”
}

================= CONFIG =================

$baseUrl = “https://tenant.api.my.com
$headers = @{ Authorization = “Bearer $Token” }
$outputFile = “C:\Users\Documents\GovGroups-$CurrentDates.csv”

=========================================

Pagination settings

$limit = 250
$offset = 0
$hasMoreGroups = $true
$exportData = @()
$rowNumber = 0 # <— Added row counter

Write-Host “Fetching governance groups…”

while ($hasMoreGroups) {
$groupsUrl = “$baseUrl/beta/workgroups?limit=$limit&offset=$offset”
$groupsResponse = Invoke-RestMethod -Uri $groupsUrl -Headers $headers -Method Get -ErrorAction Stop

# Normalize response to array
$groups = @()
if ($null -ne $groupsResponse) {
    if ($groupsResponse -is [System.Collections.IEnumerable]) {
        $groups = @($groupsResponse)
    } else {
        $groups = @($groupsResponse)
    }
}

if ($groups.Count -eq 0) {
    $hasMoreGroups = $false
    break
}

foreach ($group in $groups) {

    # Increment row number
    $rowNumber++

    $groupId   = $group.id
    $groupName = $group.name
    $groupDesc = $group.description

    # Detect owner (adjust field if API returns differently)
    $ownerName = $group.owner.name

    Write-Host "[$rowNumber] Processing group: $groupName ($groupId) | Owner: $ownerName"

    # Collect all members across pages for this group
    $memberOffset    = 0
    $hasMoreMembers  = $true
    $memberNames     = New-Object System.Collections.Generic.List[string]
    $memberEmails    = New-Object System.Collections.Generic.List[string]
    $memberIds       = New-Object System.Collections.Generic.List[string]

    while ($hasMoreMembers) {
        $membersUrl = "$baseUrl/beta/workgroups/$groupId/members?limit=$limit&offset=$memberOffset"
        try {
            $membersResponse = Invoke-RestMethod -Uri $membersUrl -Headers $headers -Method Get -ErrorAction Stop

            # Normalize
            $members = @()
            if ($null -ne $membersResponse) {
                if ($membersResponse -is [System.Collections.IEnumerable]) {
                    $members = @($membersResponse)
                } else {
                    $members = @($membersResponse)
                }
            }

            if ($members.Count -eq 0) {
                $hasMoreMembers = $false
                break
            }

            foreach ($member in $members) {
                if ($member.name)  { $memberNames.Add([string]$member.name)  | Out-Null }
                if ($member.email) { $memberEmails.Add([string]$member.email) | Out-Null }
                if ($member.id)    { $memberIds.Add([string]$member.id)       | Out-Null }
            }

            # Advance pagination
            $memberOffset += $limit

            if ($members.Count -lt $limit) {
                $hasMoreMembers = $false
            }
        }
        catch {
            Write-Warning "Failed to get members for group '$groupName' ($groupId): $($_.Exception.Message)"
            $hasMoreMembers = $false
        }
    }

    # Join all member values
    $namesJoined  = ($memberNames.ToArray()  -join '; ')
    $emailsJoined = ($memberEmails.ToArray() -join '; ')

    # Add export object
    $exportData += [PSCustomObject]@{
        GroupName        = $groupName
        GroupDescription = $groupDesc
        OwnerName        = $ownerName
        MemberNames      = $namesJoined
        MemberEmails     = $emailsJoined
        MemberCount      = $memberIds.Count
    }
}

# Advance group pagination
$offset += $limit

if ($groups.Count -lt $limit) {
    $hasMoreGroups = $false
}

}

– Export to CSV –

$exportData | Export-Csv -Path $outputFile -NoTypeInformation -Encoding UTF8
Write-Host “Report generated: $outputFile”
$htmlTable = “This email includes the Governance Group Members report from the SailPoint, listing those designated as approvers for entitlements.”

$emailParams = @{
To = “KaranMarwah@my.com”
From = “KaranMarwah@my.com”
Subject = “GovernanceGroup Membership Report from SailPoint”
Body = $htmlTable
Attachment = “C:\Users\Documents\GovGroups-$CurrentDates.csv”
BodyAsHtml = $true
SmtpServer = “yourmail.corp”

}


# Send the email

Send-MailMessage @emailParams

I Hope this script will help everyone who are looking for a way to download Governance Groups Report from ISC.

Hi @karan_1984 ,

Thanks for contribution to community
May be this post should go under
Blog Post ,knowledgebase section that would be great addition for community and you

Thanks
Avinash Mulpuru

2 Likes

Hey @karan_1984 ,

This is nice, thanks for sharing this.

1 Like