SHELL/5.3.4.ps1
|
$CheckId = "5.3.4" $Title = "Ensure approval is required for Global Administrator role activation" $Level = "L1" $BenchmarkType = "Automated" $RoleDefinitionId = "62e90394-69f5-4237-9190-012177145e10" $RoleDisplayName = "Global Administrator" function Get-PropValue { param( [AllowNull()]$Object, [string]$Name ) if ($null -eq $Object) { return $null } if ($Object -is [hashtable]) { foreach ($Key in $Object.Keys) { if ([string]$Key -ieq $Name) { return $Object[$Key] } } } if ($Object.PSObject -and $Object.PSObject.Properties) { foreach ($Property in $Object.PSObject.Properties) { if ([string]$Property.Name -ieq $Name) { return $Property.Value } } } return $null } try { $Filter = [uri]::EscapeDataString("scopeType eq 'DirectoryRole' and scopeId eq '/' and roleDefinitionId eq '$RoleDefinitionId'") $AssignmentsUri = "https://graph.microsoft.com/beta/policies/roleManagementPolicyAssignments?`$filter=$Filter" $AssignmentsResponse = Invoke-MgGraphRequest -Uri $AssignmentsUri -Method GET -ErrorAction Stop $Assignments = @(Get-PropValue -Object $AssignmentsResponse -Name "value") if ($Assignments.Count -eq 0) { [pscustomobject]@{ CheckId = $CheckId Title = $Title Level = $Level BenchmarkType = $BenchmarkType Status = "FAIL" Pass = $false Evidence = [pscustomobject]@{ RoleDefinitionId = $RoleDefinitionId RoleDisplayName = $RoleDisplayName RoleManagementPolicyAssignmentCount = 0 SourceDocument = "CIS_Microsoft_365_Foundations_Benchmark_v6.0.1" } Error = "No role management policy assignment was found for Global Administrator." Timestamp = Get-Date } return } $Assignment = $Assignments | Select-Object -First 1 $PolicyId = [string](Get-PropValue -Object $Assignment -Name "policyId") if ([string]::IsNullOrWhiteSpace($PolicyId)) { throw "Role management policy assignment does not include a policyId." } $RulesUri = "https://graph.microsoft.com/beta/policies/roleManagementPolicies/$PolicyId/rules" $RulesResponse = Invoke-MgGraphRequest -Uri $RulesUri -Method GET -ErrorAction Stop $Rules = @(Get-PropValue -Object $RulesResponse -Name "value") $ApprovalRules = @($Rules | Where-Object { ([string](Get-PropValue -Object $_ -Name "@odata.type")) -match '(?i)approval' -and (([string](Get-PropValue -Object (Get-PropValue -Object $_ -Name "target") -Name "caller")) -match '^(?i:enduser)$') }) $RuleEvaluations = foreach ($Rule in $ApprovalRules) { $Target = Get-PropValue -Object $Rule -Name "target" $Setting = Get-PropValue -Object $Rule -Name "setting" $Stages = @(Get-PropValue -Object $Setting -Name "approvalStages") $PrimaryApprovers = @() foreach ($Stage in $Stages) { $PrimaryApprovers += @(Get-PropValue -Object $Stage -Name "primaryApprovers") } $ApproverCount = @($PrimaryApprovers | Where-Object { $_ }).Count $IsApprovalRequired = [bool](Get-PropValue -Object $Setting -Name "isApprovalRequired") $Operations = @(Get-PropValue -Object $Target -Name "operations") [pscustomobject]@{ RuleId = [string](Get-PropValue -Object $Rule -Name "id") Caller = [string](Get-PropValue -Object $Target -Name "caller") Operations = $Operations IsApprovalRequired = $IsApprovalRequired ApproverCount = $ApproverCount IsCompliant = $IsApprovalRequired -and ($ApproverCount -ge 2) } } $CompliantRules = @($RuleEvaluations | Where-Object { $_.IsCompliant }) $Pass = $CompliantRules.Count -gt 0 $Status = if ($Pass) { "PASS" } else { "FAIL" } [pscustomobject]@{ CheckId = $CheckId Title = $Title Level = $Level BenchmarkType = $BenchmarkType Status = $Status Pass = $Pass Evidence = [pscustomobject]@{ RoleDefinitionId = $RoleDefinitionId RoleDisplayName = $RoleDisplayName PolicyId = $PolicyId RoleManagementPolicyAssignmentCount = $Assignments.Count ApprovalRuleCount = $ApprovalRules.Count RuleEvaluations = @($RuleEvaluations) SourceDocument = "CIS_Microsoft_365_Foundations_Benchmark_v6.0.1" } Error = if ($Pass) { $null } else { "No Global Administrator activation approval rule was found with approval required and at least two approvers." } Timestamp = Get-Date } } catch { [pscustomobject]@{ CheckId = $CheckId Title = $Title Level = $Level BenchmarkType = $BenchmarkType Status = "ERROR" Pass = $null Evidence = [pscustomobject]@{ RoleDefinitionId = $RoleDefinitionId RoleDisplayName = $RoleDisplayName SourceDocument = "CIS_Microsoft_365_Foundations_Benchmark_v6.0.1" } Error = $_.Exception.Message Timestamp = Get-Date } } |