functions/Copy-HydrationManagementGroupHierarchy.ps1

function Copy-HydrationManagementGroupHierarchy {
<#
.SYNOPSIS
    This function copies a management group hierarchy.
 
.DESCRIPTION
    The Copy-HydrationManagementGroupHierarchy function takes a source group name, a destination parent group name, and a prefix.
    It then copies the management group hierarchy from the source to the destination.
 
.PARAMETER SourceGroupName
    The name of the source group from which the hierarchy will be copied.
 
.PARAMETER DestinationParentGroupName
    The name of the destination parent group where the hierarchy will be copied to.
 
.PARAMETER Prefix
    The prefix to be used in the naming of the copied hierarchy.
 
.EXAMPLE
    Copy-HydrationManagementGroupHierarchy -SourceGroupName "IntermediateRoot" -DestinationParentGroupName "11111111-1111-1111-1111-111111111111" -Prefix "EpacDev-"
 
    This will copy the hierarchy from "IntermediateRoot" to the tenant root "11111111-1111-1111-1111-111111111111", using "EpacDev-InternmediateRoot" as the new Intermediate Root for this environment.
     
.LINK
    https://aka.ms/epac
    https://github.com/Azure/enterprise-azure-policy-as-code/tree/main/Docs/start-hydration-kit.md
.NOTES
    While this is most commonly used to generate development environment for EPAC to use in its CI/CD testing, it is a general purpose tool that can be used to rapidly replicate any hierarchy to generate a new parallel hierarchical structure.
#>


[CmdletBinding()]
param (
    [Parameter(Mandatory = $true)]
    [string]
    $SourceGroupName,
    [Parameter(Mandatory = $true)]
    [string]
    $DestinationParentGroupName,
    [Parameter(Mandatory = $false)]
    [string]
    $Prefix,
    [Parameter(Mandatory = $false)]
    [string]
    $Suffix
)
$InformationPreference = "Continue"
if (!($Suffix) -and !($Prefix)) {
    Write-Error "You must modify the name with either a Suffix, a Prefix, or both in order to replicate within the current tenant without naming collision errors."
}
try {
    $null = $destParent = Get-AzManagementGroupRestMethod -GroupID $DestinationParentGroupName -ErrorAction SilentlyContinue
}
catch {
    Write-Information $_.Exception.Message
    Write-Error "Cannot continue, a valid `$DestinationParentGroupName must be specified to tell the cmdlet where to anchor your new hierarchy."
    return
}
Write-Information "Beginning Duplication to $DestinationParentGroupName..."
$hierarchy = Get-AzManagementGroupRestMethod -GroupID $SourceGroupName -Expand  -Recurse 
Write-Information " Creating $(-join($Prefix,$hierarchy.Name,$Suffix))..."
# Error action included because timeouts happen frequently, but mean nothing. Rather than have responses cause concern, we simply suppress the error.
$createdMg = New-AzManagementGroup -GroupName $( -join ($Prefix, $hierarchy.Name, $Suffix)) -DisplayName $( -join ($Prefix, $hierarchy.properties.displayName, $Suffix)) -ParentId $destParent.Id -ErrorAction SilentlyContinue
New-HydrationManagementGroupChildren -Hierarchy $hierarchy -Prefix $Prefix -Suffix $Suffix
}