From 5f5b220fd4f2dd55786b74b0fa1dce7bb6821c9b Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Sun, 26 May 2024 13:10:06 -0500 Subject: [PATCH 01/67] add: Array list to store the results of the audit --- helpers/Build-Help.ps1 | 4 ++-- source/Public/Invoke-M365SecurityAudit.ps1 | 6 +++--- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/helpers/Build-Help.ps1 b/helpers/Build-Help.ps1 index a2d483b..60067be 100644 --- a/helpers/Build-Help.ps1 +++ b/helpers/Build-Help.ps1 @@ -3,8 +3,8 @@ Import-Module .\output\module\M365FoundationsCISReport\*\*.psd1 .\helpers\psDoc-master\src\psDoc.ps1 -moduleName M365FoundationsCISReport -outputDir ".\" -template ".\helpers\psDoc-master\src\out-markdown-template.ps1" -fileName ".\README.md" -<# - $ver = "v0.1.1" +#<# + $ver = "v0.1.2" git checkout main git pull origin main git tag -a $ver -m "Release version $ver Bugfix Update" diff --git a/source/Public/Invoke-M365SecurityAudit.ps1 b/source/Public/Invoke-M365SecurityAudit.ps1 index cff7e59..f2059c0 100644 --- a/source/Public/Invoke-M365SecurityAudit.ps1 +++ b/source/Public/Invoke-M365SecurityAudit.ps1 @@ -209,7 +209,7 @@ function Invoke-M365SecurityAudit { } # End Begin Process { - $allAuditResults = @() # Initialize a collection to hold all results + $allAuditResults = [System.Collections.ArrayList]::new() #@() # Initialize a collection to hold all results # Dynamically dot-source the test scripts $testsFolderPath = Join-Path -Path $PSScriptRoot -ChildPath "tests" @@ -242,7 +242,7 @@ function Invoke-M365SecurityAudit { Write-Host "Running $functionName..." $result = & $functionName @paramList # Assuming each function returns an array of CISAuditResult or a single CISAuditResult - $allAuditResults += $result + [void]($allAuditResults.add($Result)) } } } @@ -253,7 +253,7 @@ function Invoke-M365SecurityAudit { Disconnect-M365Suite } # Return all collected audit results - return $allAuditResults + return $allAuditResults.ToArray() # Check if the Disconnect switch is present } } \ No newline at end of file From 05dbf4661ccf7a171da325d1c2f313e7c94911f2 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Sun, 26 May 2024 14:36:27 -0500 Subject: [PATCH 02/67] add: Arraylist tests and helper Template --- .../CIS 365 v3.0.0 Controls/Test-Template.ps1 | 98 +++++++++++++++++++ source/Public/Get-AdminRoleUserLicense.ps1 | 30 +++--- 2 files changed, 115 insertions(+), 13 deletions(-) create mode 100644 helpers/CIS 365 v3.0.0 Controls/Test-Template.ps1 diff --git a/helpers/CIS 365 v3.0.0 Controls/Test-Template.ps1 b/helpers/CIS 365 v3.0.0 Controls/Test-Template.ps1 new file mode 100644 index 0000000..5cb73e1 --- /dev/null +++ b/helpers/CIS 365 v3.0.0 Controls/Test-Template.ps1 @@ -0,0 +1,98 @@ +function Test-Template { + [CmdletBinding()] + param ( + # Parameters can be added if needed + ) + + begin { + # Initialization code, if needed + # Load necessary scripts, define variables, etc. + } + + process { + # Fetch relevant data + # Example: $data = Get-SomeData + + # Process the data to evaluate compliance + # Example: $compliantItems = $data | Where-Object { $_.Property -eq 'ExpectedValue' } + # Example: $nonCompliantItems = $data | Where-Object { $_.Property -ne 'ExpectedValue' } + + # Prepare failure reasons and details for non-compliant items + $failureReasons = $nonCompliantItems | ForEach-Object { + # Example: "Item: $($_.Name) - Reason: Missing expected value" + } + $failureReasons = $failureReasons -join "`n" + + # Prepare details for compliant items + $compliantDetails = $compliantItems | ForEach-Object { + # Example: "Item: $($_.Name) - Value: $($_.Property)" + } + $compliantDetails = $compliantDetails -join "`n" + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($nonCompliantItems) { 'Fail' } else { 'Pass' } + $auditResult.ELevel = 'E3' # Modify as needed + $auditResult.ProfileLevel = 'L1' # Modify as needed + $auditResult.Rec = '1.1.1' # Modify as needed + $auditResult.RecDescription = "Description of the recommendation" # Modify as needed + $auditResult.CISControlVer = 'v8' # Modify as needed + $auditResult.CISControl = "5.4" # Modify as needed + $auditResult.CISDescription = "Description of the CIS control" # Modify as needed + $auditResult.IG1 = $true # Modify as needed + $auditResult.IG2 = $true # Modify as needed + $auditResult.IG3 = $true # Modify as needed + $auditResult.Result = $nonCompliantItems.Count -eq 0 + $auditResult.Details = if ($nonCompliantItems) { + "Non-Compliant Items: $($nonCompliantItems.Count)`nDetails:`n" + ($nonCompliantItems | ForEach-Object { $_.Details } -join "`n") + } else { + "Compliant Items: $($compliantItems.Count)`nDetails:`n$compliantDetails" + } + $auditResult.FailureReason = if ($nonCompliantItems) { + "Non-compliant items:`n$failureReasons" + } else { + "N/A" + } + + # Example output object for a pass result + # Status : Pass + # ELevel : E3 + # ProfileLevel : L2 + # Rec : 8.1.1 + # RecDescription : Ensure external file sharing in Teams is enabled for only approved cloud storage services + # CISControlVer : v8 + # CISControl : 3.3 + # CISDescription : Configure Data Access Control Lists + # IG1 : True + # IG2 : True + # IG3 : True + # Result : True + # Details : Compliant Items: 5 + # Item: Team1 - Storage: OneDrive + # Item: Team2 - Storage: SharePoint + # FailureReason : N/A + + # Example output object for a fail result + # Status : Fail + # ELevel : E3 + # ProfileLevel : L2 + # Rec : 8.1.1 + # RecDescription : Ensure external file sharing in Teams is enabled for only approved cloud storage services + # CISControlVer : v8 + # CISControl : 3.3 + # CISDescription : Configure Data Access Control Lists + # IG1 : True + # IG2 : True + # IG3 : True + # Result : False + # Details : Non-Compliant Items: 2 + # Item: Team3 - Storage: Dropbox (Unapproved) + # Item: Team4 - Storage: Google Drive (Unapproved) + # FailureReason : Non-compliant items:`nUsername | Roles | HybridStatus | Missing Licence + } + + end { + # Return the audit result + return $auditResult + } +} diff --git a/source/Public/Get-AdminRoleUserLicense.ps1 b/source/Public/Get-AdminRoleUserLicense.ps1 index 6c307ee..fa2a49a 100644 --- a/source/Public/Get-AdminRoleUserLicense.ps1 +++ b/source/Public/Get-AdminRoleUserLicense.ps1 @@ -36,8 +36,8 @@ function Get-AdminRoleUserLicense { Connect-MgGraph -Scopes "Directory.Read.All", "Domain.Read.All", "Policy.Read.All", "Organization.Read.All" -NoWelcome } - $adminRoleUsers = @() - $userIds = @() + $adminRoleUsers = [System.Collections.ArrayList]::new() + $userIds = [System.Collections.ArrayList]::new() } Process { @@ -50,24 +50,28 @@ function Get-AdminRoleUserLicense { $userDetails = Get-MgUser -UserId $user.PrincipalId -Property "DisplayName, UserPrincipalName, Id, onPremisesSyncEnabled" -ErrorAction SilentlyContinue if ($userDetails) { - $userIds += $user.PrincipalId - $adminRoleUsers += [PSCustomObject]@{ - RoleName = $role.DisplayName - UserName = $userDetails.DisplayName - UserPrincipalName = $userDetails.UserPrincipalName - UserId = $userDetails.Id - HybridUser = $userDetails.onPremisesSyncEnabled - Licenses = $null # Initialize as $null - } + [void]($userIds.Add($user.PrincipalId)) + [void]( + $adminRoleUsers.Add( + [PSCustomObject]@{ + RoleName = $role.DisplayName + UserName = $userDetails.DisplayName + UserPrincipalName = $userDetails.UserPrincipalName + UserId = $userDetails.Id + HybridUser = $userDetails.onPremisesSyncEnabled + Licenses = $null # Initialize as $null + } + ) + ) } } } - foreach ($userId in $userIds | Select-Object -Unique) { + foreach ($userId in $userIds.ToArray() | Select-Object -Unique) { $licenses = Get-MgUserLicenseDetail -UserId $userId -ErrorAction SilentlyContinue if ($licenses) { $licenseList = ($licenses.SkuPartNumber -join '|') - $adminRoleUsers | Where-Object { $_.UserId -eq $userId } | ForEach-Object { + $adminRoleUsers.ToArray() | Where-Object { $_.UserId -eq $userId } | ForEach-Object { $_.Licenses = $licenseList } } From 37fbf2b32a63ec21d8fe7d53101d256dba5bcc9d Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Sun, 26 May 2024 15:33:57 -0500 Subject: [PATCH 03/67] add: Correction to test-template --- .../CIS 365 v3.0.0 Controls/Test-Template.ps1 | 27 +++++++++---------- 1 file changed, 13 insertions(+), 14 deletions(-) diff --git a/helpers/CIS 365 v3.0.0 Controls/Test-Template.ps1 b/helpers/CIS 365 v3.0.0 Controls/Test-Template.ps1 index 5cb73e1..5f49dca 100644 --- a/helpers/CIS 365 v3.0.0 Controls/Test-Template.ps1 +++ b/helpers/CIS 365 v3.0.0 Controls/Test-Template.ps1 @@ -17,17 +17,24 @@ function Test-Template { # Example: $compliantItems = $data | Where-Object { $_.Property -eq 'ExpectedValue' } # Example: $nonCompliantItems = $data | Where-Object { $_.Property -ne 'ExpectedValue' } - # Prepare failure reasons and details for non-compliant items + # Prepare failure reasons for non-compliant items $failureReasons = $nonCompliantItems | ForEach-Object { # Example: "Item: $($_.Name) - Reason: Missing expected value" } $failureReasons = $failureReasons -join "`n" - # Prepare details for compliant items - $compliantDetails = $compliantItems | ForEach-Object { - # Example: "Item: $($_.Name) - Value: $($_.Property)" + # Prepare details for non-compliant items + $nonCompliantDetails = $nonCompliantItems | ForEach-Object { + # Example: "$($_.Name) - Value: $($_.Property)" + } + $nonCompliantDetails = $nonCompliantDetails -join "`n" + + # Prepare details based on compliance + $details = if ($nonCompliantItems) { + "Non-Compliant Items: $($nonCompliantItems.Count)`nDetails:`n$nonCompliantDetails" + } else { + "Compliant Items: $($compliantItems.Count)" } - $compliantDetails = $compliantDetails -join "`n" # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() @@ -43,11 +50,7 @@ function Test-Template { $auditResult.IG2 = $true # Modify as needed $auditResult.IG3 = $true # Modify as needed $auditResult.Result = $nonCompliantItems.Count -eq 0 - $auditResult.Details = if ($nonCompliantItems) { - "Non-Compliant Items: $($nonCompliantItems.Count)`nDetails:`n" + ($nonCompliantItems | ForEach-Object { $_.Details } -join "`n") - } else { - "Compliant Items: $($compliantItems.Count)`nDetails:`n$compliantDetails" - } + $auditResult.Details = $details $auditResult.FailureReason = if ($nonCompliantItems) { "Non-compliant items:`n$failureReasons" } else { @@ -68,8 +71,6 @@ function Test-Template { # IG3 : True # Result : True # Details : Compliant Items: 5 - # Item: Team1 - Storage: OneDrive - # Item: Team2 - Storage: SharePoint # FailureReason : N/A # Example output object for a fail result @@ -86,8 +87,6 @@ function Test-Template { # IG3 : True # Result : False # Details : Non-Compliant Items: 2 - # Item: Team3 - Storage: Dropbox (Unapproved) - # Item: Team4 - Storage: Google Drive (Unapproved) # FailureReason : Non-compliant items:`nUsername | Roles | HybridStatus | Missing Licence } From 4bc75db1dc34173b7ced14045b15d91b409947f2 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Sun, 26 May 2024 15:34:16 -0500 Subject: [PATCH 04/67] add: Details to pass. --- source/tests/Test-AdministrativeAccountCompliance.ps1 | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/source/tests/Test-AdministrativeAccountCompliance.ps1 b/source/tests/Test-AdministrativeAccountCompliance.ps1 index 3273774..6bda22d 100644 --- a/source/tests/Test-AdministrativeAccountCompliance.ps1 +++ b/source/tests/Test-AdministrativeAccountCompliance.ps1 @@ -50,6 +50,12 @@ function Test-AdministrativeAccountCompliance { "$($_.UserName)|$($_.Roles)|$accountType|Missing: $($missingLicenses -join ',')" } $failureReasons = $failureReasons -join "`n" + $details = if ($nonCompliantUsers) { + "Non-Compliant Accounts: $($nonCompliantUsers.Count)`nDetails:`n" + ($nonCompliantUsers | ForEach-Object { $_.UserName }) -join "`n" + } + else { + "Compliant Accounts: $($uniqueAdminRoleUsers.Count)" + } $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($nonCompliantUsers) { 'Fail' } else { 'Pass' } @@ -64,7 +70,7 @@ function Test-AdministrativeAccountCompliance { $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.Result = $nonCompliantUsers.Count -eq 0 - $auditResult.Details = "Compliant Accounts: $($uniqueAdminRoleUsers.Count - $nonCompliantUsers.Count); Non-Compliant Accounts: $($nonCompliantUsers.Count)" + $auditResult.Details = $Details $auditResult.FailureReason = if ($nonCompliantUsers) { "Non-compliant accounts: `nUsername | Roles | HybridStatus | Missing Licence`n$failureReasons" } else { "N/A" } } From 71736bfb438b8b21c7d088daa18b7e6e11be55b0 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Sun, 26 May 2024 15:53:57 -0500 Subject: [PATCH 05/67] fix: AntiPhishingPolicy aligned with template --- source/tests/Test-AntiPhishingPolicy.ps1 | 71 ++++++++++++++++-------- 1 file changed, 47 insertions(+), 24 deletions(-) diff --git a/source/tests/Test-AntiPhishingPolicy.ps1 b/source/tests/Test-AntiPhishingPolicy.ps1 index de8f0ed..449f4c8 100644 --- a/source/tests/Test-AntiPhishingPolicy.ps1 +++ b/source/tests/Test-AntiPhishingPolicy.ps1 @@ -5,13 +5,14 @@ function Test-AntiPhishingPolicy { ) begin { - # Dot source the class script + # Dot source the class script if necessary - $auditResults = @() + # Initialization code, if needed + #$auditResults = @() } process { - # 2.1.7 Ensure that an anti-phishing policy has been created + # 2.1.7 Ensure that an anti-phishing policy has been created # Retrieve and validate the anti-phishing policies $antiPhishPolicies = Get-AntiPhishPolicy @@ -24,37 +25,59 @@ function Test-AntiPhishingPolicy { } # Check if there is at least one policy that meets the requirements - $isCompliant = $validatedPolicies.Count -gt 0 + $nonCompliantItems = $antiPhishPolicies | Where-Object { + $_.Enabled -ne $true -or + $_.PhishThresholdLevel -lt 2 -or + $_.EnableMailboxIntelligenceProtection -ne $true -or + $_.EnableMailboxIntelligence -ne $true -or + $_.EnableSpoofIntelligence -ne $true + } + $compliantItems = $validatedPolicies + $isCompliant = $compliantItems.Count -gt 0 - # Prepare failure details if policies are not compliant - $failureDetails = if (-not $isCompliant) { - "No anti-phishing policy is fully compliant with CIS benchmark requirements." + # Prepare failure reasons for non-compliant items + $nonCompliantNames = $nonCompliantItems | ForEach-Object { $_.Name } + $failureReasons = if ($nonCompliantNames.Count -gt 0) { + "Reason: Does not meet one or more compliance criteria.`nNon-compliant Policies:`n" + ($nonCompliantNames -join "`n") } else { - "Compliant Anti-Phish Policy Names: " + ($validatedPolicies.Name -join ', ') + "N/A" } - # Create an instance of CISAuditResult and populate it + # Prepare details for non-compliant items + $nonCompliantDetails = $nonCompliantItems | ForEach-Object { + "Policy: $($_.Name)" + } + $nonCompliantDetails = $nonCompliantDetails -join "`n" + + # Prepare details based on compliance + $details = if ($nonCompliantItems) { + "Non-Compliant Items: $($nonCompliantItems.Count)`nDetails:`n$nonCompliantDetails" + } + else { + "Compliant Items: $($compliantItems.Count)" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($isCompliant) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E5" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "2.1.7" - $auditResult.RecDescription = "Ensure that an anti-phishing policy has been created" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "9.7" - $auditResult.CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $true - $auditResult.Result = $isCompliant - $auditResult.Details = $failureDetails - $auditResult.FailureReason = if (-not $isCompliant) { "Anti-phishing policies do not meet CIS benchmark requirements." } else { "N/A" } + $auditResult.ELevel = 'E5' # Modify as needed + $auditResult.ProfileLevel = 'L1' # Modify as needed + $auditResult.Rec = '2.1.7' # Modify as needed + $auditResult.RecDescription = "Ensure that an anti-phishing policy has been created" # Modify as needed + $auditResult.CISControlVer = 'v8' # Modify as needed + $auditResult.CISControl = "9.7" # Modify as needed + $auditResult.CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections" # Modify as needed + $auditResult.IG1 = $false # Modify as needed + $auditResult.IG2 = $false # Modify as needed + $auditResult.IG3 = $true # Modify as needed + $auditResult.Result = $nonCompliantItems.Count -eq 0 + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons - $auditResults += $auditResult } end { # Return auditResults - return $auditResults + return $auditResult } } From 652e5ead756c2920fb0faa143f650c1d4b5fbf0d Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Sun, 26 May 2024 16:28:04 -0500 Subject: [PATCH 06/67] add: aligned test-AuditDisabledFalse --- .gitignore | 1 + source/tests/Test-AuditDisabledFalse.ps1 | 34 +++++++++++++++++------- 2 files changed, 25 insertions(+), 10 deletions(-) diff --git a/.gitignore b/.gitignore index 17c483d..d18e461 100644 --- a/.gitignore +++ b/.gitignore @@ -15,3 +15,4 @@ output/ markdownissues.txt node_modules package-lock.json +Aligned.xlsx \ No newline at end of file diff --git a/source/tests/Test-AuditDisabledFalse.ps1 b/source/tests/Test-AuditDisabledFalse.ps1 index fe56b46..bd3ee04 100644 --- a/source/tests/Test-AuditDisabledFalse.ps1 +++ b/source/tests/Test-AuditDisabledFalse.ps1 @@ -5,18 +5,34 @@ function Test-AuditDisabledFalse { ) begin { - # Dot source the class script + # Dot source the class script if necessary - $auditResults = @() + # Initialization code, if needed } process { # 6.1.1 (L1) Ensure 'AuditDisabled' organizationally is set to 'False' - # Pass if AuditDisabled is False. Fail otherwise. + + # Retrieve the AuditDisabled configuration $auditDisabledConfig = Get-OrganizationConfig | Select-Object AuditDisabled $auditNotDisabled = -not $auditDisabledConfig.AuditDisabled - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $auditNotDisabled) { + "AuditDisabled is set to True" + } + else { + "N/A" + } + + $details = if ($auditNotDisabled) { + "Audit is not disabled organizationally" + } + else { + "Audit is disabled organizationally" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($auditNotDisabled) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" @@ -30,14 +46,12 @@ function Test-AuditDisabledFalse { $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.Result = $auditNotDisabled - $auditResult.Details = if ($auditNotDisabled) { "Audit is not disabled organizationally" } else { "Audit is disabled organizationally" } - $auditResult.FailureReason = if (-not $auditNotDisabled) { "AuditDisabled is set to True" } else { "N/A" } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From f4ae24b99ff01b331d627e745a54c1f3d6492fcc Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Sun, 26 May 2024 17:32:08 -0500 Subject: [PATCH 07/67] add: connections to helper table --- source/helper/TestDefinitions.csv | 104 +++++++++++++++--------------- 1 file changed, 52 insertions(+), 52 deletions(-) diff --git a/source/helper/TestDefinitions.csv b/source/helper/TestDefinitions.csv index 5bef5ae..1bd9e43 100644 --- a/source/helper/TestDefinitions.csv +++ b/source/helper/TestDefinitions.csv @@ -1,52 +1,52 @@ -Index,TestFileName,Rec,ELevel,ProfileLevel,IG1,IG2,IG3,Automated -1,Test-AdministrativeAccountCompliance.ps1,1.1.1,E3,L1,TRUE,TRUE,TRUE,FALSE -2,Test-GlobalAdminsCount.ps1,1.1.3,E3,L1,TRUE,TRUE,TRUE,TRUE -3,Test-ManagedApprovedPublicGroups.ps1,1.2.1,E3,L2,TRUE,TRUE,TRUE,TRUE -4,Test-BlockSharedMailboxSignIn.ps1,1.2.2,E3,L1,FALSE,FALSE,FALSE,TRUE -5,Test-PasswordNeverExpirePolicy.ps1,1.3.1,E3,L1,TRUE,TRUE,TRUE,TRUE -6,Test-ExternalSharingCalendars.ps1,1.3.3,E3,L2,FALSE,TRUE,TRUE,TRUE -7,Test-CustomerLockbox.ps1,1.3.6,E5,L2,FALSE,FALSE,FALSE,TRUE -8,Test-SafeLinksOfficeApps.ps1,2.1.1,E5,L2,TRUE,TRUE,TRUE,TRUE -9,Test-CommonAttachmentFilter.ps1,2.1.2,E3,L1,FALSE,TRUE,TRUE,TRUE -10,Test-NotifyMalwareInternal.ps1,2.1.3,E3,L1,FALSE,TRUE,TRUE,TRUE -11,Test-SafeAttachmentsPolicy.ps1,2.1.4,E5,L2,FALSE,FALSE,TRUE,TRUE -12,Test-SafeAttachmentsTeams.ps1,2.1.5,E5,L2,TRUE,TRUE,TRUE,TRUE -13,Test-SpamPolicyAdminNotify.ps1,2.1.6,E3,L1,FALSE,TRUE,TRUE,TRUE -14,Test-AntiPhishingPolicy.ps1,2.1.7,E5,L1,FALSE,FALSE,TRUE,TRUE -15,Test-EnableDKIM.ps1,2.1.9,E3,L1,FALSE,TRUE,TRUE,TRUE -16,Test-AuditLogSearch.ps1,3.1.1,E3,L1,TRUE,TRUE,TRUE,TRUE -17,Test-RestrictTenantCreation.ps1,5.1.2.3,E3,L1,FALSE,FALSE,FALSE,TRUE -18,Test-PasswordHashSync.ps1,5.1.8.1,E3,L1,FALSE,TRUE,TRUE,TRUE -19,Test-AuditDisabledFalse.ps1,6.1.1,E3,L1,TRUE,TRUE,TRUE,TRUE -20,Test-MailboxAuditingE3.ps1,6.1.2,E3,L1,TRUE,TRUE,TRUE,TRUE -21,Test-MailboxAuditingE5.ps1,6.1.3,E5,L1,TRUE,TRUE,TRUE,TRUE -22,Test-BlockMailForwarding.ps1,6.2.1,E3,L1,FALSE,FALSE,FALSE,TRUE -23,Test-NoWhitelistDomains.ps1,6.2.2,E3,L1,FALSE,FALSE,FALSE,TRUE -24,Test-IdentifyExternalEmail.ps1,6.2.3,E3,L1,FALSE,FALSE,FALSE,TRUE -25,Test-RestrictOutlookAddins.ps1,6.3.1,E3,L2,FALSE,TRUE,TRUE,TRUE -26,Test-ModernAuthExchangeOnline.ps1,6.5.1,E3,L1,FALSE,TRUE,TRUE,TRUE -27,Test-MailTipsEnabled.ps1,6.5.2,E3,L2,FALSE,FALSE,FALSE,TRUE -28,Test-RestrictStorageProvidersOutlook.ps1,6.5.3,E3,L2,TRUE,TRUE,TRUE,TRUE -29,Test-ModernAuthSharePoint.ps1,7.2.1,E3,L1,FALSE,TRUE,TRUE,TRUE -30,Test-SharePointAADB2B.ps1,7.2.2,E3,L1,FALSE,FALSE,FALSE,TRUE -31,Test-RestrictExternalSharing.ps1,7.2.3,E3,L1,TRUE,TRUE,TRUE,TRUE -32,Test-OneDriveContentRestrictions.ps1,7.2.4,E3,L2,TRUE,TRUE,TRUE,TRUE -33,Test-SharePointGuestsItemSharing.ps1,7.2.5,E3,L2,TRUE,TRUE,TRUE,TRUE -34,Test-SharePointExternalSharingDomains.ps1,7.2.6,E3,L2,TRUE,TRUE,TRUE,TRUE -35,Test-LinkSharingRestrictions.ps1,7.2.7,E3,L1,TRUE,TRUE,TRUE,TRUE -36,Test-GuestAccessExpiration.ps1,7.2.9,E3,L1,FALSE,FALSE,FALSE,TRUE -37,Test-ReauthWithCode.ps1,7.2.10,E3,L1,FALSE,FALSE,FALSE,TRUE -38,Test-DisallowInfectedFilesDownload.ps1,7.3.1,E5,L2,TRUE,TRUE,TRUE,TRUE -39,Test-OneDriveSyncRestrictions.ps1,7.3.2,E3,L2,FALSE,FALSE,FALSE,TRUE -40,Test-RestrictCustomScripts.ps1,7.3.4,E3,L1,FALSE,FALSE,TRUE,TRUE -41,Test-TeamsExternalFileSharing.ps1,8.1.1,E3,L2,TRUE,TRUE,TRUE,TRUE -42,Test-BlockChannelEmails.ps1,8.1.2,E3,L1,FALSE,FALSE,FALSE,TRUE -43,Test-TeamsExternalAccess.ps1,8.2.1,E3,L2,FALSE,FALSE,FALSE,TRUE -44,Test-NoAnonymousMeetingJoin.ps1,8.5.1,E3,L2,FALSE,FALSE,FALSE,TRUE -45,Test-NoAnonymousMeetingStart.ps1,8.5.2,E3,L1,FALSE,FALSE,FALSE,TRUE -46,Test-OrgOnlyBypassLobby.ps1,8.5.3,E3,L1,FALSE,FALSE,TRUE,TRUE -47,Test-DialInBypassLobby.ps1,8.5.4,E3,L1,FALSE,FALSE,FALSE,TRUE -48,Test-MeetingChatNoAnonymous.ps1,8.5.5,E3,L1,FALSE,FALSE,FALSE,TRUE -49,Test-OrganizersPresent.ps1,8.5.6,E3,L1,FALSE,FALSE,FALSE,TRUE -50,Test-ExternalNoControl.ps1,8.5.7,E3,L1,FALSE,FALSE,FALSE,TRUE -51,Test-ReportSecurityInTeams.ps1,8.6.1,E3,L1,FALSE,FALSE,FALSE,TRUE +Index,TestFileName,Rec,ELevel,ProfileLevel,IG1,IG2,IG3,Automated,Connection +1,Test-AdministrativeAccountCompliance.ps1,1.1.1,E3,L1,TRUE,TRUE,TRUE,FALSE,AzureAD +2,Test-GlobalAdminsCount.ps1,1.1.3,E3,L1,TRUE,TRUE,TRUE,TRUE,Microsoft Graph +3,Test-ManagedApprovedPublicGroups.ps1,1.2.1,E3,L2,TRUE,TRUE,TRUE,TRUE,Microsoft Graph +4,Test-BlockSharedMailboxSignIn.ps1,1.2.2,E3,L1,FALSE,FALSE,FALSE,TRUE,AzureAD | EXO +5,Test-PasswordNeverExpirePolicy.ps1,1.3.1,E3,L1,TRUE,TRUE,TRUE,TRUE,Microsoft Graph +6,Test-ExternalSharingCalendars.ps1,1.3.3,E3,L2,FALSE,TRUE,TRUE,TRUE,EXO +7,Test-CustomerLockbox.ps1,1.3.6,E5,L2,FALSE,FALSE,FALSE,TRUE,EXO +8,Test-SafeLinksOfficeApps.ps1,2.1.1,E5,L2,TRUE,TRUE,TRUE,TRUE,EXO +9,Test-CommonAttachmentFilter.ps1,2.1.2,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO +10,Test-NotifyMalwareInternal.ps1,2.1.3,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO +11,Test-SafeAttachmentsPolicy.ps1,2.1.4,E5,L2,FALSE,FALSE,TRUE,TRUE,EXO +12,Test-SafeAttachmentsTeams.ps1,2.1.5,E5,L2,TRUE,TRUE,TRUE,TRUE,EXO +13,Test-SpamPolicyAdminNotify.ps1,2.1.6,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO +14,Test-AntiPhishingPolicy.ps1,2.1.7,E5,L1,FALSE,FALSE,TRUE,TRUE,EXO +15,Test-EnableDKIM.ps1,2.1.9,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO +16,Test-AuditLogSearch.ps1,3.1.1,E3,L1,TRUE,TRUE,TRUE,TRUE,EXO +17,Test-RestrictTenantCreation.ps1,5.1.2.3,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Graph +18,Test-PasswordHashSync.ps1,5.1.8.1,E3,L1,FALSE,TRUE,TRUE,TRUE,Microsoft Graph +19,Test-AuditDisabledFalse.ps1,6.1.1,E3,L1,TRUE,TRUE,TRUE,TRUE,Microsoft Graph +20,Test-MailboxAuditingE3.ps1,6.1.2,E3,L1,TRUE,TRUE,TRUE,TRUE,EXO +21,Test-MailboxAuditingE5.ps1,6.1.3,E5,L1,TRUE,TRUE,TRUE,TRUE,EXO +22,Test-BlockMailForwarding.ps1,6.2.1,E3,L1,FALSE,FALSE,FALSE,TRUE,EXO +23,Test-NoWhitelistDomains.ps1,6.2.2,E3,L1,FALSE,FALSE,FALSE,TRUE,EXO +24,Test-IdentifyExternalEmail.ps1,6.2.3,E3,L1,FALSE,FALSE,FALSE,TRUE,EXO +25,Test-RestrictOutlookAddins.ps1,6.3.1,E3,L2,FALSE,TRUE,TRUE,TRUE,EXO +26,Test-ModernAuthExchangeOnline.ps1,6.5.1,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO +27,Test-MailTipsEnabled.ps1,6.5.2,E3,L2,FALSE,FALSE,FALSE,TRUE,EXO +28,Test-RestrictStorageProvidersOutlook.ps1,6.5.3,E3,L2,TRUE,TRUE,TRUE,TRUE,EXO +29,Test-ModernAuthSharePoint.ps1,7.2.1,E3,L1,FALSE,TRUE,TRUE,TRUE,SPO +30,Test-SharePointAADB2B.ps1,7.2.2,E3,L1,FALSE,FALSE,FALSE,TRUE,SPO +31,Test-RestrictExternalSharing.ps1,7.2.3,E3,L1,TRUE,TRUE,TRUE,TRUE,SPO +32,Test-OneDriveContentRestrictions.ps1,7.2.4,E3,L2,TRUE,TRUE,TRUE,TRUE,SPO +33,Test-SharePointGuestsItemSharing.ps1,7.2.5,E3,L2,TRUE,TRUE,TRUE,TRUE,SPO +34,Test-SharePointExternalSharingDomains.ps1,7.2.6,E3,L2,TRUE,TRUE,TRUE,TRUE,SPO +35,Test-LinkSharingRestrictions.ps1,7.2.7,E3,L1,TRUE,TRUE,TRUE,TRUE,SPO +36,Test-GuestAccessExpiration.ps1,7.2.9,E3,L1,FALSE,FALSE,FALSE,TRUE,SPO +37,Test-ReauthWithCode.ps1,7.2.10,E3,L1,FALSE,FALSE,FALSE,TRUE,SPO +38,Test-DisallowInfectedFilesDownload.ps1,7.3.1,E5,L2,TRUE,TRUE,TRUE,TRUE,SPO +39,Test-OneDriveSyncRestrictions.ps1,7.3.2,E3,L2,FALSE,FALSE,FALSE,TRUE,SPO +40,Test-RestrictCustomScripts.ps1,7.3.4,E3,L1,FALSE,FALSE,TRUE,TRUE,SPO +41,Test-TeamsExternalFileSharing.ps1,8.1.1,E3,L2,TRUE,TRUE,TRUE,TRUE,Microsoft Teams +42,Test-BlockChannelEmails.ps1,8.1.2,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +43,Test-TeamsExternalAccess.ps1,8.2.1,E3,L2,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +44,Test-NoAnonymousMeetingJoin.ps1,8.5.1,E3,L2,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +45,Test-NoAnonymousMeetingStart.ps1,8.5.2,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +46,Test-OrgOnlyBypassLobby.ps1,8.5.3,E3,L1,FALSE,FALSE,TRUE,TRUE,Microsoft Teams +47,Test-DialInBypassLobby.ps1,8.5.4,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +48,Test-MeetingChatNoAnonymous.ps1,8.5.5,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +49,Test-OrganizersPresent.ps1,8.5.6,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +50,Test-ExternalNoControl.ps1,8.5.7,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +51,Test-ReportSecurityInTeams.ps1,8.6.1,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams | EXO From a1a2ecbd497d285cadf9776c87e8cb48fdb35d7f Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 09:29:06 -0500 Subject: [PATCH 08/67] fix: Included functions aligned. --- .../Test-AdministrativeAccountCompliance.ps1 | 1 + source/tests/Test-AntiPhishingPolicy.ps1 | 1 + source/tests/Test-AuditDisabledFalse.ps1 | 1 + source/tests/Test-AuditLogSearch.ps1 | 35 +++++++++++++------ 4 files changed, 28 insertions(+), 10 deletions(-) diff --git a/source/tests/Test-AdministrativeAccountCompliance.ps1 b/source/tests/Test-AdministrativeAccountCompliance.ps1 index 6bda22d..523ec11 100644 --- a/source/tests/Test-AdministrativeAccountCompliance.ps1 +++ b/source/tests/Test-AdministrativeAccountCompliance.ps1 @@ -1,6 +1,7 @@ function Test-AdministrativeAccountCompliance { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { diff --git a/source/tests/Test-AntiPhishingPolicy.ps1 b/source/tests/Test-AntiPhishingPolicy.ps1 index 449f4c8..0aef681 100644 --- a/source/tests/Test-AntiPhishingPolicy.ps1 +++ b/source/tests/Test-AntiPhishingPolicy.ps1 @@ -1,6 +1,7 @@ function Test-AntiPhishingPolicy { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) diff --git a/source/tests/Test-AuditDisabledFalse.ps1 b/source/tests/Test-AuditDisabledFalse.ps1 index bd3ee04..205d05a 100644 --- a/source/tests/Test-AuditDisabledFalse.ps1 +++ b/source/tests/Test-AuditDisabledFalse.ps1 @@ -1,5 +1,6 @@ function Test-AuditDisabledFalse { [CmdletBinding()] + # Aligned param ( # Parameters can be added if needed ) diff --git a/source/tests/Test-AuditLogSearch.ps1 b/source/tests/Test-AuditLogSearch.ps1 index 3249872..ac45913 100644 --- a/source/tests/Test-AuditLogSearch.ps1 +++ b/source/tests/Test-AuditLogSearch.ps1 @@ -1,22 +1,39 @@ function Test-AuditLogSearch { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary - $auditResults = @() + # Initialization code, if needed } process { # 3.1.1 (L1) Ensure Microsoft 365 audit log search is Enabled - # Pass if UnifiedAuditLogIngestionEnabled is True. Fail otherwise. + + # Retrieve the audit log configuration $auditLogConfig = Get-AdminAuditLogConfig | Select-Object UnifiedAuditLogIngestionEnabled $auditLogResult = $auditLogConfig.UnifiedAuditLogIngestionEnabled - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $auditLogResult) { + "Audit log search is not enabled" + } + else { + "N/A" + } + + $details = if ($auditLogResult) { + "UnifiedAuditLogIngestionEnabled: True" + } + else { + "UnifiedAuditLogIngestionEnabled: False" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($auditLogResult) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" @@ -30,14 +47,12 @@ function Test-AuditLogSearch { $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.Result = $auditLogResult - $auditResult.Details = "UnifiedAuditLogIngestionEnabled: $($auditLogConfig.UnifiedAuditLogIngestionEnabled)" - $auditResult.FailureReason = if (-not $auditLogResult) { "Audit log search is not enabled" } else { "N/A" } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From d5faf071b9cfebbfc471f7dd1598cffa8b439b1c Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 09:39:42 -0500 Subject: [PATCH 09/67] fix: "8.1.2" aligned with test-template --- source/tests/Test-BlockChannelEmails.ps1 | 36 ++++++++++++++++-------- 1 file changed, 25 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-BlockChannelEmails.ps1 b/source/tests/Test-BlockChannelEmails.ps1 index fc438ee..94e1e9e 100644 --- a/source/tests/Test-BlockChannelEmails.ps1 +++ b/source/tests/Test-BlockChannelEmails.ps1 @@ -1,26 +1,42 @@ function Test-BlockChannelEmails { [CmdletBinding()] param ( + # Aligned # Parameters can be added here if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary - $auditResults = @() + # Initialization code, if needed } process { # 8.1.2 (L1) Ensure users can't send emails to a channel email address - # Connect to Teams PowerShell using Connect-MicrosoftTeams + # Retrieve Teams client configuration $teamsClientConfig = Get-CsTeamsClientConfiguration -Identity Global $allowEmailIntoChannel = $teamsClientConfig.AllowEmailIntoChannel - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if ($allowEmailIntoChannel) { + "Emails can be sent to a channel email address" + } + else { + "N/A" + } + + $details = if ($allowEmailIntoChannel) { + "AllowEmailIntoChannel is set to True" + } + else { + "AllowEmailIntoChannel is set to False" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # This control is Explicitly Not Mapped as per the image provided + $auditResult.CISControl = "0.0" # This control is explicitly not mapped as per the image provided $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.Rec = "8.1.2" $auditResult.ELevel = "E3" @@ -30,15 +46,13 @@ function Test-BlockChannelEmails { $auditResult.IG3 = $false # Set based on the benchmark $auditResult.RecDescription = "Ensure users can't send emails to a channel email address" $auditResult.Result = -not $allowEmailIntoChannel - $auditResult.Details = "AllowEmailIntoChannel is set to $allowEmailIntoChannel" - $auditResult.FailureReason = if ($allowEmailIntoChannel) { "Emails can be sent to a channel email address" } else { "N/A" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if (-not $allowEmailIntoChannel) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From b93df00334266eb31568d4976de3fc5424658945 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 09:52:30 -0500 Subject: [PATCH 10/67] fix: "6.2.1" aligned with test-template --- source/tests/Test-BlockMailForwarding.ps1 | 59 +++++++++++++---------- 1 file changed, 34 insertions(+), 25 deletions(-) diff --git a/source/tests/Test-BlockMailForwarding.ps1 b/source/tests/Test-BlockMailForwarding.ps1 index d4bcaea..860beb0 100644 --- a/source/tests/Test-BlockMailForwarding.ps1 +++ b/source/tests/Test-BlockMailForwarding.ps1 @@ -1,51 +1,60 @@ function Test-BlockMailForwarding { [CmdletBinding()] param ( + # Aligned Compare # Parameters can be added if needed ) begin { + # Dot source the class script if necessary + # Initialization code, if needed + } + + process { + # 6.2.1 (L1) Ensure all forms of mail forwarding are blocked and/or disabled + + # Retrieve the transport rules that redirect messages + $transportRules = Get-TransportRule | Where-Object { $null -ne $_.RedirectMessageTo } + $forwardingBlocked = $transportRules.Count -eq 0 + + # Prepare failure reasons and details based on compliance + $failureReasons = if ($transportRules.Count -gt 0) { + "Mail forwarding rules found: $($transportRules.Name -join ', ')" + } + else { + "N/A" + } + + $details = if ($transportRules.Count -gt 0) { + $transportRules | ForEach-Object { + "$($_.Name) redirects to $($_.RedirectMessageTo)" + } -join " | " + } + else { + "Step 1: No forwarding rules found. Please proceed with Step 2 described in CIS Benchmark." + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Rec = "6.2.1" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" + $auditResult.CISControl = "0.0" # Explicitly Not Mapped $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.IG1 = $false $auditResult.IG2 = $false $auditResult.IG3 = $false $auditResult.RecDescription = "Ensure all forms of mail forwarding are blocked and/or disabled" - } - - process { - # Verify that no rules are forwarding the email to external domains - $transportRules = Get-TransportRule | Where-Object { $_.RedirectMessageTo -ne $null } - $forwardingBlocked = $transportRules.Count -eq 0 - $auditResult.Result = $forwardingBlocked - $auditResult.Details = if ($transportRules.Count -gt 0) { - $transportRules | ForEach-Object { - "$($_.Name) redirects to $($_.RedirectMessageTo)" - } -join " | " - } else { - "Step 1: No forwarding rules found. Please proceed with Step 2 described in CIS Benchmark." - } - $auditResult.FailureReason = if (-not $forwardingBlocked) { - "Mail forwarding rules found: $($transportRules.Name -join ', ')" - } else { - "N/A" - } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($forwardingBlocked) { "Pass" } else { "Fail" } } end { - # Return the result object + # Return the audit result return $auditResult } } - - - - From 2f8d7b358a6ae41d43f0df20b9fc8d51c97aa796 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 09:55:57 -0500 Subject: [PATCH 11/67] fix: 1.2.2 aligned with test-template --- .../tests/Test-BlockSharedMailboxSignIn.ps1 | 44 ++++++++++++------- 1 file changed, 28 insertions(+), 16 deletions(-) diff --git a/source/tests/Test-BlockSharedMailboxSignIn.ps1 b/source/tests/Test-BlockSharedMailboxSignIn.ps1 index b74afad..31e49a3 100644 --- a/source/tests/Test-BlockSharedMailboxSignIn.ps1 +++ b/source/tests/Test-BlockSharedMailboxSignIn.ps1 @@ -1,48 +1,60 @@ function Test-BlockSharedMailboxSignIn { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary - $auditResults = @() + # Initialization code, if needed } process { # 1.2.2 (L1) Ensure sign-in to shared mailboxes is blocked - # Pass if all shared mailboxes have AccountEnabled set to False. - # Fail if any shared mailbox has AccountEnabled set to True. - # Review: Details property - Add verbosity. + # Retrieve shared mailbox details $MBX = Get-EXOMailbox -RecipientTypeDetails SharedMailbox $sharedMailboxDetails = $MBX | ForEach-Object { Get-AzureADUser -ObjectId $_.ExternalDirectoryObjectId } $enabledMailboxes = $sharedMailboxDetails | Where-Object { $_.AccountEnabled } | ForEach-Object { $_.DisplayName } $allBlocked = $enabledMailboxes.Count -eq 0 - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $allBlocked) { + "Some mailboxes have sign-in enabled: $($enabledMailboxes -join ', ')" + } + else { + "N/A" + } + + $details = if ($allBlocked) { + "All shared mailboxes have sign-in blocked." + } + else { + "Enabled Mailboxes: $($enabledMailboxes -join ', ')" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Control is explicitly not mapped + $auditResult.CISControl = "0.0" # Control is explicitly not mapped $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.Rec = "1.2.2" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Control is not mapped, hence IG1 is false - $auditResult.IG2 = $false # Control is not mapped, hence IG2 is false - $auditResult.IG3 = $false # Control is not mapped, hence IG3 is false + $auditResult.IG1 = $false # Control is not mapped, hence IG1 is false + $auditResult.IG2 = $false # Control is not mapped, hence IG2 is false + $auditResult.IG3 = $false # Control is not mapped, hence IG3 is false $auditResult.RecDescription = "Ensure sign-in to shared mailboxes is blocked" $auditResult.Result = $allBlocked - $auditResult.Details = "Enabled Mailboxes: $($enabledMailboxes -join ', ')" - $auditResult.FailureReason = if ($allBlocked) { "N/A" } else { "Some mailboxes have sign-in enabled: $($enabledMailboxes -join ', ')" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($allBlocked) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 283b27852421629426615f98591985399186a8b3 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 09:58:49 -0500 Subject: [PATCH 12/67] fix: 2.1.2 aligned with test-template --- source/tests/Test-CommonAttachmentFilter.ps1 | 36 +++++++++++++------- 1 file changed, 24 insertions(+), 12 deletions(-) diff --git a/source/tests/Test-CommonAttachmentFilter.ps1 b/source/tests/Test-CommonAttachmentFilter.ps1 index 7f4ff33..962311a 100644 --- a/source/tests/Test-CommonAttachmentFilter.ps1 +++ b/source/tests/Test-CommonAttachmentFilter.ps1 @@ -1,27 +1,41 @@ function Test-CommonAttachmentFilter { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { + # Dot source the class script if necessary - $auditResults = @() + # Initialization code, if needed } process { # 2.1.2 (L1) Ensure the Common Attachment Types Filter is enabled - # Pass if EnableFileFilter is set to True. Fail otherwise. + # Retrieve the attachment filter policy $attachmentFilter = Get-MalwareFilterPolicy -Identity Default | Select-Object EnableFileFilter $result = $attachmentFilter.EnableFileFilter - $details = "File Filter Enabled: $($attachmentFilter.EnableFileFilter)" - $failureReason = if ($result) { "N/A" } else { "Common Attachment Types Filter is disabled" } - $status = if ($result) { "Pass" } else { "Fail" } - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $result) { + "Common Attachment Types Filter is disabled" + } + else { + "N/A" + } + + $details = if ($result) { + "File Filter Enabled: True" + } + else { + "File Filter Enabled: False" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() - $auditResult.Status = $status + $auditResult.Status = if ($result) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" $auditResult.Rec = "2.1.2" @@ -34,13 +48,11 @@ function Test-CommonAttachmentFilter { $auditResult.IG3 = $true $auditResult.Result = $result $auditResult.Details = $details - $auditResult.FailureReason = $failureReason - - $auditResults += $auditResult + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From fbe22abe9c62324e78a15522f3c2e63952c39bf4 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:05:35 -0500 Subject: [PATCH 13/67] fix: 1.3.6 aligned with test-template --- source/tests/Test-CustomerLockbox.ps1 | 36 ++++++++++++++++++++------- 1 file changed, 27 insertions(+), 9 deletions(-) diff --git a/source/tests/Test-CustomerLockbox.ps1 b/source/tests/Test-CustomerLockbox.ps1 index 542ce5c..6060a78 100644 --- a/source/tests/Test-CustomerLockbox.ps1 +++ b/source/tests/Test-CustomerLockbox.ps1 @@ -1,19 +1,39 @@ function Test-CustomerLockbox { [CmdletBinding()] param ( - # Define your parameters here + # Aligned + # Define your parameters here if needed ) begin { + # Dot source the class script if necessary - $auditResults = @() + # Initialization code, if needed } process { # 1.3.6 (L2) Ensure the customer lockbox feature is enabled + + # Retrieve the organization configuration $orgConfig = Get-OrganizationConfig | Select-Object CustomerLockBoxEnabled $customerLockboxEnabled = $orgConfig.CustomerLockBoxEnabled + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $customerLockboxEnabled) { + "Customer lockbox feature is not enabled." + } + else { + "N/A" + } + + $details = if ($customerLockboxEnabled) { + "Customer Lockbox Enabled: True" + } + else { + "Customer Lockbox Enabled: False" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($customerLockboxEnabled) { "Pass" } else { "Fail" } $auditResult.ELevel = "E5" @@ -21,20 +41,18 @@ function Test-CustomerLockbox { $auditResult.Rec = "1.3.6" $auditResult.RecDescription = "Ensure the customer lockbox feature is enabled" $auditResult.CISControlVer = 'v8' - $auditResult.CISControl = "0.0" # As per the snapshot provided, this is explicitly not mapped + $auditResult.CISControl = "0.0" # As per the snapshot provided, this is explicitly not mapped $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.IG1 = $false $auditResult.IG2 = $false $auditResult.IG3 = $false $auditResult.Result = $customerLockboxEnabled - $auditResult.Details = "Customer Lockbox Enabled: $customerLockboxEnabled" - $auditResult.FailureReason = if ($customerLockboxEnabled) { "N/A" } else { "Customer lockbox feature is not enabled." } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 5e9fbfd690f5927ee4ecb51ea502f8254a26fbe1 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:09:58 -0500 Subject: [PATCH 14/67] fix: 8.5.4 aligned with test-template --- source/tests/Test-DialInBypassLobby.ps1 | 43 ++++++++++++++++--------- 1 file changed, 28 insertions(+), 15 deletions(-) diff --git a/source/tests/Test-DialInBypassLobby.ps1 b/source/tests/Test-DialInBypassLobby.ps1 index 122a30a..ab4c843 100644 --- a/source/tests/Test-DialInBypassLobby.ps1 +++ b/source/tests/Test-DialInBypassLobby.ps1 @@ -1,45 +1,58 @@ function Test-DialInBypassLobby { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary - $auditResults = @() + # Initialization code, if needed } process { # 8.5.4 (L1) Ensure users dialing in can't bypass the lobby - # Connect to Teams PowerShell using Connect-MicrosoftTeams - + # Retrieve Teams meeting policy for PSTN users $CsTeamsMeetingPolicyPSTN = Get-CsTeamsMeetingPolicy -Identity Global | Select-Object -Property AllowPSTNUsersToBypassLobby $PSTNBypassDisabled = -not $CsTeamsMeetingPolicyPSTN.AllowPSTNUsersToBypassLobby - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $PSTNBypassDisabled) { + "Users dialing in can bypass the lobby" + } + else { + "N/A" + } + + $details = if ($PSTNBypassDisabled) { + "AllowPSTNUsersToBypassLobby is set to False" + } + else { + "AllowPSTNUsersToBypassLobby is set to True" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped as per the image provided + $auditResult.CISControl = "0.0" # Explicitly Not Mapped $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.Rec = "8.5.4" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image + $auditResult.IG1 = $false # Set based on the CIS Controls image + $auditResult.IG2 = $false # Set based on the CIS Controls image + $auditResult.IG3 = $false # Set based on the CIS Controls image $auditResult.RecDescription = "Ensure users dialing in can't bypass the lobby" $auditResult.Result = $PSTNBypassDisabled - $auditResult.Details = "AllowPSTNUsersToBypassLobby is set to $($CsTeamsMeetingPolicyPSTN.AllowPSTNUsersToBypassLobby)" - $auditResult.FailureReason = if ($PSTNBypassDisabled) { "N/A" } else { "Users dialing in can bypass the lobby" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($PSTNBypassDisabled) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 5f4217d264e5116ea30216dbcd9fbd19fd2b70bc Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:15:40 -0500 Subject: [PATCH 15/67] fix: 7.3.1 aligned with test-template --- .../Test-DisallowInfectedFilesDownload.ps1 | 35 ++++++++++++++----- 1 file changed, 26 insertions(+), 9 deletions(-) diff --git a/source/tests/Test-DisallowInfectedFilesDownload.ps1 b/source/tests/Test-DisallowInfectedFilesDownload.ps1 index f3c5f91..5b0fb86 100644 --- a/source/tests/Test-DisallowInfectedFilesDownload.ps1 +++ b/source/tests/Test-DisallowInfectedFilesDownload.ps1 @@ -1,25 +1,43 @@ function Test-DisallowInfectedFilesDownload { [CmdletBinding()] param ( - # Define your parameters here + # Define your parameters here if needed ) begin { - # Initialization code + # Dot source the class script if necessary + . .\source\Classes\CISAuditResult.ps1 - $auditResult = [CISAuditResult]::new() + # Initialization code, if needed } process { # 7.3.1 (L2) Ensure Office 365 SharePoint infected files are disallowed for download + + # Retrieve the SharePoint tenant configuration $SPOTenantDisallowInfectedFileDownload = Get-SPOTenant | Select-Object DisallowInfectedFileDownload $isDisallowInfectedFileDownloadEnabled = $SPOTenantDisallowInfectedFileDownload.DisallowInfectedFileDownload - # Populate the auditResult object with the required properties + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $isDisallowInfectedFileDownloadEnabled) { + "Downloading infected files is not disallowed." + } + else { + "N/A" + } + + $details = if ($isDisallowInfectedFileDownloadEnabled) { + "DisallowInfectedFileDownload: True" + } + else { + "DisallowInfectedFileDownload: False" + } + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" $auditResult.CISControl = "10.1" $auditResult.CISDescription = "Deploy and Maintain Anti-Malware Software" - $auditResult.Rec = "7.3.1" $auditResult.ELevel = "E5" $auditResult.ProfileLevel = "L2" @@ -27,15 +45,14 @@ function Test-DisallowInfectedFilesDownload { $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.RecDescription = "Ensure Office 365 SharePoint infected files are disallowed for download" - $auditResult.Result = $isDisallowInfectedFileDownloadEnabled - $auditResult.Details = "DisallowInfectedFileDownload: $($SPOTenantDisallowInfectedFileDownload.DisallowInfectedFileDownload)" - $auditResult.FailureReason = if (-not $isDisallowInfectedFileDownloadEnabled) { "Downloading infected files is not disallowed." } else { "N/A" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($isDisallowInfectedFileDownloadEnabled) { "Pass" } else { "Fail" } } end { - # Return auditResult + # Return the audit result return $auditResult } } From ccb02d84d2982af8ad9af910dd2cadfea5cb0222 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:24:34 -0500 Subject: [PATCH 16/67] fix: 7.3.1 added comment --- source/tests/Test-DisallowInfectedFilesDownload.ps1 | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/source/tests/Test-DisallowInfectedFilesDownload.ps1 b/source/tests/Test-DisallowInfectedFilesDownload.ps1 index 5b0fb86..67778fc 100644 --- a/source/tests/Test-DisallowInfectedFilesDownload.ps1 +++ b/source/tests/Test-DisallowInfectedFilesDownload.ps1 @@ -1,12 +1,13 @@ function Test-DisallowInfectedFilesDownload { [CmdletBinding()] param ( + # Aligned # Define your parameters here if needed ) begin { # Dot source the class script if necessary - . .\source\Classes\CISAuditResult.ps1 + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } From 0ae69e5b56d04f06bf94154a269a256a97601c70 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:25:03 -0500 Subject: [PATCH 17/67] fix: 2.1.9 aligned with test-template --- source/tests/Test-EnableDKIM.ps1 | 39 ++++++++++++++++++++++---------- 1 file changed, 27 insertions(+), 12 deletions(-) diff --git a/source/tests/Test-EnableDKIM.ps1 b/source/tests/Test-EnableDKIM.ps1 index a0b5da9..607fad2 100644 --- a/source/tests/Test-EnableDKIM.ps1 +++ b/source/tests/Test-EnableDKIM.ps1 @@ -1,23 +1,40 @@ function Test-EnableDKIM { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 2.1.9 (L1) Ensure DKIM is enabled for all Exchange Online Domains - # Pass if Enabled is True for all domains. Fail if any domain has Enabled set to False. + + # Retrieve DKIM configuration for all domains $dkimConfig = Get-DkimSigningConfig | Select-Object Domain, Enabled $dkimResult = ($dkimConfig | ForEach-Object { $_.Enabled }) -notcontains $false $dkimFailedDomains = $dkimConfig | Where-Object { -not $_.Enabled } | ForEach-Object { $_.Domain } - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $dkimResult) { + "DKIM is not enabled for some domains" + } + else { + "N/A" + } + + $details = if ($dkimResult) { + "All domains have DKIM enabled" + } + else { + "DKIM not enabled for: $($dkimFailedDomains -join ', ')" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($dkimResult) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" @@ -31,14 +48,12 @@ function Test-EnableDKIM { $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.Result = $dkimResult - $auditResult.Details = if (-not $dkimResult) { "DKIM not enabled for: $($dkimFailedDomains -join ', ')" } else { "All domains have DKIM enabled" } - $auditResult.FailureReason = if (-not $dkimResult) { "DKIM is not enabled for some domains" } else { "N/A" } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } -} \ No newline at end of file +} From 0d764e61520ae570ceb1e9819269e2474bbfe2dd Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:27:38 -0500 Subject: [PATCH 18/67] fix: 8.5.7 aligned with test-template --- source/tests/Test-ExternalNoControl.ps1 | 44 ++++++++++++++++--------- 1 file changed, 29 insertions(+), 15 deletions(-) diff --git a/source/tests/Test-ExternalNoControl.ps1 b/source/tests/Test-ExternalNoControl.ps1 index aa5978f..f3745ef 100644 --- a/source/tests/Test-ExternalNoControl.ps1 +++ b/source/tests/Test-ExternalNoControl.ps1 @@ -1,45 +1,59 @@ function Test-ExternalNoControl { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary + # . .\source\Classes\CISAuditResult.ps1 - $auditResults = @() + # Initialization code, if needed } process { # 8.5.7 (L1) Ensure external participants can't give or request control - # Connect to Teams PowerShell using Connect-MicrosoftTeams - + # Retrieve Teams meeting policy for external participant control $CsTeamsMeetingPolicyControl = Get-CsTeamsMeetingPolicy -Identity Global | Select-Object -Property AllowExternalParticipantGiveRequestControl $externalControlRestricted = -not $CsTeamsMeetingPolicyControl.AllowExternalParticipantGiveRequestControl - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $externalControlRestricted) { + "External participants can give or request control" + } + else { + "N/A" + } + + $details = if ($externalControlRestricted) { + "AllowExternalParticipantGiveRequestControl is set to False" + } + else { + "AllowExternalParticipantGiveRequestControl is set to True" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped as per the image provided + $auditResult.CISControl = "0.0" # Explicitly Not Mapped $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.Rec = "8.5.7" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image + $auditResult.IG1 = $false # Set based on the CIS Controls image + $auditResult.IG2 = $false # Set based on the CIS Controls image + $auditResult.IG3 = $false # Set based on the CIS Controls image $auditResult.RecDescription = "Ensure external participants can't give or request control" $auditResult.Result = $externalControlRestricted - $auditResult.Details = "AllowExternalParticipantGiveRequestControl is set to $($CsTeamsMeetingPolicyControl.AllowExternalParticipantGiveRequestControl)" - $auditResult.FailureReason = if ($externalControlRestricted) { "N/A" } else { "External participants can give or request control" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($externalControlRestricted) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 20ee994ebc68302ecd18319a49b84237d5fa3678 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:31:06 -0500 Subject: [PATCH 19/67] fix: 1.3.3 aligned with test-template --- .../tests/Test-ExternalSharingCalendars.ps1 | 37 +++++++++++++------ 1 file changed, 26 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-ExternalSharingCalendars.ps1 b/source/tests/Test-ExternalSharingCalendars.ps1 index d721a14..17e6dce 100644 --- a/source/tests/Test-ExternalSharingCalendars.ps1 +++ b/source/tests/Test-ExternalSharingCalendars.ps1 @@ -1,17 +1,21 @@ function Test-ExternalSharingCalendars { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary + # . .\source\Classes\CISAuditResult.ps1 - $auditResults = @() + # Initialization code, if needed } process { # 1.3.3 (L2) Ensure 'External sharing' of calendars is not available (Automated) + + # Retrieve sharing policies related to calendar sharing $sharingPolicies = Get-SharingPolicy | Where-Object { $_.Domains -like '*CalendarSharing*' } # Check if calendar sharing is disabled in all applicable policies @@ -24,30 +28,41 @@ function Test-ExternalSharingCalendars { } } - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $isExternalSharingDisabled) { + "Calendar sharing with external users is enabled in one or more policies." + } + else { + "N/A" + } + + $details = if ($isExternalSharingDisabled) { + "Calendar sharing with external users is disabled." + } + else { + "Enabled Sharing Policies: $($sharingPolicyDetails -join ', ')" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Rec = "1.3.3" $auditResult.RecDescription = "Ensure 'External sharing' of calendars is not available" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L2" - # The following IG values are placeholders. Replace with actual values when known. $auditResult.IG1 = $false $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.CISControlVer = "v8" - # Placeholder for CIS Control, to be replaced with the actual value when available $auditResult.CISControl = "4.8" $auditResult.CISDescription = "Uninstall or Disable Unnecessary Services on Enterprise Assets and Software" $auditResult.Result = $isExternalSharingDisabled - $auditResult.Details = if ($isExternalSharingDisabled) { "Calendar sharing with external users is disabled." } else { "Enabled Sharing Policies: $($sharingPolicyDetails -join ', ')" } - $auditResult.FailureReason = if ($isExternalSharingDisabled) { "N/A" } else { "Calendar sharing with external users is enabled in one or more policies." } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($isExternalSharingDisabled) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From d0c3d907b92439a14c32d7cdb239cd8992e3cdce Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:33:54 -0500 Subject: [PATCH 20/67] fix: 1.1.3 aligned with test-template --- source/tests/Test-GlobalAdminsCount.ps1 | 43 ++++++++++++++++--------- 1 file changed, 28 insertions(+), 15 deletions(-) diff --git a/source/tests/Test-GlobalAdminsCount.ps1 b/source/tests/Test-GlobalAdminsCount.ps1 index f79b04e..e1fe62e 100644 --- a/source/tests/Test-GlobalAdminsCount.ps1 +++ b/source/tests/Test-GlobalAdminsCount.ps1 @@ -1,46 +1,59 @@ function Test-GlobalAdminsCount { [CmdletBinding()] param ( - # Define your parameters here + # Aligned + # Define your parameters here if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary + . .\source\Classes\CISAuditResult.ps1 - $auditResults = @() + # Initialization code, if needed } process { # 1.1.3 (L1) Ensure that between two and four global admins are designated - # Pass if the count of global admins is between 2 and 4. Fail otherwise. + # Retrieve global admin role and members $globalAdminRole = Get-MgDirectoryRole -Filter "RoleTemplateId eq '62e90394-69f5-4237-9190-012177145e10'" $globalAdmins = Get-MgDirectoryRoleMember -DirectoryRoleId $globalAdminRole.Id $globalAdminCount = $globalAdmins.AdditionalProperties.Count $globalAdminUsernames = ($globalAdmins | ForEach-Object { $_.AdditionalProperties["displayName"] }) -join ', ' - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if ($globalAdminCount -lt 2) { + "Less than 2 global admins: $globalAdminUsernames" + } + elseif ($globalAdminCount -gt 4) { + "More than 4 global admins: $globalAdminUsernames" + } + else { + "N/A" + } + + $details = "Count: $globalAdminCount; Users: $globalAdminUsernames" + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" $auditResult.CISControl = "5.1" $auditResult.CISDescription = "Establish and Maintain an Inventory of Accounts" $auditResult.Rec = "1.1.3" - $auditResult.ELevel = "E3" # Based on your environment (E3, E5, etc.) + $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $true # Set based on the benchmark - $auditResult.IG2 = $true # Set based on the benchmark - $auditResult.IG3 = $true # Set based on the benchmark + $auditResult.IG1 = $true + $auditResult.IG2 = $true + $auditResult.IG3 = $true $auditResult.RecDescription = "Ensure that between two and four global admins are designated" $auditResult.Result = $globalAdminCount -ge 2 -and $globalAdminCount -le 4 - $auditResult.Details = "Count: $globalAdminCount; Users: $globalAdminUsernames" - $auditResult.FailureReason = if ($globalAdminCount -lt 2) { "Less than 2 global admins: $globalAdminUsernames" } elseif ($globalAdminCount -gt 4) { "More than 4 global admins: $globalAdminUsernames" } else { "N/A" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($globalAdminCount -ge 2 -and $globalAdminCount -le 4) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From dc88df6eefe3c95029b187604433d157fe33356c Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:36:29 -0500 Subject: [PATCH 21/67] fix: 7.2.9 aligned with test-template --- source/tests/Test-GuestAccessExpiration.ps1 | 35 ++++++++++++++------- 1 file changed, 24 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-GuestAccessExpiration.ps1 b/source/tests/Test-GuestAccessExpiration.ps1 index fb9b8cb..d1e6f24 100644 --- a/source/tests/Test-GuestAccessExpiration.ps1 +++ b/source/tests/Test-GuestAccessExpiration.ps1 @@ -1,25 +1,39 @@ function Test-GuestAccessExpiration { [CmdletBinding()] param ( - # Define your parameters here + # Aligned + # Define your parameters here if needed ) begin { - # Initialization code + # Dot source the class script if necessary + # . .\source\Classes\CISAuditResult.ps1 - $auditResult = [CISAuditResult]::new() + # Initialization code, if needed } process { # 7.2.9 (L1) Ensure guest access to a site or OneDrive will expire automatically + + # Retrieve SharePoint tenant settings related to guest access expiration $SPOTenantGuestAccess = Get-SPOTenant | Select-Object ExternalUserExpirationRequired, ExternalUserExpireInDays $isGuestAccessExpirationConfiguredCorrectly = $SPOTenantGuestAccess.ExternalUserExpirationRequired -and $SPOTenantGuestAccess.ExternalUserExpireInDays -le 30 - # Populate the auditResult object with the required properties - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" - $auditResult.CISDescription = "Explicitly Not Mapped" + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $isGuestAccessExpirationConfiguredCorrectly) { + "Guest access expiration is not configured to automatically expire within 30 days or less." + } + else { + "N/A" + } + $details = "ExternalUserExpirationRequired: $($SPOTenantGuestAccess.ExternalUserExpirationRequired); ExternalUserExpireInDays: $($SPOTenantGuestAccess.ExternalUserExpireInDays)" + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.CISControlVer = "v8" + $auditResult.CISControl = "0.0" # Explicitly Not Mapped + $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.Rec = "7.2.9" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" @@ -27,15 +41,14 @@ function Test-GuestAccessExpiration { $auditResult.IG2 = $false $auditResult.IG3 = $false $auditResult.RecDescription = "Ensure guest access to a site or OneDrive will expire automatically" - $auditResult.Result = $isGuestAccessExpirationConfiguredCorrectly - $auditResult.Details = "ExternalUserExpirationRequired: $($SPOTenantGuestAccess.ExternalUserExpirationRequired); ExternalUserExpireInDays: $($SPOTenantGuestAccess.ExternalUserExpireInDays)" - $auditResult.FailureReason = if (-not $isGuestAccessExpirationConfiguredCorrectly) { "Guest access expiration is not configured to automatically expire within 30 days or less." } else { "N/A" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($isGuestAccessExpirationConfiguredCorrectly) { "Pass" } else { "Fail" } } end { - # Return auditResult + # Return the audit result return $auditResult } } From b8690ddb441795c686213229e746f3b318bf45aa Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:39:54 -0500 Subject: [PATCH 22/67] fix: 1.1.4 aligned with test-template --- .../tests/Test-GuestUsersBiweeklyReview.ps1 | 58 +++++++++++-------- 1 file changed, 33 insertions(+), 25 deletions(-) diff --git a/source/tests/Test-GuestUsersBiweeklyReview.ps1 b/source/tests/Test-GuestUsersBiweeklyReview.ps1 index b89ae85..bb90cf6 100644 --- a/source/tests/Test-GuestUsersBiweeklyReview.ps1 +++ b/source/tests/Test-GuestUsersBiweeklyReview.ps1 @@ -1,22 +1,42 @@ function Test-GuestUsersBiweeklyReview { [CmdletBinding()] - param () + param ( + # Aligned + # Define your parameters here if needed + ) begin { - #. .\source\Classes\CISAuditResult.ps1 - $auditResults = @() + # Dot source the class script if necessary + . .\source\Classes\CISAuditResult.ps1 + + # Initialization code, if needed } process { # 1.1.4 (L1) Ensure Guest Users are reviewed at least biweekly - # The function will fail if guest users are found since they should be reviewed manually biweekly. try { - # Connect to Microsoft Graph - placeholder for connection command + # Retrieve guest users from Microsoft Graph # Connect-MgGraph -Scopes "User.Read.All" $guestUsers = Get-MgUser -All -Filter "UserType eq 'Guest'" - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if ($guestUsers) { + "Guest users present: $($guestUsers.Count)" + } + else { + "N/A" + } + + $details = if ($guestUsers) { + $auditCommand = "Get-MgUser -All -Property UserType,UserPrincipalName | Where {`$_.UserType -ne 'Member'} | Format-Table UserPrincipalName, UserType" + "Manual review required. To list guest users, run: `"$auditCommand`"." + } + else { + "No guest users found." + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControl = "5.1, 5.3" $auditResult.CISDescription = "Establish and Maintain an Inventory of Accounts, Disable Dormant Accounts" @@ -28,34 +48,22 @@ function Test-GuestUsersBiweeklyReview { $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.CISControlVer = 'v8' - - if ($guestUsers) { - $auditCommand = "Get-MgUser -All -Property UserType,UserPrincipalName | Where {`$_.UserType -ne 'Member'} | Format-Table UserPrincipalName, UserType" - $auditResult.Status = "Fail" - $auditResult.Result = $false - $auditResult.Details = "Manual review required. To list guest users, run: `"$auditCommand`"." - $auditResult.FailureReason = "Guest users present: $($guestUsers.Count)" - } else { - $auditResult.Status = "Pass" - $auditResult.Result = $true - $auditResult.Details = "No guest users found." - $auditResult.FailureReason = "N/A" - } + $auditResult.Result = -not $guestUsers + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons + $auditResult.Status = if ($guestUsers) { "Fail" } else { "Pass" } } catch { + $auditResult = [CISAuditResult]::new() $auditResult.Status = "Error" $auditResult.Result = $false $auditResult.Details = "Error while attempting to check guest users. Error message: $($_.Exception.Message)" $auditResult.FailureReason = "An error occurred during the audit check." } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } - - From 4b28258b3ee0dded00533998c5ee7848197db8b7 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:41:57 -0500 Subject: [PATCH 23/67] fix: added test comments --- source/tests/Test-AdministrativeAccountCompliance.ps1 | 2 +- source/tests/Test-AntiPhishingPolicy.ps1 | 2 +- source/tests/Test-AuditDisabledFalse.ps1 | 2 +- source/tests/Test-AuditLogSearch.ps1 | 2 +- source/tests/Test-BlockChannelEmails.ps1 | 2 +- source/tests/Test-BlockMailForwarding.ps1 | 2 +- source/tests/Test-BlockSharedMailboxSignIn.ps1 | 2 +- source/tests/Test-CommonAttachmentFilter.ps1 | 2 +- source/tests/Test-CustomerLockbox.ps1 | 2 +- source/tests/Test-DialInBypassLobby.ps1 | 2 +- source/tests/Test-GlobalAdminsCount.ps1 | 2 +- source/tests/Test-GuestUsersBiweeklyReview.ps1 | 2 +- 12 files changed, 12 insertions(+), 12 deletions(-) diff --git a/source/tests/Test-AdministrativeAccountCompliance.ps1 b/source/tests/Test-AdministrativeAccountCompliance.ps1 index 523ec11..3e6dce1 100644 --- a/source/tests/Test-AdministrativeAccountCompliance.ps1 +++ b/source/tests/Test-AdministrativeAccountCompliance.ps1 @@ -5,7 +5,7 @@ function Test-AdministrativeAccountCompliance { # Parameters can be added if needed ) begin { - #. C:\Temp\CISAuditResult.ps1 + #. .\source\Classes\CISAuditResult.ps1 $validLicenses = @('AAD_PREMIUM', 'AAD_PREMIUM_P2') } process { diff --git a/source/tests/Test-AntiPhishingPolicy.ps1 b/source/tests/Test-AntiPhishingPolicy.ps1 index 0aef681..4b669db 100644 --- a/source/tests/Test-AntiPhishingPolicy.ps1 +++ b/source/tests/Test-AntiPhishingPolicy.ps1 @@ -7,7 +7,7 @@ function Test-AntiPhishingPolicy { begin { # Dot source the class script if necessary - + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed #$auditResults = @() } diff --git a/source/tests/Test-AuditDisabledFalse.ps1 b/source/tests/Test-AuditDisabledFalse.ps1 index 205d05a..1ba0362 100644 --- a/source/tests/Test-AuditDisabledFalse.ps1 +++ b/source/tests/Test-AuditDisabledFalse.ps1 @@ -7,7 +7,7 @@ function Test-AuditDisabledFalse { begin { # Dot source the class script if necessary - + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-AuditLogSearch.ps1 b/source/tests/Test-AuditLogSearch.ps1 index ac45913..48a0c91 100644 --- a/source/tests/Test-AuditLogSearch.ps1 +++ b/source/tests/Test-AuditLogSearch.ps1 @@ -7,7 +7,7 @@ function Test-AuditLogSearch { begin { # Dot source the class script if necessary - + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-BlockChannelEmails.ps1 b/source/tests/Test-BlockChannelEmails.ps1 index 94e1e9e..f69a5c0 100644 --- a/source/tests/Test-BlockChannelEmails.ps1 +++ b/source/tests/Test-BlockChannelEmails.ps1 @@ -7,7 +7,7 @@ function Test-BlockChannelEmails { begin { # Dot source the class script if necessary - + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-BlockMailForwarding.ps1 b/source/tests/Test-BlockMailForwarding.ps1 index 860beb0..f00377d 100644 --- a/source/tests/Test-BlockMailForwarding.ps1 +++ b/source/tests/Test-BlockMailForwarding.ps1 @@ -7,7 +7,7 @@ function Test-BlockMailForwarding { begin { # Dot source the class script if necessary - + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-BlockSharedMailboxSignIn.ps1 b/source/tests/Test-BlockSharedMailboxSignIn.ps1 index 31e49a3..958d434 100644 --- a/source/tests/Test-BlockSharedMailboxSignIn.ps1 +++ b/source/tests/Test-BlockSharedMailboxSignIn.ps1 @@ -7,7 +7,7 @@ function Test-BlockSharedMailboxSignIn { begin { # Dot source the class script if necessary - + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-CommonAttachmentFilter.ps1 b/source/tests/Test-CommonAttachmentFilter.ps1 index 962311a..5d4e356 100644 --- a/source/tests/Test-CommonAttachmentFilter.ps1 +++ b/source/tests/Test-CommonAttachmentFilter.ps1 @@ -7,7 +7,7 @@ function Test-CommonAttachmentFilter { begin { # Dot source the class script if necessary - + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-CustomerLockbox.ps1 b/source/tests/Test-CustomerLockbox.ps1 index 6060a78..2404203 100644 --- a/source/tests/Test-CustomerLockbox.ps1 +++ b/source/tests/Test-CustomerLockbox.ps1 @@ -7,7 +7,7 @@ function Test-CustomerLockbox { begin { # Dot source the class script if necessary - + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-DialInBypassLobby.ps1 b/source/tests/Test-DialInBypassLobby.ps1 index ab4c843..0d3eefb 100644 --- a/source/tests/Test-DialInBypassLobby.ps1 +++ b/source/tests/Test-DialInBypassLobby.ps1 @@ -7,7 +7,7 @@ function Test-DialInBypassLobby { begin { # Dot source the class script if necessary - + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-GlobalAdminsCount.ps1 b/source/tests/Test-GlobalAdminsCount.ps1 index e1fe62e..a01089a 100644 --- a/source/tests/Test-GlobalAdminsCount.ps1 +++ b/source/tests/Test-GlobalAdminsCount.ps1 @@ -7,7 +7,7 @@ function Test-GlobalAdminsCount { begin { # Dot source the class script if necessary - . .\source\Classes\CISAuditResult.ps1 + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-GuestUsersBiweeklyReview.ps1 b/source/tests/Test-GuestUsersBiweeklyReview.ps1 index bb90cf6..64bd6c9 100644 --- a/source/tests/Test-GuestUsersBiweeklyReview.ps1 +++ b/source/tests/Test-GuestUsersBiweeklyReview.ps1 @@ -7,7 +7,7 @@ function Test-GuestUsersBiweeklyReview { begin { # Dot source the class script if necessary - . .\source\Classes\CISAuditResult.ps1 + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } From 0d049c6dcb0710ee908397c882f77c3c6d8c1b28 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:44:16 -0500 Subject: [PATCH 24/67] fix: 6.2.3 aligned with test-template --- source/tests/Test-IdentifyExternalEmail.ps1 | 33 +++++++++++++-------- 1 file changed, 21 insertions(+), 12 deletions(-) diff --git a/source/tests/Test-IdentifyExternalEmail.ps1 b/source/tests/Test-IdentifyExternalEmail.ps1 index 9c421c0..a876c7d 100644 --- a/source/tests/Test-IdentifyExternalEmail.ps1 +++ b/source/tests/Test-IdentifyExternalEmail.ps1 @@ -1,24 +1,35 @@ function Test-IdentifyExternalEmail { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 - $auditResults = @() + # Initialization code, if needed } process { # 6.2.3 (L1) Ensure email from external senders is identified - # Requirement is to have external sender tagging enabled - # Review + # Retrieve external sender tagging configuration $externalInOutlook = Get-ExternalInOutlook $externalTaggingEnabled = ($externalInOutlook | ForEach-Object { $_.Enabled }) -contains $true - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $externalTaggingEnabled) { + "External sender tagging is disabled" + } + else { + "N/A" + } + + $details = "Enabled: $($externalTaggingEnabled); AllowList: $($externalInOutlook.AllowList)" + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($externalTaggingEnabled) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" @@ -26,20 +37,18 @@ function Test-IdentifyExternalEmail { $auditResult.Rec = "6.2.3" $auditResult.RecDescription = "Ensure email from external senders is identified" $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" + $auditResult.CISControl = "0.0" # Explicitly Not Mapped $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.IG1 = $false $auditResult.IG2 = $false $auditResult.IG3 = $false $auditResult.Result = $externalTaggingEnabled - $auditResult.Details = "Enabled: $($externalTaggingEnabled); AllowList: $($externalInOutlook.AllowList)" - $auditResult.FailureReason = if (-not $externalTaggingEnabled) { "External sender tagging is disabled" } else { "N/A" } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 5ed1e1de35d0d8eaeefe03ec2a9fc7ec3cf371e7 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:49:31 -0500 Subject: [PATCH 25/67] fix: 7.2.7 aligned with test-template --- source/tests/Test-LinkSharingRestrictions.ps1 | 46 ++++++++++++------- 1 file changed, 29 insertions(+), 17 deletions(-) diff --git a/source/tests/Test-LinkSharingRestrictions.ps1 b/source/tests/Test-LinkSharingRestrictions.ps1 index b0c14b0..a2bcaba 100644 --- a/source/tests/Test-LinkSharingRestrictions.ps1 +++ b/source/tests/Test-LinkSharingRestrictions.ps1 @@ -1,42 +1,54 @@ function Test-LinkSharingRestrictions { [CmdletBinding()] param ( + # Aligned # Define your parameters here # Test behavior in prod ) begin { - # Initialization code - - $auditResult = [CISAuditResult]::new() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 7.2.7 (L1) Ensure link sharing is restricted in SharePoint and OneDrive - $SPOTenantLinkSharing = Get-SPOTenant | Select-Object DefaultSharingLinkType - $isLinkSharingRestricted = $SPOTenantLinkSharing.DefaultSharingLinkType -eq 'Direct' # Or 'SpecificPeople' as per the recommendation - # Populate the auditResult object with the required properties + # Retrieve link sharing configuration for SharePoint and OneDrive + $SPOTenantLinkSharing = Get-SPOTenant | Select-Object DefaultSharingLinkType + $isLinkSharingRestricted = $SPOTenantLinkSharing.DefaultSharingLinkType -eq 'Direct' # Or 'SpecificPeople' as per the recommendation + + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $isLinkSharingRestricted) { + "Link sharing is not restricted to 'Specific people'. Current setting: $($SPOTenantLinkSharing.DefaultSharingLinkType)" + } + else { + "N/A" + } + + $details = "DefaultSharingLinkType: $($SPOTenantLinkSharing.DefaultSharingLinkType)" + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($isLinkSharingRestricted) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" + $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "7.2.7" + $auditResult.RecDescription = "Ensure link sharing is restricted in SharePoint and OneDrive" $auditResult.CISControlVer = "v8" $auditResult.CISControl = "3.3" $auditResult.CISDescription = "Configure Data Access Control Lists" - - $auditResult.Rec = "7.2.7" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" $auditResult.IG1 = $true $auditResult.IG2 = $true $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure link sharing is restricted in SharePoint and OneDrive" - $auditResult.Result = $isLinkSharingRestricted - $auditResult.Details = "DefaultSharingLinkType: $($SPOTenantLinkSharing.DefaultSharingLinkType)" - $auditResult.FailureReason = if (-not $isLinkSharingRestricted) { "Link sharing is not restricted to 'Specific people'. Current setting: $($SPOTenantLinkSharing.DefaultSharingLinkType)" } else { "N/A" } - $auditResult.Status = if ($isLinkSharingRestricted) { "Pass" } else { "Fail" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResult + # Return the audit result return $auditResult } -} +} \ No newline at end of file From f5a3f0e460251fbf884786792147f1b8e958fbac Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:54:52 -0500 Subject: [PATCH 26/67] fix: 6.1.2 aligned with test-template --- source/tests/Test-MailboxAuditingE3.ps1 | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/source/tests/Test-MailboxAuditingE3.ps1 b/source/tests/Test-MailboxAuditingE3.ps1 index f37bd65..f9583b4 100644 --- a/source/tests/Test-MailboxAuditingE3.ps1 +++ b/source/tests/Test-MailboxAuditingE3.ps1 @@ -1,15 +1,19 @@ function Test-MailboxAuditingE3 { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 $e3SkuPartNumbers = @("ENTERPRISEPACK", "OFFICESUBSCRIPTION") $AdminActions = @("ApplyRecord", "Copy", "Create", "FolderBind", "HardDelete", "Move", "MoveToDeletedItems", "SendAs", "SendOnBehalf", "SoftDelete", "Update", "UpdateCalendarDelegation", "UpdateFolderPermissions", "UpdateInboxRules") $DelegateActions = @("ApplyRecord", "Create", "FolderBind", "HardDelete", "Move", "MoveToDeletedItems", "SendAs", "SendOnBehalf", "SoftDelete", "Update", "UpdateFolderPermissions", "UpdateInboxRules") $OwnerActions = @("ApplyRecord", "Create", "HardDelete", "MailboxLogin", "Move", "MoveToDeletedItems", "SoftDelete", "Update", "UpdateCalendarDelegation", "UpdateFolderPermissions", "UpdateInboxRules") + $auditResult = [CISAuditResult]::new() $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" @@ -72,10 +76,15 @@ function Test-MailboxAuditingE3 { } } + # Prepare failure reasons and details based on compliance + $failureReasons = if ($allFailures.Count -eq 0) { "N/A" } else { "Audit issues detected." } + $details = if ($allFailures.Count -eq 0) { "All Office E3 users have correct mailbox audit settings." } else { $allFailures -join " | " } + + # Populate the audit result $auditResult.Result = $allFailures.Count -eq 0 $auditResult.Status = if ($auditResult.Result) { "Pass" } else { "Fail" } - $auditResult.Details = if ($auditResult.Result) { "All Office E3 users have correct mailbox audit settings." } else { $allFailures -join " | " } - $auditResult.FailureReason = if (-not $auditResult.Result) { "Audit issues detected." } else { "N/A" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { From 0196607f69c8e824d18c63c48fc79eb93ab35c2a Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 10:59:23 -0500 Subject: [PATCH 27/67] fix: 6.1.2/3 aligned with test-template --- source/tests/Test-MailboxAuditingE3.ps1 | 1 + source/tests/Test-MailboxAuditingE5.ps1 | 28 +++++++++++++++---------- 2 files changed, 18 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-MailboxAuditingE3.ps1 b/source/tests/Test-MailboxAuditingE3.ps1 index f9583b4..186a2f6 100644 --- a/source/tests/Test-MailboxAuditingE3.ps1 +++ b/source/tests/Test-MailboxAuditingE3.ps1 @@ -2,6 +2,7 @@ function Test-MailboxAuditingE3 { [CmdletBinding()] param ( # Aligned + # Create Table for Details # Parameters can be added if needed ) diff --git a/source/tests/Test-MailboxAuditingE5.ps1 b/source/tests/Test-MailboxAuditingE5.ps1 index a2ee587..aab4538 100644 --- a/source/tests/Test-MailboxAuditingE5.ps1 +++ b/source/tests/Test-MailboxAuditingE5.ps1 @@ -1,12 +1,20 @@ function Test-MailboxAuditingE5 { [CmdletBinding()] - param () + param ( + # Aligned + # Create Table for Details + # Parameters can be added if needed + ) begin { + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + $e5SkuPartNumbers = @("SPE_E5", "ENTERPRISEPREMIUM", "OFFICEE5") $AdminActions = @("ApplyRecord", "Copy", "Create", "FolderBind", "HardDelete", "MailItemsAccessed", "Move", "MoveToDeletedItems", "SendAs", "SendOnBehalf", "Send", "SoftDelete", "Update", "UpdateCalendarDelegation", "UpdateFolderPermissions", "UpdateInboxRules") $DelegateActions = @("ApplyRecord", "Create", "FolderBind", "HardDelete", "MailItemsAccessed", "Move", "MoveToDeletedItems", "SendAs", "SendOnBehalf", "SoftDelete", "Update", "UpdateFolderPermissions", "UpdateInboxRules") $OwnerActions = @("ApplyRecord", "Create", "HardDelete", "MailboxLogin", "Move", "MailItemsAccessed", "MoveToDeletedItems", "Send", "SoftDelete", "Update", "UpdateCalendarDelegation", "UpdateFolderPermissions", "UpdateInboxRules") + $auditResult = [CISAuditResult]::new() $auditResult.ELevel = "E5" $auditResult.ProfileLevel = "L1" @@ -31,15 +39,11 @@ function Test-MailboxAuditingE5 { } try { - # Define SKU Part Numbers for Office E5 licenses - # Define SKU Part Numbers for Office E5 licenses - $e5SkuPartNumbers = @("SPE_E5", "ENTERPRISEPREMIUM", "OFFICEE5") $licenseDetails = Get-MgUserLicenseDetail -UserId $user.UserPrincipalName $hasOfficeE5 = ($licenseDetails | Where-Object { $_.SkuPartNumber -in $e5SkuPartNumbers }).Count -gt 0 Write-Verbose "Evaluating user $($user.UserPrincipalName) for Office E5 license." if ($hasOfficeE5) { $userUPN = $user.UserPrincipalName - $mailbox = Get-EXOMailbox -Identity $userUPN -PropertySets Audit $missingActions = @() @@ -78,13 +82,15 @@ function Test-MailboxAuditingE5 { } } - if ($allFailures.Count -eq 0) { - Write-Verbose "All evaluated E5 users have correct mailbox audit settings." - } + # Prepare failure reasons and details based on compliance + $failureReasons = if ($allFailures.Count -eq 0) { "N/A" } else { "Audit issues detected." } + $details = if ($allFailures.Count -eq 0) { "All Office E5 users have correct mailbox audit settings." } else { $allFailures -join " | " } + + # Populate the audit result $auditResult.Result = $allFailures.Count -eq 0 $auditResult.Status = if ($auditResult.Result) { "Pass" } else { "Fail" } - $auditResult.Details = if ($auditResult.Result) { "All Office E5 users have correct mailbox audit settings." } else { $allFailures -join " | " } - $auditResult.FailureReason = if (-not $auditResult.Result) { "Audit issues detected." } else { "N/A" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { @@ -117,4 +123,4 @@ function Format-MissingActions { } return $formattedResults -join '; ' -} \ No newline at end of file +} From 2148a37b35bbb6957b642a318a401dc77a56181d Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:02:25 -0500 Subject: [PATCH 28/67] fix: 6.5.2 aligned with test-template --- source/tests/Test-MailTipsEnabled.ps1 | 39 +++++++++++++++++++-------- 1 file changed, 28 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-MailTipsEnabled.ps1 b/source/tests/Test-MailTipsEnabled.ps1 index 9a2efba..410a066 100644 --- a/source/tests/Test-MailTipsEnabled.ps1 +++ b/source/tests/Test-MailTipsEnabled.ps1 @@ -1,26 +1,45 @@ function Test-MailTipsEnabled { [CmdletBinding()] param ( - # Define your parameters here + # Aligned + # Parameters can be added if needed ) begin { - # Initialization code + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed $auditResult = [CISAuditResult]::new() } process { # 6.5.2 (L2) Ensure MailTips are enabled for end users + + # Retrieve organization configuration for MailTips settings $orgConfig = Get-OrganizationConfig | Select-Object MailTipsAllTipsEnabled, MailTipsExternalRecipientsTipsEnabled, MailTipsGroupMetricsEnabled, MailTipsLargeAudienceThreshold $allTipsEnabled = $orgConfig.MailTipsAllTipsEnabled -and $orgConfig.MailTipsGroupMetricsEnabled -and $orgConfig.MailTipsLargeAudienceThreshold -eq 25 $externalRecipientsTipsEnabled = $orgConfig.MailTipsExternalRecipientsTipsEnabled - # Since there is no direct CIS Control mapping, the control will be set as not applicable. - $auditResult.CISControl = "0" - $auditResult.CISControlVer = "v8" - $auditResult.CISDescription = "Explicitly Not Mapped" + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not ($allTipsEnabled -and $externalRecipientsTipsEnabled)) { + "One or more MailTips settings are not configured as required." + } + else { + "N/A" + } + $details = if ($allTipsEnabled -and $externalRecipientsTipsEnabled) { + "MailTipsAllTipsEnabled: $($orgConfig.MailTipsAllTipsEnabled); MailTipsExternalRecipientsTipsEnabled: $($orgConfig.MailTipsExternalRecipientsTipsEnabled); MailTipsGroupMetricsEnabled: $($orgConfig.MailTipsGroupMetricsEnabled); MailTipsLargeAudienceThreshold: $($orgConfig.MailTipsLargeAudienceThreshold)" + } + else { + "One or more MailTips settings are not configured as required." + } + + # Create and populate the CISAuditResult object + $auditResult.CISControlVer = "v8" + $auditResult.CISControl = "0.0" # Explicitly Not Mapped + $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.Rec = "6.5.2" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L2" @@ -28,16 +47,14 @@ function Test-MailTipsEnabled { $auditResult.IG2 = $false $auditResult.IG3 = $false $auditResult.RecDescription = "Ensure MailTips are enabled for end users" - $auditResult.Result = $allTipsEnabled -and $externalRecipientsTipsEnabled - $auditResult.Details = "MailTipsAllTipsEnabled: $($orgConfig.MailTipsAllTipsEnabled); MailTipsExternalRecipientsTipsEnabled: $($orgConfig.MailTipsExternalRecipientsTipsEnabled); MailTipsGroupMetricsEnabled: $($orgConfig.MailTipsGroupMetricsEnabled); MailTipsLargeAudienceThreshold: $($orgConfig.MailTipsLargeAudienceThreshold)" - $auditResult.FailureReason = if (-not $auditResult.Result) { "One or more MailTips settings are not configured as required." } else { "N/A" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($auditResult.Result) { "Pass" } else { "Fail" } } end { - # Return auditResult + # Return the audit result return $auditResult } } - From e96a5a9d48a1f9cf3ddd151465a030b95cc736d1 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:05:41 -0500 Subject: [PATCH 29/67] fix: 1.2.1 aligned with test-template --- .../Test-ManagedApprovedPublicGroups.ps1 | 53 ++++++++++--------- 1 file changed, 29 insertions(+), 24 deletions(-) diff --git a/source/tests/Test-ManagedApprovedPublicGroups.ps1 b/source/tests/Test-ManagedApprovedPublicGroups.ps1 index b7b708d..7039c7e 100644 --- a/source/tests/Test-ManagedApprovedPublicGroups.ps1 +++ b/source/tests/Test-ManagedApprovedPublicGroups.ps1 @@ -1,21 +1,40 @@ function Test-ManagedApprovedPublicGroups { [CmdletBinding()] param ( - # Define your parameters here + # Aligned + # Parameters can be added if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed - $auditResults = @() } process { # 1.2.1 (L2) Ensure that only organizationally managed/approved public groups exist (Automated) + # Retrieve all public groups $allGroups = Get-MgGroup -All | Where-Object { $_.Visibility -eq "Public" } | Select-Object DisplayName, Visibility - # Check if there are public groups and if they are organizationally managed/approved + # Prepare failure reasons and details based on compliance + $failureReasons = if ($null -ne $allGroups -and $allGroups.Count -gt 0) { + "There are public groups present that are not organizationally managed/approved." + } + else { + "N/A" + } + + $details = if ($null -eq $allGroups -or $allGroups.Count -eq 0) { + "No public groups found." + } + else { + $groupDetails = $allGroups | ForEach-Object { $_.DisplayName + " (" + $_.Visibility + ")" } + "Public groups found: $($groupDetails -join ', ')" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" $auditResult.CISControl = "3.3" @@ -25,30 +44,16 @@ function Test-ManagedApprovedPublicGroups { $auditResult.ProfileLevel = "L2" $auditResult.IG1 = $true $auditResult.IG2 = $true - $auditResult.IG3 = $true # Based on the provided CIS Control image, IG3 is not applicable + $auditResult.IG3 = $true $auditResult.RecDescription = "Ensure that only organizationally managed/approved public groups exist" - - if ($null -eq $allGroups -or $allGroups.Count -eq 0) { - $auditResult.Result = $true - $auditResult.Details = "No public groups found." - $auditResult.FailureReason = "N/A" - $auditResult.Status = "Pass" - } - else { - $groupDetails = $allGroups | ForEach-Object { $_.DisplayName + " (" + $_.Visibility + ")" } - $detailsString = $groupDetails -join ', ' - - $auditResult.Result = $false - $auditResult.Details = "Public groups found: $detailsString" - $auditResult.FailureReason = "There are public groups present that are not organizationally managed/approved." - $auditResult.Status = "Fail" - } - - $auditResults += $auditResult + $auditResult.Result = $null -eq $allGroups -or $allGroups.Count -eq 0 + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons + $auditResult.Status = if ($auditResult.Result) { "Pass" } else { "Fail" } } end { # Return auditResults - return $auditResults + return $auditResult } } From b4c09932403ba45e277992061846eda519f11498 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:09:30 -0500 Subject: [PATCH 30/67] fix: 8.5.5 aligned with test-template --- source/tests/Test-MeetingChatNoAnonymous.ps1 | 31 +++++++++++++------- 1 file changed, 20 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-MeetingChatNoAnonymous.ps1 b/source/tests/Test-MeetingChatNoAnonymous.ps1 index b75835a..5a6035a 100644 --- a/source/tests/Test-MeetingChatNoAnonymous.ps1 +++ b/source/tests/Test-MeetingChatNoAnonymous.ps1 @@ -1,25 +1,36 @@ function Test-MeetingChatNoAnonymous { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 8.5.5 (L2) Ensure meeting chat does not allow anonymous users - # Name doesn't match profile level in benchmarks either. # Connect to Teams PowerShell using Connect-MicrosoftTeams + # Retrieve the Teams meeting policy for meeting chat $CsTeamsMeetingPolicyChat = Get-CsTeamsMeetingPolicy -Identity Global | Select-Object -Property MeetingChatEnabledType $chatAnonDisabled = $CsTeamsMeetingPolicyChat.MeetingChatEnabledType -eq 'EnabledExceptAnonymous' - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if ($chatAnonDisabled) { + "N/A" + } + else { + "Meeting chat allows anonymous users" + } + + $details = "MeetingChatEnabledType is set to $($CsTeamsMeetingPolicyChat.MeetingChatEnabledType)" + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" $auditResult.CISControl = "0.0" # Explicitly Not Mapped as per the image provided @@ -32,15 +43,13 @@ function Test-MeetingChatNoAnonymous { $auditResult.IG3 = $false # Set based on the CIS Controls image $auditResult.RecDescription = "Ensure meeting chat does not allow anonymous users" $auditResult.Result = $chatAnonDisabled - $auditResult.Details = "MeetingChatEnabledType is set to $($CsTeamsMeetingPolicyChat.MeetingChatEnabledType)" - $auditResult.FailureReason = if ($chatAnonDisabled) { "N/A" } else { "Meeting chat allows anonymous users" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($chatAnonDisabled) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 77c74432fe669e0932dc349383cdbf1c7d888a8b Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:13:37 -0500 Subject: [PATCH 31/67] fix: 6.5.1 aligned with test-template --- .../tests/Test-ModernAuthExchangeOnline.ps1 | 56 ++++++++++--------- 1 file changed, 30 insertions(+), 26 deletions(-) diff --git a/source/tests/Test-ModernAuthExchangeOnline.ps1 b/source/tests/Test-ModernAuthExchangeOnline.ps1 index db0c8af..768788c 100644 --- a/source/tests/Test-ModernAuthExchangeOnline.ps1 +++ b/source/tests/Test-ModernAuthExchangeOnline.ps1 @@ -1,40 +1,49 @@ function Test-ModernAuthExchangeOnline { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - - $auditResults = [CISAuditResult]::new() - # Initialization code + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { try { # Ensuring the ExchangeOnlineManagement module is available - # 6.5.1 (L1) Ensure modern authentication for Exchange Online is enabled $orgConfig = Get-OrganizationConfig | Select-Object -Property Name, OAuth2ClientProfileEnabled - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $orgConfig.OAuth2ClientProfileEnabled) { + "Modern authentication is disabled" + } + else { + "N/A" + } - $auditResults.CISControlVer = "v8" - $auditResults.CISControl = "3.10" - $auditResults.CISDescription = "Encrypt Sensitive Data in Transit" - $auditResults.IG1 = $false # As per CIS Control v8 mapping for IG1 - $auditResults.IG2 = $true # As per CIS Control v8 mapping for IG2 - $auditResults.IG3 = $true # As per CIS Control v8 mapping for IG3 - $auditResults.ELevel = "E3" # Based on your environment (E3, E5, etc.) - $auditResults.ProfileLevel = "L1" - $auditResults.Rec = "6.5.1" - $auditResults.RecDescription = "Ensure modern authentication for Exchange Online is enabled (Automated)" - $auditResults.Result = $orgConfig.OAuth2ClientProfileEnabled - $auditResults.Details = $auditResults.Details = $orgConfig.Name + " OAuth2ClientProfileEnabled: " + $orgConfig.OAuth2ClientProfileEnabled - $auditResults.FailureReason = if (-not $orgConfig.OAuth2ClientProfileEnabled) { "Modern authentication is disabled" } else { "N/A" } - $auditResults.Status = if ($orgConfig.OAuth2ClientProfileEnabled) { "Pass" } else { "Fail" } + $details = "OAuth2ClientProfileEnabled: $($orgConfig.OAuth2ClientProfileEnabled) for Organization: $($orgConfig.Name)" + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.CISControlVer = "v8" + $auditResult.CISControl = "3.10" + $auditResult.CISDescription = "Encrypt Sensitive Data in Transit" + $auditResult.IG1 = $false # As per CIS Control v8 mapping for IG1 + $auditResult.IG2 = $true # As per CIS Control v8 mapping for IG2 + $auditResult.IG3 = $true # As per CIS Control v8 mapping for IG3 + $auditResult.ELevel = "E3" # Based on your environment (E3, E5, etc.) + $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "6.5.1" + $auditResult.RecDescription = "Ensure modern authentication for Exchange Online is enabled (Automated)" + $auditResult.Result = $orgConfig.OAuth2ClientProfileEnabled + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons + $auditResult.Status = if ($orgConfig.OAuth2ClientProfileEnabled) { "Pass" } else { "Fail" } } catch { @@ -43,12 +52,7 @@ function Test-ModernAuthExchangeOnline { } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } - - - - - From d5c64910abf6a1213796718e70d7b1a56f0cc68b Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:15:22 -0500 Subject: [PATCH 32/67] fix: 7.2.1 aligned with test-template --- source/tests/Test-ModernAuthSharePoint.ps1 | 26 ++++++++++++++++------ 1 file changed, 19 insertions(+), 7 deletions(-) diff --git a/source/tests/Test-ModernAuthSharePoint.ps1 b/source/tests/Test-ModernAuthSharePoint.ps1 index 0677c3a..7f9f60e 100644 --- a/source/tests/Test-ModernAuthSharePoint.ps1 +++ b/source/tests/Test-ModernAuthSharePoint.ps1 @@ -1,13 +1,14 @@ function Test-ModernAuthSharePoint { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - # Initialization code - - $auditResult = [CISAuditResult]::new() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { @@ -15,7 +16,18 @@ function Test-ModernAuthSharePoint { $SPOTenant = Get-SPOTenant | Select-Object -Property LegacyAuthProtocolsEnabled $modernAuthForSPRequired = -not $SPOTenant.LegacyAuthProtocolsEnabled - # Populate the auditResult object with the required properties + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $modernAuthForSPRequired) { + "Legacy authentication protocols are enabled" + } + else { + "N/A" + } + + $details = "LegacyAuthProtocolsEnabled: $($SPOTenant.LegacyAuthProtocolsEnabled)" + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" $auditResult.CISControl = "3.10" $auditResult.CISDescription = "Encrypt Sensitive Data in Transit" @@ -27,13 +39,13 @@ function Test-ModernAuthSharePoint { $auditResult.IG3 = $true $auditResult.RecDescription = "Modern Authentication for SharePoint Applications" $auditResult.Result = $modernAuthForSPRequired - $auditResult.Details = "LegacyAuthProtocolsEnabled: $($SPOTenant.LegacyAuthProtocolsEnabled)" - $auditResult.FailureReason = if (-not $modernAuthForSPRequired) { "Legacy authentication protocols are enabled" } else { "N/A" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($modernAuthForSPRequired) { "Pass" } else { "Fail" } } end { - # Return auditResult + # Return the audit result return $auditResult } } From c122174cb706e2e25099dab485cb9d5c930a47f6 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:22:23 -0500 Subject: [PATCH 33/67] fix: 8.5.1 aligned with test-template --- source/tests/Test-NoAnonymousMeetingJoin.ps1 | 31 +++++++++++++------- 1 file changed, 20 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-NoAnonymousMeetingJoin.ps1 b/source/tests/Test-NoAnonymousMeetingJoin.ps1 index b72c2f4..af62feb 100644 --- a/source/tests/Test-NoAnonymousMeetingJoin.ps1 +++ b/source/tests/Test-NoAnonymousMeetingJoin.ps1 @@ -1,13 +1,14 @@ function Test-NoAnonymousMeetingJoin { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { @@ -18,7 +19,17 @@ function Test-NoAnonymousMeetingJoin { $teamsMeetingPolicy = Get-CsTeamsMeetingPolicy -Identity Global $allowAnonymousUsersToJoinMeeting = $teamsMeetingPolicy.AllowAnonymousUsersToJoinMeeting - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if ($allowAnonymousUsersToJoinMeeting) { + "Anonymous users are allowed to join meetings" + } + else { + "N/A" + } + + $details = "AllowAnonymousUsersToJoinMeeting is set to $allowAnonymousUsersToJoinMeeting" + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" $auditResult.CISControl = "0.0" # The control is Explicitly Not Mapped as per the image provided @@ -31,15 +42,13 @@ function Test-NoAnonymousMeetingJoin { $auditResult.IG3 = $false # Set based on the CIS Controls image $auditResult.RecDescription = "Ensure anonymous users can't join a meeting" $auditResult.Result = -not $allowAnonymousUsersToJoinMeeting - $auditResult.Details = "AllowAnonymousUsersToJoinMeeting is set to $allowAnonymousUsersToJoinMeeting" - $auditResult.FailureReason = if ($allowAnonymousUsersToJoinMeeting) { "Anonymous users are allowed to join meetings" } else { "N/A" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if (-not $allowAnonymousUsersToJoinMeeting) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } -} +} \ No newline at end of file From 36cb3f1944517adefdfd3e3d3b3151a820f5ac27 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:23:55 -0500 Subject: [PATCH 34/67] fix: 8.5.2 aligned with test-template --- source/tests/Test-NoAnonymousMeetingStart.ps1 | 29 ++++++++++++------- 1 file changed, 19 insertions(+), 10 deletions(-) diff --git a/source/tests/Test-NoAnonymousMeetingStart.ps1 b/source/tests/Test-NoAnonymousMeetingStart.ps1 index 4d5a432..38a6b2d 100644 --- a/source/tests/Test-NoAnonymousMeetingStart.ps1 +++ b/source/tests/Test-NoAnonymousMeetingStart.ps1 @@ -1,13 +1,14 @@ function Test-NoAnonymousMeetingStart { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { @@ -18,7 +19,17 @@ function Test-NoAnonymousMeetingStart { $CsTeamsMeetingPolicyAnonymous = Get-CsTeamsMeetingPolicy -Identity Global | Select-Object -Property AllowAnonymousUsersToStartMeeting $anonymousStartDisabled = -not $CsTeamsMeetingPolicyAnonymous.AllowAnonymousUsersToStartMeeting - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if ($anonymousStartDisabled) { + "N/A" + } + else { + "Anonymous users and dial-in callers can start a meeting" + } + + $details = "AllowAnonymousUsersToStartMeeting is set to $($CsTeamsMeetingPolicyAnonymous.AllowAnonymousUsersToStartMeeting)" + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" $auditResult.CISControl = "0.0" # Explicitly Not Mapped as per the image provided @@ -31,15 +42,13 @@ function Test-NoAnonymousMeetingStart { $auditResult.IG3 = $false # Set based on the CIS Controls image $auditResult.RecDescription = "Ensure anonymous users and dial-in callers can't start a meeting" $auditResult.Result = $anonymousStartDisabled - $auditResult.Details = "AllowAnonymousUsersToStartMeeting is set to $($CsTeamsMeetingPolicyAnonymous.AllowAnonymousUsersToStartMeeting)" - $auditResult.FailureReason = if ($anonymousStartDisabled) { "N/A" } else { "Anonymous users and dial-in callers can start a meeting" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons $auditResult.Status = if ($anonymousStartDisabled) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 3cf76bb6b3fa511e2e703c85b2a6086142d930e4 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:25:57 -0500 Subject: [PATCH 35/67] fix: 2.1.3 aligned with test-template --- source/tests/Test-NotifyMalwareInternal.ps1 | 35 ++++++++++++++------- 1 file changed, 24 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-NotifyMalwareInternal.ps1 b/source/tests/Test-NotifyMalwareInternal.ps1 index 90e7f74..d198668 100644 --- a/source/tests/Test-NotifyMalwareInternal.ps1 +++ b/source/tests/Test-NotifyMalwareInternal.ps1 @@ -1,12 +1,14 @@ function Test-NotifyMalwareInternal { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { @@ -24,10 +26,23 @@ function Test-NotifyMalwareInternal { # Determine the result based on the presence of custom policies without notifications $result = $policiesToReport.Count -eq 0 - $details = if ($result) { "All custom malware policies have notifications enabled." } else { "Misconfigured Policies: $($policiesToReport -join ', ')" } - $failureReason = if ($result) { "N/A" } else { "Some custom policies do not have notifications for internal users sending malware enabled." } - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if ($result) { + "N/A" + } + else { + "Some custom policies do not have notifications for internal users sending malware enabled." + } + + $details = if ($result) { + "All custom malware policies have notifications enabled." + } + else { + "Misconfigured Policies: $($policiesToReport -join ', ')" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($result) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" @@ -42,13 +57,11 @@ function Test-NotifyMalwareInternal { $auditResult.IG3 = $true $auditResult.Result = $result $auditResult.Details = $details - $auditResult.FailureReason = $failureReason - - $auditResults += $auditResult + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } -} +} \ No newline at end of file From c752b7e4fdf151571abf5479d7f1992b7c8ad59b Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:29:07 -0500 Subject: [PATCH 36/67] fix: 6.2.2 aligned with test-template --- source/tests/Test-NoWhitelistDomains.ps1 | 57 ++++++++++++++---------- 1 file changed, 34 insertions(+), 23 deletions(-) diff --git a/source/tests/Test-NoWhitelistDomains.ps1 b/source/tests/Test-NoWhitelistDomains.ps1 index b290dca..2fb6554 100644 --- a/source/tests/Test-NoWhitelistDomains.ps1 +++ b/source/tests/Test-NoWhitelistDomains.ps1 @@ -1,47 +1,58 @@ function Test-NoWhitelistDomains { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - # Initialization code - - $auditResult = [CISAuditResult]::new() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 6.2.2 (L1) Ensure mail transport rules do not whitelist specific domains - $whitelistedRules = Get-TransportRule | Where-Object { $_.SetSCL -eq -1 -and $_.SenderDomainIs -ne $null } - $auditResult.CISControl = "0.0" - $auditResult.CISControlVer = "v8" - $auditResult.CISDescription = "Explicitly Not Mapped" + # Retrieve transport rules that whitelist specific domains + $whitelistedRules = Get-TransportRule | Where-Object { $_.SetSCL -eq -1 -and $null -ne $_.SenderDomainIs } - $auditResult.Rec = "6.2.2" + # Prepare failure reasons and details based on compliance + $failureReasons = if ($whitelistedRules) { + "There are transport rules whitelisting specific domains." + } + else { + "N/A" + } + + $details = if ($whitelistedRules) { + $ruleDetails = $whitelistedRules | ForEach-Object { "{0}: {1}" -f $_.Name, ($_.SenderDomainIs -join ', ') } + "Whitelisted Rules: $($ruleDetails -join '; ')" + } + else { + "No transport rules whitelisting specific domains found." + } + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($whitelistedRules) { "Fail" } else { "Pass" } $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "6.2.2" + $auditResult.RecDescription = "Ensure mail transport rules do not whitelist specific domains" + $auditResult.CISControlVer = "v8" + $auditResult.CISControl = "0.0" + $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.IG1 = $false $auditResult.IG2 = $false $auditResult.IG3 = $false - $auditResult.RecDescription = "Ensure mail transport rules do not whitelist specific domains" - - if ($whitelistedRules) { - $ruleDetails = $whitelistedRules | ForEach-Object { "{0}: {1}" -f $_.Name, ($_.SenderDomainIs -join ', ') } - $auditResult.Result = $false - $auditResult.Details = "Whitelisted Rules: $($ruleDetails -join '; ')" - $auditResult.FailureReason = "There are transport rules whitelisting specific domains." - $auditResult.Status = "Fail" - } else { - $auditResult.Result = $true - $auditResult.Details = "No transport rules whitelisting specific domains found." - $auditResult.FailureReason = "N/A" - $auditResult.Status = "Pass" - } + $auditResult.Result = -not $whitelistedRules + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { # Return auditResult return $auditResult } -} +} \ No newline at end of file From c918f0203e35e17e2a084d77a17205e22a9eafa9 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 11:31:45 -0500 Subject: [PATCH 37/67] fix: 7.2.4 aligned with test-template --- .../Test-OneDriveContentRestrictions.ps1 | 45 +++++++++++++------ 1 file changed, 31 insertions(+), 14 deletions(-) diff --git a/source/tests/Test-OneDriveContentRestrictions.ps1 b/source/tests/Test-OneDriveContentRestrictions.ps1 index 2a610ca..5d52bad 100644 --- a/source/tests/Test-OneDriveContentRestrictions.ps1 +++ b/source/tests/Test-OneDriveContentRestrictions.ps1 @@ -1,41 +1,58 @@ function Test-OneDriveContentRestrictions { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - # Initialization code - - $auditResult = [CISAuditResult]::new() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 7.2.4 (L2) Ensure OneDrive content sharing is restricted + + # Retrieve OneDrive sharing capability settings $SPOTenant = Get-SPOTenant | Select-Object OneDriveSharingCapability $isOneDriveSharingRestricted = $SPOTenant.OneDriveSharingCapability -eq 'Disabled' - # Populate the auditResult object with the required properties + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $isOneDriveSharingRestricted) { + "OneDrive content sharing is not restricted to 'Disabled'. Current setting: $($SPOTenant.OneDriveSharingCapability)" + } + else { + "N/A" + } + + $details = if ($isOneDriveSharingRestricted) { + "OneDrive content sharing is restricted." + } + else { + "OneDriveSharingCapability: $($SPOTenant.OneDriveSharingCapability)" + } + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($isOneDriveSharingRestricted) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" + $auditResult.ProfileLevel = "L2" + $auditResult.Rec = "7.2.4" + $auditResult.RecDescription = "Ensure OneDrive content sharing is restricted" $auditResult.CISControlVer = "v8" $auditResult.CISControl = "3.3" $auditResult.CISDescription = "Configure Data Access Control Lists" - - $auditResult.Rec = "7.2.4" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" $auditResult.IG1 = $true $auditResult.IG2 = $true $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure OneDrive content sharing is restricted" - $auditResult.Result = $isOneDriveSharingRestricted - $auditResult.Details = "OneDriveSharingCapability: $($SPOTenant.OneDriveSharingCapability)" - $auditResult.FailureReason = if (-not $isOneDriveSharingRestricted) { "OneDrive content sharing is not restricted to 'Disabled'. Current setting: $($SPOTenant.OneDriveSharingCapability)" } else { "N/A" } - $auditResult.Status = if ($isOneDriveSharingRestricted) { "Pass" } else { "Fail" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { # Return auditResult return $auditResult } -} +} \ No newline at end of file From 26fa3a8922eb7f88429244bd1800edc9185e9d2f Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 13:08:36 -0500 Subject: [PATCH 38/67] fix: 7.3.2 aligned with test-template --- .../tests/Test-OneDriveSyncRestrictions.ps1 | 43 +++++++++++++------ 1 file changed, 30 insertions(+), 13 deletions(-) diff --git a/source/tests/Test-OneDriveSyncRestrictions.ps1 b/source/tests/Test-OneDriveSyncRestrictions.ps1 index 5b3ca53..67be5d3 100644 --- a/source/tests/Test-OneDriveSyncRestrictions.ps1 +++ b/source/tests/Test-OneDriveSyncRestrictions.ps1 @@ -1,37 +1,54 @@ function Test-OneDriveSyncRestrictions { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - # Initialization code - - $auditResult = [CISAuditResult]::new() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 7.3.2 (L2) Ensure OneDrive sync is restricted for unmanaged devices + + # Retrieve OneDrive sync client restriction settings $SPOTenantSyncClientRestriction = Get-SPOTenantSyncClientRestriction | Select-Object TenantRestrictionEnabled, AllowedDomainList $isSyncRestricted = $SPOTenantSyncClientRestriction.TenantRestrictionEnabled -and $SPOTenantSyncClientRestriction.AllowedDomainList - # Populate the auditResult object with the required properties + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $isSyncRestricted) { + "OneDrive sync is not restricted to managed devices. TenantRestrictionEnabled should be True and AllowedDomainList should contain trusted domains GUIDs." + } + else { + "N/A" + } + + $details = if ($isSyncRestricted) { + "OneDrive sync is restricted for unmanaged devices." + } + else { + "TenantRestrictionEnabled: $($SPOTenantSyncClientRestriction.TenantRestrictionEnabled); AllowedDomainList: $($SPOTenantSyncClientRestriction.AllowedDomainList -join ', ')" + } + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($isSyncRestricted) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" + $auditResult.ProfileLevel = "L2" + $auditResult.Rec = "7.3.2" + $auditResult.RecDescription = "Ensure OneDrive sync is restricted for unmanaged devices" $auditResult.CISControlVer = "v8" $auditResult.CISControl = "0.0" $auditResult.CISDescription = "Explicitly Not Mapped" - - $auditResult.Rec = "7.3.2" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" $auditResult.IG1 = $false $auditResult.IG2 = $false $auditResult.IG3 = $false - $auditResult.RecDescription = "Ensure OneDrive sync is restricted for unmanaged devices" - $auditResult.Result = $isSyncRestricted - $auditResult.Details = "TenantRestrictionEnabled: $($SPOTenantSyncClientRestriction.TenantRestrictionEnabled); AllowedDomainList: $($SPOTenantSyncClientRestriction.AllowedDomainList -join ', ')" - $auditResult.FailureReason = if (-not $isSyncRestricted) { "OneDrive sync is not restricted to managed devices. TenantRestrictionEnabled should be True and AllowedDomainList should contain trusted domains GUIDs." } else { "N/A" } - $auditResult.Status = if ($isSyncRestricted) { "Pass" } else { "Fail" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { From 8d03d1825bbffae361f5d2e854fbfc11ab09139c Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 13:10:32 -0500 Subject: [PATCH 39/67] fix: 8.5.6 aligned with test-template --- source/tests/Test-OrganizersPresent.ps1 | 47 ++++++++++++++++--------- 1 file changed, 31 insertions(+), 16 deletions(-) diff --git a/source/tests/Test-OrganizersPresent.ps1 b/source/tests/Test-OrganizersPresent.ps1 index 8bf8cd6..c47f0d8 100644 --- a/source/tests/Test-OrganizersPresent.ps1 +++ b/source/tests/Test-OrganizersPresent.ps1 @@ -1,13 +1,14 @@ function Test-OrganizersPresent { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { @@ -15,31 +16,45 @@ function Test-OrganizersPresent { # Connect to Teams PowerShell using Connect-MicrosoftTeams + # Retrieve the Teams meeting policy for presenters $CsTeamsMeetingPolicyPresenters = Get-CsTeamsMeetingPolicy -Identity Global | Select-Object -Property DesignatedPresenterRoleMode $presenterRoleRestricted = $CsTeamsMeetingPolicyPresenters.DesignatedPresenterRoleMode -eq 'OrganizerOnlyUserOverride' - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $presenterRoleRestricted) { + "Others besides organizers and co-organizers can present" + } + else { + "N/A" + } + + $details = if ($presenterRoleRestricted) { + "Only organizers and co-organizers can present." + } + else { + "DesignatedPresenterRoleMode is set to $($CsTeamsMeetingPolicyPresenters.DesignatedPresenterRoleMode)" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped as per the image provided - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "8.5.6" + $auditResult.Status = if ($presenterRoleRestricted) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "8.5.6" + $auditResult.RecDescription = "Ensure only organizers and co-organizers can present" + $auditResult.CISControlVer = "v8" + $auditResult.CISControl = "0.0" # Explicitly Not Mapped + $auditResult.CISDescription = "Explicitly Not Mapped" $auditResult.IG1 = $false # Set based on the CIS Controls image $auditResult.IG2 = $false # Set based on the CIS Controls image $auditResult.IG3 = $false # Set based on the CIS Controls image - $auditResult.RecDescription = "Ensure only organizers and co-organizers can present" $auditResult.Result = $presenterRoleRestricted - $auditResult.Details = "DesignatedPresenterRoleMode is set to $($CsTeamsMeetingPolicyPresenters.DesignatedPresenterRoleMode)" - $auditResult.FailureReason = if ($presenterRoleRestricted) { "N/A" } else { "Others besides organizers and co-organizers can present" } - $auditResult.Status = if ($presenterRoleRestricted) { "Pass" } else { "Fail" } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 776b0bf2ecd214da85cb7dd39d0acd8e3ea3e6c4 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 13:12:38 -0500 Subject: [PATCH 40/67] fix: 8.5.3 aligned with test-template --- source/tests/Test-OrgOnlyBypassLobby.ps1 | 45 ++++++++++++++++-------- 1 file changed, 30 insertions(+), 15 deletions(-) diff --git a/source/tests/Test-OrgOnlyBypassLobby.ps1 b/source/tests/Test-OrgOnlyBypassLobby.ps1 index 013fe6d..4a2b5be 100644 --- a/source/tests/Test-OrgOnlyBypassLobby.ps1 +++ b/source/tests/Test-OrgOnlyBypassLobby.ps1 @@ -1,13 +1,14 @@ function Test-OrgOnlyBypassLobby { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { @@ -15,31 +16,45 @@ function Test-OrgOnlyBypassLobby { # Connect to Teams PowerShell using Connect-MicrosoftTeams + # Retrieve the Teams meeting policy for lobby bypass settings $CsTeamsMeetingPolicyLobby = Get-CsTeamsMeetingPolicy -Identity Global | Select-Object -Property AutoAdmittedUsers $lobbyBypassRestricted = $CsTeamsMeetingPolicyLobby.AutoAdmittedUsers -eq 'EveryoneInCompanyExcludingGuests' - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $lobbyBypassRestricted) { + "External participants can bypass the lobby" + } + else { + "N/A" + } + + $details = if ($lobbyBypassRestricted) { + "Only people in the organization can bypass the lobby." + } + else { + "AutoAdmittedUsers is set to $($CsTeamsMeetingPolicyLobby.AutoAdmittedUsers)" + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($lobbyBypassRestricted) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" + $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "8.5.3" + $auditResult.RecDescription = "Ensure only people in my org can bypass the lobby" $auditResult.CISControlVer = "v8" $auditResult.CISControl = "6.8" $auditResult.CISDescription = "Define and Maintain Role-Based Access Control" - $auditResult.Rec = "8.5.3" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" $auditResult.IG1 = $false # Set based on the CIS Controls image $auditResult.IG2 = $false # Set based on the CIS Controls image $auditResult.IG3 = $true # Set based on the CIS Controls image - $auditResult.RecDescription = "Ensure only people in my org can bypass the lobby" $auditResult.Result = $lobbyBypassRestricted - $auditResult.Details = "AutoAdmittedUsers is set to $($CsTeamsMeetingPolicyLobby.AutoAdmittedUsers)" - $auditResult.FailureReason = if ($lobbyBypassRestricted) { "N/A" } else { "External participants can bypass the lobby" } - $auditResult.Status = if ($lobbyBypassRestricted) { "Pass" } else { "Fail" } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 398ce397f525fbf8c73c1e9d002157c8837cc7ba Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 13:14:34 -0500 Subject: [PATCH 41/67] fix: 5.1.8.1 aligned with test-template --- source/tests/Test-PasswordHashSync.ps1 | 35 +++++++++++++++++--------- 1 file changed, 23 insertions(+), 12 deletions(-) diff --git a/source/tests/Test-PasswordHashSync.ps1 b/source/tests/Test-PasswordHashSync.ps1 index df0acca..c65ac31 100644 --- a/source/tests/Test-PasswordHashSync.ps1 +++ b/source/tests/Test-PasswordHashSync.ps1 @@ -1,22 +1,35 @@ function Test-PasswordHashSync { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 5.1.8.1 (L1) Ensure password hash sync is enabled for hybrid deployments # Pass if OnPremisesSyncEnabled is True. Fail otherwise. - $passwordHashSync = Get-MgOrganization | Select-Object OnPremisesSyncEnabled - $hashSyncResult = $passwordHashSync.OnPremisesSyncEnabled - # Create an instance of CISAuditResult and populate it + # Retrieve password hash sync status + $passwordHashSync = Get-MgOrganization | Select-Object -ExpandProperty OnPremisesSyncEnabled + $hashSyncResult = $passwordHashSync + + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $hashSyncResult) { + "Password hash sync for hybrid deployments is not enabled" + } + else { + "N/A" + } + + $details = "OnPremisesSyncEnabled: $($passwordHashSync)" + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($hashSyncResult) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" @@ -30,14 +43,12 @@ function Test-PasswordHashSync { $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.Result = $hashSyncResult - $auditResult.Details = "OnPremisesSyncEnabled: $($passwordHashSync.OnPremisesSyncEnabled)" - $auditResult.FailureReason = if (-not $hashSyncResult) { "Password hash sync for hybrid deployments is not enabled" } else { "N/A" } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 3883e33a4af569b55741ae346e21448062961aff Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 13:17:11 -0500 Subject: [PATCH 42/67] fix: 1.3.1 aligned with test-template --- .../tests/Test-PasswordNeverExpirePolicy.ps1 | 45 +++++++++++-------- 1 file changed, 27 insertions(+), 18 deletions(-) diff --git a/source/tests/Test-PasswordNeverExpirePolicy.ps1 b/source/tests/Test-PasswordNeverExpirePolicy.ps1 index 8faaf24..66e039a 100644 --- a/source/tests/Test-PasswordNeverExpirePolicy.ps1 +++ b/source/tests/Test-PasswordNeverExpirePolicy.ps1 @@ -1,45 +1,54 @@ function Test-PasswordNeverExpirePolicy { [CmdletBinding()] param ( + # Aligned [Parameter(Mandatory)] [string]$DomainName # DomainName parameter is now mandatory ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 1.3.1 (L1) Ensure the 'Password expiration policy' is set to 'Set passwords to never expire' - # Pass if PasswordValidityPeriodInDays is 0. - # Fail otherwise. + # Pass if PasswordValidityPeriodInDays is 0. Fail otherwise. - $passwordPolicy = Get-MgDomain -DomainId $DomainName | Select-Object PasswordValidityPeriodInDays + # Retrieve password expiration policy + $passwordPolicy = Get-MgDomain -DomainId $DomainName | Select-Object -ExpandProperty PasswordValidityPeriodInDays - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if ($passwordPolicy -ne 0) { + "Password expiration is not set to never expire" + } + else { + "N/A" + } + + $details = "Validity Period: $passwordPolicy days" + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() - $auditResult.Rec = "1.3.1" - $auditResult.RecDescription = "Ensure the 'Password expiration policy' is set to 'Set passwords to never expire'" + $auditResult.Status = if ($passwordPolicy -eq 0) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "1.3.1" + $auditResult.RecDescription = "Ensure the 'Password expiration policy' is set to 'Set passwords to never expire'" $auditResult.CISControlVer = "v8" $auditResult.CISControl = "5.2" $auditResult.CISDescription = "Use Unique Passwords" $auditResult.IG1 = $true $auditResult.IG2 = $true - $auditResult.IG3 = $true # All are true - $auditResult.Result = $passwordPolicy.PasswordValidityPeriodInDays -eq 0 - $auditResult.Details = "Validity Period: $($passwordPolicy.PasswordValidityPeriodInDays) days" - $auditResult.FailureReason = if ($passwordPolicy.PasswordValidityPeriodInDays -eq 0) { "N/A" } else { "Password expiration is not set to never expire" } - $auditResult.Status = if ($passwordPolicy.PasswordValidityPeriodInDays -eq 0) { "Pass" } else { "Fail" } - - $auditResults += $auditResult + $auditResult.IG3 = $true + $auditResult.Result = $passwordPolicy -eq 0 + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 5b3c68a8f914c77d263057fded161f0c53baa38b Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 13:19:20 -0500 Subject: [PATCH 43/67] fix: 7.2.10 aligned with test-template --- source/tests/Test-ReauthWithCode.ps1 | 38 ++++++++++++++++++---------- 1 file changed, 25 insertions(+), 13 deletions(-) diff --git a/source/tests/Test-ReauthWithCode.ps1 b/source/tests/Test-ReauthWithCode.ps1 index 9733868..53e600f 100644 --- a/source/tests/Test-ReauthWithCode.ps1 +++ b/source/tests/Test-ReauthWithCode.ps1 @@ -1,37 +1,49 @@ function Test-ReauthWithCode { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - # Initialization code - - $auditResult = [CISAuditResult]::new() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 7.2.10 (L1) Ensure reauthentication with verification code is restricted + + # Retrieve reauthentication settings for SharePoint Online $SPOTenantReauthentication = Get-SPOTenant | Select-Object EmailAttestationRequired, EmailAttestationReAuthDays $isReauthenticationRestricted = $SPOTenantReauthentication.EmailAttestationRequired -and $SPOTenantReauthentication.EmailAttestationReAuthDays -le 15 - # Populate the auditResult object with the required properties + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $isReauthenticationRestricted) { + "Reauthentication with verification code does not require reauthentication within 15 days or less." + } + else { + "N/A" + } + + $details = "EmailAttestationRequired: $($SPOTenantReauthentication.EmailAttestationRequired); EmailAttestationReAuthDays: $($SPOTenantReauthentication.EmailAttestationReAuthDays)" + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($isReauthenticationRestricted) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" + $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "7.2.10" + $auditResult.RecDescription = "Ensure reauthentication with verification code is restricted" $auditResult.CISControlVer = "v8" $auditResult.CISControl = "0.0" $auditResult.CISDescription = "Explicitly Not Mapped" - - $auditResult.Rec = "7.2.10" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" $auditResult.IG1 = $false $auditResult.IG2 = $false $auditResult.IG3 = $false - $auditResult.RecDescription = "Ensure reauthentication with verification code is restricted" - $auditResult.Result = $isReauthenticationRestricted - $auditResult.Details = "EmailAttestationRequired: $($SPOTenantReauthentication.EmailAttestationRequired); EmailAttestationReAuthDays: $($SPOTenantReauthentication.EmailAttestationReAuthDays)" - $auditResult.FailureReason = if (-not $isReauthenticationRestricted) { "Reauthentication with verification code does not require reauthentication within 15 days or less." } else { "N/A" } - $auditResult.Status = if ($isReauthenticationRestricted) { "Pass" } else { "Fail" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { From d511ea7b27bf749a3f507605166e62a4f2fd399e Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 13:21:39 -0500 Subject: [PATCH 44/67] fix: 8.6.1 aligned with test-template --- source/tests/Test-ReportSecurityInTeams.ps1 | 57 ++++++++++++--------- 1 file changed, 32 insertions(+), 25 deletions(-) diff --git a/source/tests/Test-ReportSecurityInTeams.ps1 b/source/tests/Test-ReportSecurityInTeams.ps1 index f7ac954..479847b 100644 --- a/source/tests/Test-ReportSecurityInTeams.ps1 +++ b/source/tests/Test-ReportSecurityInTeams.ps1 @@ -1,21 +1,20 @@ function Test-ReportSecurityInTeams { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 8.6.1 (L1) Ensure users can report security concerns in Teams - # Connect to Teams PowerShell using Connect-MicrosoftTeams - # Connect to Exchange Online PowerShell using Connect-ExchangeOnline - + # Retrieve the necessary settings for Teams and Exchange Online $CsTeamsMessagingPolicy = Get-CsTeamsMessagingPolicy -Identity Global | Select-Object -Property AllowSecurityEndUserReporting $ReportSubmissionPolicy = Get-ReportSubmissionPolicy | Select-Object -Property ReportJunkToCustomizedAddress, ReportNotJunkToCustomizedAddress, ReportPhishToCustomizedAddress, ReportChatMessageToCustomizedAddressEnabled @@ -25,32 +24,40 @@ function Test-ReportSecurityInTeams { $ReportSubmissionPolicy.ReportPhishToCustomizedAddress -and $ReportSubmissionPolicy.ReportChatMessageToCustomizedAddressEnabled - # Create an instance of CISAuditResult and populate it - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped as per the image provided - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "8.6.1" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image - $auditResult.RecDescription = "Ensure users can report security concerns in Teams" - $auditResult.Result = $securityReportEnabled - $auditResult.Details = "AllowSecurityEndUserReporting: $($CsTeamsMessagingPolicy.AllowSecurityEndUserReporting); " + + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $securityReportEnabled) { + "Users cannot report security concerns in Teams due to one or more incorrect settings" + } + else { + "N/A" + } + + $details = "AllowSecurityEndUserReporting: $($CsTeamsMessagingPolicy.AllowSecurityEndUserReporting); " + "ReportJunkToCustomizedAddress: $($ReportSubmissionPolicy.ReportJunkToCustomizedAddress); " + "ReportNotJunkToCustomizedAddress: $($ReportSubmissionPolicy.ReportNotJunkToCustomizedAddress); " + "ReportPhishToCustomizedAddress: $($ReportSubmissionPolicy.ReportPhishToCustomizedAddress); " + "ReportChatMessageToCustomizedAddressEnabled: $($ReportSubmissionPolicy.ReportChatMessageToCustomizedAddressEnabled)" - $auditResult.FailureReason = if (-not $securityReportEnabled) { "Users cannot report security concerns in Teams due to one or more incorrect settings" } else { "N/A" } - $auditResult.Status = if ($securityReportEnabled) { "Pass" } else { "Fail" } - $auditResults += $auditResult + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($securityReportEnabled) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" + $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "8.6.1" + $auditResult.RecDescription = "Ensure users can report security concerns in Teams" + $auditResult.CISControlVer = "v8" + $auditResult.CISControl = "0.0" + $auditResult.CISDescription = "Explicitly Not Mapped" + $auditResult.IG1 = $false + $auditResult.IG2 = $false + $auditResult.IG3 = $false + $auditResult.Result = $securityReportEnabled + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return auditResult + return $auditResult } } From c7cdaa4bf6f17401dbfd38f0181ab3e9f3e7c552 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 13:24:10 -0500 Subject: [PATCH 45/67] fix: 7.3.4 aligned with test-template --- source/tests/Test-RestrictCustomScripts.ps1 | 66 ++++++++++----------- 1 file changed, 32 insertions(+), 34 deletions(-) diff --git a/source/tests/Test-RestrictCustomScripts.ps1 b/source/tests/Test-RestrictCustomScripts.ps1 index 3702ebd..454be84 100644 --- a/source/tests/Test-RestrictCustomScripts.ps1 +++ b/source/tests/Test-RestrictCustomScripts.ps1 @@ -1,21 +1,20 @@ function Test-RestrictCustomScripts { [CmdletBinding()] param ( + # Aligned # Define your parameters here if needed ) -#Limit All - begin { - # .TODO Test behavior in Prod - # Dot source the class script - $auditResults = @() + begin { + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { - # CIS 2.7 Ensure custom script execution is restricted on site collections - # Pass if DenyAddAndCustomizePages is set to true (Enabled). Fail otherwise. + # 7.3.4 (L1) Ensure custom script execution is restricted on site collections - # Get all site collections and select necessary properties + # Retrieve all site collections and select necessary properties $SPOSitesCustomScript = Get-SPOSite -Limit All | Select-Object Title, Url, DenyAddAndCustomizePages # Find sites where custom scripts are allowed (DenyAddAndCustomizePages is not 'Enabled') @@ -29,42 +28,41 @@ function Test-RestrictCustomScripts { "$($_.Title) ($($_.Url)): Custom Script Allowed" } - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $complianceResult) { + "The following site collections allow custom script execution: " + ($nonCompliantSiteDetails -join "; ") + } + else { + "N/A" + } + + $details = if ($complianceResult) { + "All site collections have custom script execution restricted" + } + else { + $nonCompliantSiteDetails -join "; " + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($complianceResult) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" + $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "7.3.4" + $auditResult.RecDescription = "Ensure custom script execution is restricted on site collections" $auditResult.CISControlVer = "v8" $auditResult.CISControl = "2.7" $auditResult.CISDescription = "Allowlist Authorized Scripts" - $auditResult.Rec = "7.3.4" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" $auditResult.IG1 = $false $auditResult.IG2 = $false $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure custom script execution is restricted on site collections" $auditResult.Result = $complianceResult - $auditResult.Details = if (-not $complianceResult) { - $nonCompliantSiteDetails -join "; " - } else { - "All site collections have custom script execution restricted" - } - $auditResult.FailureReason = if (-not $complianceResult) { - "The following site collections allow custom script execution: " + ($nonCompliantSiteDetails -join "; ") - } else { - "N/A" - } - $auditResult.Status = if ($complianceResult) { - "Pass" - } else { - "Fail" - } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } - - end { - # Return auditResults - return $auditResults + # Return auditResult + return $auditResult } } From 75faf04ea6e008b34f4745ed0ea349bae8f000cf Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 13:27:15 -0500 Subject: [PATCH 46/67] fix: 7.2.3 aligned with test-template --- source/tests/Test-RestrictExternalSharing.ps1 | 38 ++++++++++++------- 1 file changed, 25 insertions(+), 13 deletions(-) diff --git a/source/tests/Test-RestrictExternalSharing.ps1 b/source/tests/Test-RestrictExternalSharing.ps1 index 7d7a47c..2034767 100644 --- a/source/tests/Test-RestrictExternalSharing.ps1 +++ b/source/tests/Test-RestrictExternalSharing.ps1 @@ -1,37 +1,49 @@ function Test-RestrictExternalSharing { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - # Initialization code - - $auditResult = [CISAuditResult]::new() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 7.2.3 (L1) Ensure external content sharing is restricted + + # Retrieve the SharingCapability setting for the SharePoint tenant $SPOTenantSharingCapability = Get-SPOTenant | Select-Object SharingCapability $isRestricted = $SPOTenantSharingCapability.SharingCapability -in @('ExternalUserSharingOnly', 'ExistingExternalUserSharingOnly', 'Disabled') - # Populate the auditResult object with the required properties + # Prepare failure reasons and details based on compliance + $failureReasons = if (-not $isRestricted) { + "External content sharing is not adequately restricted. Current setting: $($SPOTenantSharingCapability.SharingCapability)" + } + else { + "N/A" + } + + $details = "SharingCapability: $($SPOTenantSharingCapability.SharingCapability)" + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($isRestricted) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" + $auditResult.ProfileLevel = "L1" + $auditResult.Rec = "7.2.3" + $auditResult.RecDescription = "Ensure external content sharing is restricted" $auditResult.CISControlVer = "v8" $auditResult.CISControl = "3.3" $auditResult.CISDescription = "Configure Data Access Control Lists" - - $auditResult.Rec = "7.2.3" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" $auditResult.IG1 = $true $auditResult.IG2 = $true $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure external content sharing is restricted" - $auditResult.Result = $isRestricted - $auditResult.Details = "SharingCapability: $($SPOTenantSharingCapability.SharingCapability)" - $auditResult.FailureReason = if (-not $isRestricted) { "External content sharing is not adequately restricted. Current setting: $($SPOTenantSharingCapability.SharingCapability)" } else { "N/A" } - $auditResult.Status = if ($isRestricted) { "Pass" } else { "Fail" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { From 2d9342202755418db2e370b130b35daef5e74f7d Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:17:12 -0500 Subject: [PATCH 47/67] fix: 6.3.1 aligned with test-template --- source/tests/Test-RestrictOutlookAddins.ps1 | 56 ++++++++++----------- 1 file changed, 26 insertions(+), 30 deletions(-) diff --git a/source/tests/Test-RestrictOutlookAddins.ps1 b/source/tests/Test-RestrictOutlookAddins.ps1 index be1e635..56934ab 100644 --- a/source/tests/Test-RestrictOutlookAddins.ps1 +++ b/source/tests/Test-RestrictOutlookAddins.ps1 @@ -1,20 +1,20 @@ function Test-RestrictOutlookAddins { [CmdletBinding()] param ( + # Aligned # Parameters could include credentials or other necessary data ) begin { + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 # Initialization code - - $auditResult = [CISAuditResult]::new() $customPolicyFailures = @() $defaultPolicyFailureDetails = @() $relevantRoles = @('My Custom Apps', 'My Marketplace Apps', 'My ReadWriteMailbox Apps') } process { - # Main functionality # 6.3.1 (L2) Ensure users installing Outlook add-ins is not allowed # Check all mailboxes for custom policies with unallowed add-ins @@ -38,24 +38,11 @@ function Test-RestrictOutlookAddins { if ($defaultPolicyRoles) { $defaultPolicyFailureDetails = $defaultPolicyRoles } - } - - end { - # Prepare result object - $auditResult.Rec = "6.3.1" - $auditResult.CISControl = "9.4" - $auditResult.CISDescription = "Restrict Unnecessary or Unauthorized Browser and Email Client Extensions" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $false - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure users installing Outlook add-ins is not allowed" + # Prepare result details string $detailsString = "" if ($customPolicyFailures) { $detailsString += "Custom Policy Failures: | " - # Use pipes or tabs here instead of newlines $detailsString += ($customPolicyFailures -join " | ") } else { @@ -70,20 +57,29 @@ function Test-RestrictOutlookAddins { $detailsString += "Compliant" } - if ($customPolicyFailures -or $defaultPolicyFailureDetails) { - $auditResult.Result = $false - $auditResult.Status = "Fail" - $auditResult.Details = $detailsString - $auditResult.FailureReason = "Unauthorized Outlook add-ins found in custom or default policies." - } - else { - $auditResult.Result = $true - $auditResult.Status = "Pass" - $auditResult.Details = "No unauthorized Outlook add-ins found in custom or default policies." - $auditResult.FailureReason = "N/A" - } + # Determine result based on findings + $isCompliant = -not ($customPolicyFailures -or $defaultPolicyFailureDetails) - # Return auditResult + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($isCompliant) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" + $auditResult.ProfileLevel = "L2" + $auditResult.Rec = "6.3.1" + $auditResult.RecDescription = "Ensure users installing Outlook add-ins is not allowed" + $auditResult.CISControlVer = "v8" + $auditResult.CISControl = "9.4" + $auditResult.CISDescription = "Restrict Unnecessary or Unauthorized Browser and Email Client Extensions" + $auditResult.IG1 = $false + $auditResult.IG2 = $true + $auditResult.IG3 = $true + $auditResult.Result = $isCompliant + $auditResult.Details = $detailsString + $auditResult.FailureReason = if ($isCompliant) { "N/A" } else { "Unauthorized Outlook add-ins found in custom or default policies." } + } + + end { + # Return the audit result return $auditResult } } \ No newline at end of file From 532cb942e8dc2cbf35fefe6c142a57aafaffef43 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:20:06 -0500 Subject: [PATCH 48/67] fix: 6.5.3 aligned with test-template --- .../Test-RestrictStorageProvidersOutlook.ps1 | 57 ++++++++++++------- 1 file changed, 36 insertions(+), 21 deletions(-) diff --git a/source/tests/Test-RestrictStorageProvidersOutlook.ps1 b/source/tests/Test-RestrictStorageProvidersOutlook.ps1 index 1aaf0d4..706c5b6 100644 --- a/source/tests/Test-RestrictStorageProvidersOutlook.ps1 +++ b/source/tests/Test-RestrictStorageProvidersOutlook.ps1 @@ -1,48 +1,63 @@ function Test-RestrictStorageProvidersOutlook { [CmdletBinding()] param ( + # Aligned # Parameters can be added here if needed ) begin { - # Dot source the class script - - $auditResult = [CISAuditResult]::new() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 6.5.3 (L2) Ensure additional storage providers are restricted in Outlook on the web - $owaPolicies = Get-OwaMailboxPolicy - $allPoliciesRestricted = $owaPolicies | ForEach-Object { $_.AdditionalStorageProvidersAvailable } | ForEach-Object { -not $_ } - # Create an instance of CISAuditResult and populate it + # Retrieve all OwaMailbox policies + $owaPolicies = Get-OwaMailboxPolicy + $nonCompliantPolicies = $owaPolicies | Where-Object { $_.AdditionalStorageProvidersAvailable } + + # Determine compliance + $allPoliciesRestricted = $nonCompliantPolicies.Count -eq 0 + + # Prepare failure reasons and details based on compliance + $failureReasons = if ($allPoliciesRestricted) { + "N/A" + } + else { + "One or more OwaMailbox policies allow AdditionalStorageProvidersAvailable." + } + + $details = if ($allPoliciesRestricted) { + "All OwaMailbox policies restrict AdditionalStorageProvidersAvailable" + } + else { + "Non-compliant OwaMailbox policies: $($nonCompliantPolicies.Name -join ', ')" + } + + # Create and populate the CISAuditResult object + $auditResult = [CISAuditResult]::new() + $auditResult.Status = if ($allPoliciesRestricted) { "Pass" } else { "Fail" } + $auditResult.ELevel = "E3" # Based on your environment + $auditResult.ProfileLevel = "L2" + $auditResult.Rec = "6.5.3" + $auditResult.RecDescription = "Ensure additional storage providers are restricted in Outlook on the web" $auditResult.CISControlVer = "v8" $auditResult.CISControl = "3.3" $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.Rec = "6.5.3" - $auditResult.ELevel = "E3" # Based on your environment - $auditResult.ProfileLevel = "L2" $auditResult.IG1 = $true $auditResult.IG2 = $true $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure additional storage providers are restricted in Outlook on the web" $auditResult.Result = $allPoliciesRestricted - $auditResult.Details = if($allPoliciesRestricted) { - "All OwaMailbox policies restrict AdditionalStorageProvidersAvailable" - } else { - $nonCompliantPolicies = $owaPolicies | Where-Object { $_.AdditionalStorageProvidersAvailable } | Select-Object -ExpandProperty Name - "Non-compliant OwaMailbox policies: $($nonCompliantPolicies -join ', ')" - } - $auditResult.FailureReason = if(-not $allPoliciesRestricted) { "One or more OwaMailbox policies allow AdditionalStorageProvidersAvailable." } else { "N/A" } - $auditResult.Status = if($allPoliciesRestricted) { "Pass" } else { "Fail" } + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResult + # Return the audit result return $auditResult } } - # Additional helper functions (if any) - From c1e94ff3bc081aa0f2a7b31d30456d5b82c5131c Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:24:09 -0500 Subject: [PATCH 49/67] fix: 5.1.2.3 aligned with test-template --- source/tests/Test-RestrictTenantCreation.ps1 | 34 +++++++++++++------- 1 file changed, 23 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-RestrictTenantCreation.ps1 b/source/tests/Test-RestrictTenantCreation.ps1 index 887c927..969a146 100644 --- a/source/tests/Test-RestrictTenantCreation.ps1 +++ b/source/tests/Test-RestrictTenantCreation.ps1 @@ -1,22 +1,34 @@ function Test-RestrictTenantCreation { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { - # Dot source the class script - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { # 5.1.2.3 (L1) Ensure 'Restrict non-admin users from creating tenants' is set to 'Yes' - # Pass if AllowedToCreateTenants is False. Fail otherwise. + + # Retrieve the tenant creation policy $tenantCreationPolicy = (Get-MgPolicyAuthorizationPolicy).DefaultUserRolePermissions | Select-Object AllowedToCreateTenants $tenantCreationResult = -not $tenantCreationPolicy.AllowedToCreateTenants - # Create an instance of CISAuditResult and populate it + # Prepare failure reasons and details based on compliance + $failureReasons = if ($tenantCreationResult) { + "N/A" + } + else { + "Non-admin users can create tenants" + } + + $details = "AllowedToCreateTenants: $($tenantCreationPolicy.AllowedToCreateTenants)" + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($tenantCreationResult) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" @@ -30,14 +42,14 @@ function Test-RestrictTenantCreation { $auditResult.IG2 = $false $auditResult.IG3 = $false $auditResult.Result = $tenantCreationResult - $auditResult.Details = "AllowedToCreateTenants: $($tenantCreationPolicy.AllowedToCreateTenants)" - $auditResult.FailureReason = if (-not $tenantCreationResult) { "Non-admin users can create tenants" } else { "N/A" } - - $auditResults += $auditResult + $auditResult.Details = $details + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } + +# Additional helper functions (if any) From d1a5cb8d7382ab765c56ae719ab0098e90ccc5f7 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:26:38 -0500 Subject: [PATCH 50/67] fix: 2.1.4 aligned with test-template --- source/tests/Test-SafeAttachmentsPolicy.ps1 | 35 ++++++++++++++------- 1 file changed, 23 insertions(+), 12 deletions(-) diff --git a/source/tests/Test-SafeAttachmentsPolicy.ps1 b/source/tests/Test-SafeAttachmentsPolicy.ps1 index 588c932..7cf285f 100644 --- a/source/tests/Test-SafeAttachmentsPolicy.ps1 +++ b/source/tests/Test-SafeAttachmentsPolicy.ps1 @@ -1,28 +1,39 @@ function Test-SafeAttachmentsPolicy { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { + # 2.1.4 (L2) Ensure Safe Attachments policy is enabled + # Retrieve all Safe Attachment policies where Enable is set to True $safeAttachmentPolicies = Get-SafeAttachmentPolicy | Where-Object { $_.Enable -eq $true } - # If there are any enabled policies, the result is Pass. If not, it's Fail. - $result = $safeAttachmentPolicies -ne $null -and $safeAttachmentPolicies.Count -gt 0 + # Determine result and details based on the presence of enabled policies + $result = $null -ne $safeAttachmentPolicies -and $safeAttachmentPolicies.Count -gt 0 $details = if ($result) { "Enabled Safe Attachments Policies: $($safeAttachmentPolicies.Name -join ', ')" - } else { + } + else { "No Safe Attachments Policies are enabled." } - $failureReason = if ($result) { "N/A" } else { "Safe Attachments policy is not enabled." } - # Create an instance of CISAuditResult and populate it + $failureReasons = if ($result) { + "N/A" + } + else { + "Safe Attachments policy is not enabled." + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($result) { "Pass" } else { "Fail" } $auditResult.ELevel = "E5" @@ -37,13 +48,13 @@ function Test-SafeAttachmentsPolicy { $auditResult.IG3 = $true $auditResult.Result = $result $auditResult.Details = $details - $auditResult.FailureReason = $failureReason - - $auditResults += $auditResult + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } + +# Additional helper functions (if any) From dbc577bc678e5586725978499d4c36c940010ffc Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:29:09 -0500 Subject: [PATCH 51/67] fix: 2.1.5 aligned with test-template --- source/tests/Test-SafeAttachmentsTeams.ps1 | 32 ++++++++++++++-------- 1 file changed, 21 insertions(+), 11 deletions(-) diff --git a/source/tests/Test-SafeAttachmentsTeams.ps1 b/source/tests/Test-SafeAttachmentsTeams.ps1 index 1647681..649de39 100644 --- a/source/tests/Test-SafeAttachmentsTeams.ps1 +++ b/source/tests/Test-SafeAttachmentsTeams.ps1 @@ -1,16 +1,19 @@ function Test-SafeAttachmentsTeams { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { - # Requires E5 license + # 2.1.5 (L2) Ensure Safe Attachments for SharePoint, OneDrive, and Microsoft Teams is Enabled + # Retrieve the ATP policies for Office 365 and check Safe Attachments settings $atpPolicies = Get-AtpPolicyForO365 @@ -25,12 +28,19 @@ function Test-SafeAttachmentsTeams { $result = $null -ne $atpPolicyResult $details = if ($result) { "ATP for SharePoint, OneDrive, and Teams is enabled with correct settings." - } else { + } + else { "ATP for SharePoint, OneDrive, and Teams is not enabled with correct settings." } - $failureReason = if ($result) { "N/A" } else { "ATP policy for SharePoint, OneDrive, and Microsoft Teams is not correctly configured." } - # Create an instance of CISAuditResult and populate it + $failureReasons = if ($result) { + "N/A" + } + else { + "ATP policy for SharePoint, OneDrive, and Microsoft Teams is not correctly configured." + } + + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($result) { "Pass" } else { "Fail" } $auditResult.ELevel = "E5" @@ -45,13 +55,13 @@ function Test-SafeAttachmentsTeams { $auditResult.IG3 = $true $auditResult.Result = $result $auditResult.Details = $details - $auditResult.FailureReason = $failureReason - - $auditResults += $auditResult + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } + +# Additional helper functions (if any) From 3d84a8679364e847697db4726a815e6bb5d40912 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:34:17 -0500 Subject: [PATCH 52/67] fix: 2.1.1 aligned with test-template --- source/tests/Test-SafeLinksOfficeApps.ps1 | 20 +++++++++++--------- 1 file changed, 11 insertions(+), 9 deletions(-) diff --git a/source/tests/Test-SafeLinksOfficeApps.ps1 b/source/tests/Test-SafeLinksOfficeApps.ps1 index 22bec97..0779515 100644 --- a/source/tests/Test-SafeLinksOfficeApps.ps1 +++ b/source/tests/Test-SafeLinksOfficeApps.ps1 @@ -1,16 +1,19 @@ function Test-SafeLinksOfficeApps { [CmdletBinding()] param ( + # Aligned # Define your parameters here if needed ) begin { - # Initialization code - - $auditResults = @() + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed } process { + # 2.1.1 (L2) Ensure Safe Links for Office Applications is Enabled + # Retrieve all Safe Links policies $policies = Get-SafeLinksPolicy @@ -42,8 +45,9 @@ function Test-SafeLinksOfficeApps { # Prepare the final result $result = $misconfiguredDetails.Count -eq 0 $details = if ($result) { "All Safe Links policies are correctly configured." } else { $misconfiguredDetails -join ' | ' } + $failureReasons = if ($result) { "N/A" } else { "The following Safe Links policies settings do not meet the recommended configuration: $($misconfiguredDetails -join ' | ')" } - # Create the audit result object + # Create and populate the CISAuditResult object $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($result) { "Pass" } else { "Fail" } $auditResult.ELevel = "E5" @@ -58,13 +62,11 @@ function Test-SafeLinksOfficeApps { $auditResult.IG3 = $true $auditResult.Result = $result $auditResult.Details = $details - $auditResult.FailureReason = if ($result) { "N/A" } else { "The following Safe Links policies settings do not meet the recommended configuration: $($misconfiguredDetails -join ' | ')" } - - $auditResults += $auditResult + $auditResult.FailureReason = $failureReasons } end { - # Return auditResults - return $auditResults + # Return the audit result + return $auditResult } } From 87db439d66aed5210c8c12d1c891983c5e769eff Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:38:28 -0500 Subject: [PATCH 53/67] fix: 7.2.2 aligned with test-template --- source/tests/Test-SharePointAADB2B.ps1 | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/source/tests/Test-SharePointAADB2B.ps1 b/source/tests/Test-SharePointAADB2B.ps1 index 2a93edb..49817ce 100644 --- a/source/tests/Test-SharePointAADB2B.ps1 +++ b/source/tests/Test-SharePointAADB2B.ps1 @@ -1,11 +1,14 @@ function Test-SharePointAADB2B { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - # Initialization code + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed $auditResult = [CISAuditResult]::new() } @@ -18,7 +21,6 @@ function Test-SharePointAADB2B { $auditResult.CISControlVer = "v8" $auditResult.CISControl = "0.0" $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "7.2.2" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" @@ -26,7 +28,6 @@ function Test-SharePointAADB2B { $auditResult.IG2 = $false $auditResult.IG3 = $false $auditResult.RecDescription = "Ensure SharePoint and OneDrive integration with Azure AD B2B is enabled" - $auditResult.Result = $SPOTenantAzureADB2B.EnableAzureADB2BIntegration $auditResult.Details = "EnableAzureADB2BIntegration: $($SPOTenantAzureADB2B.EnableAzureADB2BIntegration)" $auditResult.FailureReason = if (-not $SPOTenantAzureADB2B.EnableAzureADB2BIntegration) { "Azure AD B2B integration is not enabled" } else { "N/A" } @@ -37,4 +38,4 @@ function Test-SharePointAADB2B { # Return auditResult return $auditResult } -} +} \ No newline at end of file From 69306732092bc540a2eca4180fe54a7dd564a4ee Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:40:56 -0500 Subject: [PATCH 54/67] fix: 7.2.6 aligned with test-template --- source/tests/Test-SharePointExternalSharingDomains.ps1 | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/source/tests/Test-SharePointExternalSharingDomains.ps1 b/source/tests/Test-SharePointExternalSharingDomains.ps1 index 5e30c94..05b65b8 100644 --- a/source/tests/Test-SharePointExternalSharingDomains.ps1 +++ b/source/tests/Test-SharePointExternalSharingDomains.ps1 @@ -1,11 +1,14 @@ function Test-SharePointExternalSharingDomains { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - # Initialization code + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed $auditResult = [CISAuditResult]::new() } @@ -19,7 +22,6 @@ function Test-SharePointExternalSharingDomains { $auditResult.CISControlVer = "v8" $auditResult.CISControl = "3.3" $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.Rec = "7.2.6" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L2" @@ -27,7 +29,6 @@ function Test-SharePointExternalSharingDomains { $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.RecDescription = "Ensure SharePoint external sharing is managed through domain whitelist/blacklists" - $auditResult.Result = $isDomainRestrictionConfigured $auditResult.Details = "SharingDomainRestrictionMode: $($SPOTenant.SharingDomainRestrictionMode); SharingAllowedDomainList: $($SPOTenant.SharingAllowedDomainList)" $auditResult.FailureReason = if (-not $isDomainRestrictionConfigured) { "Domain restrictions for SharePoint external sharing are not configured to 'AllowList'. Current setting: $($SPOTenant.SharingDomainRestrictionMode)" } else { "N/A" } From deec4c4f5e56b90f0d63b4b345c0beb1a669c059 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:43:30 -0500 Subject: [PATCH 55/67] fix: 7.2.5 aligned with test-template --- source/tests/Test-SharePointGuestsItemSharing.ps1 | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/source/tests/Test-SharePointGuestsItemSharing.ps1 b/source/tests/Test-SharePointGuestsItemSharing.ps1 index ac50ac6..bff9180 100644 --- a/source/tests/Test-SharePointGuestsItemSharing.ps1 +++ b/source/tests/Test-SharePointGuestsItemSharing.ps1 @@ -1,11 +1,14 @@ function Test-SharePointGuestsItemSharing { [CmdletBinding()] param ( + # Aligned # Define your parameters here ) begin { - # Initialization code + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed $auditResult = [CISAuditResult]::new() } @@ -19,7 +22,6 @@ function Test-SharePointGuestsItemSharing { $auditResult.CISControlVer = "v8" $auditResult.CISControl = "3.3" $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.Rec = "7.2.5" $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L2" @@ -27,7 +29,6 @@ function Test-SharePointGuestsItemSharing { $auditResult.IG2 = $true $auditResult.IG3 = $true $auditResult.RecDescription = "Ensure that SharePoint guest users cannot share items they don't own" - $auditResult.Result = $isGuestResharingPrevented $auditResult.Details = "PreventExternalUsersFromResharing: $isGuestResharingPrevented" $auditResult.FailureReason = if (-not $isGuestResharingPrevented) { "Guest users can reshare items they don't own." } else { "N/A" } From 050ea83acd88e4d12a8bfd5c4f59953c35920e21 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:47:42 -0500 Subject: [PATCH 56/67] fix: 2.1.6 aligned with test-template --- source/tests/Test-SpamPolicyAdminNotify.ps1 | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) diff --git a/source/tests/Test-SpamPolicyAdminNotify.ps1 b/source/tests/Test-SpamPolicyAdminNotify.ps1 index ebe2d81..4e822ec 100644 --- a/source/tests/Test-SpamPolicyAdminNotify.ps1 +++ b/source/tests/Test-SpamPolicyAdminNotify.ps1 @@ -1,16 +1,20 @@ function Test-SpamPolicyAdminNotify { [CmdletBinding()] param ( + # Aligned # Parameters can be added if needed ) begin { + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed - $auditResults = @() + $auditResult = [CISAuditResult]::new() } process { - # 2.1.6 Ensure Exchange Online Spam Policies are set to notify administrators + # 2.1.6 Ensure Exchange Online Spam Policies are set to notify administrators # Get the default hosted outbound spam filter policy $hostedOutboundSpamFilterPolicy = Get-HostedOutboundSpamFilterPolicy | Where-Object { $_.IsDefault -eq $true } @@ -30,7 +34,6 @@ function Test-SpamPolicyAdminNotify { } # Create an instance of CISAuditResult and populate it - $auditResult = [CISAuditResult]::new() $auditResult.Status = if ($areSettingsEnabled) { "Pass" } else { "Fail" } $auditResult.ELevel = "E3" $auditResult.ProfileLevel = "L1" @@ -45,14 +48,10 @@ function Test-SpamPolicyAdminNotify { $auditResult.Result = $areSettingsEnabled $auditResult.Details = if ($areSettingsEnabled) { "Both BccSuspiciousOutboundMail and NotifyOutboundSpam are enabled." } else { $failureDetails -join ' ' } $auditResult.FailureReason = if (-not $areSettingsEnabled) { "One or both spam policies are not set to notify administrators." } else { "N/A" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return auditResult + return $auditResult } } - - From f445893aedf717014ba0c207e9b1338c1dbfbfe2 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:49:23 -0500 Subject: [PATCH 57/67] fix: 8.2.1 aligned with test-template --- source/tests/Test-TeamsExternalAccess.ps1 | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/source/tests/Test-TeamsExternalAccess.ps1 b/source/tests/Test-TeamsExternalAccess.ps1 index ef4d67d..06b98eb 100644 --- a/source/tests/Test-TeamsExternalAccess.ps1 +++ b/source/tests/Test-TeamsExternalAccess.ps1 @@ -1,13 +1,16 @@ function Test-TeamsExternalAccess { [CmdletBinding()] param ( + # Aligned # Parameters can be defined here if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed - $auditResults = @() + $auditResult = [CISAuditResult]::new() } process { @@ -26,7 +29,6 @@ function Test-TeamsExternalAccess { $isCompliant = -not $externalAccessConfig.AllowTeamsConsumer -and -not $externalAccessConfig.AllowPublicUsers -and (-not $externalAccessConfig.AllowFederatedUsers -or $allowedDomainsLimited) # Create an instance of CISAuditResult and populate it - $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" $auditResult.CISControl = "0.0" # The control is Explicitly Not Mapped as per the image provided $auditResult.CISDescription = "Explicitly Not Mapped" @@ -41,12 +43,10 @@ function Test-TeamsExternalAccess { $auditResult.Details = "AllowTeamsConsumer: $($externalAccessConfig.AllowTeamsConsumer); AllowPublicUsers: $($externalAccessConfig.AllowPublicUsers); AllowFederatedUsers: $($externalAccessConfig.AllowFederatedUsers); AllowedDomains limited: $allowedDomainsLimited" $auditResult.FailureReason = if (-not $isCompliant) { "One or more external access configurations are not compliant." } else { "N/A" } $auditResult.Status = if ($isCompliant) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return auditResult + return $auditResult } } From 686272d4e09bb58bbfe10abd9a2a3a04e5981762 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:51:24 -0500 Subject: [PATCH 58/67] fix: 8.1.1 aligned with test-template --- source/tests/Test-TeamsExternalFileSharing.ps1 | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/source/tests/Test-TeamsExternalFileSharing.ps1 b/source/tests/Test-TeamsExternalFileSharing.ps1 index 0c7d5ba..9226a64 100644 --- a/source/tests/Test-TeamsExternalFileSharing.ps1 +++ b/source/tests/Test-TeamsExternalFileSharing.ps1 @@ -1,13 +1,16 @@ function Test-TeamsExternalFileSharing { [CmdletBinding()] param ( + # Aligned # Parameters can be added here if needed ) begin { - # Dot source the class script + # Dot source the class script if necessary + #. .\source\Classes\CISAuditResult.ps1 + # Initialization code, if needed - $auditResults = @() + $auditResult = [CISAuditResult]::new() } process { @@ -30,7 +33,6 @@ function Test-TeamsExternalFileSharing { } # Create an instance of CISAuditResult and populate it - $auditResult = [CISAuditResult]::new() $auditResult.CISControlVer = "v8" $auditResult.CISControl = "3.3" $auditResult.CISDescription = "Configure Data Access Control Lists" @@ -45,12 +47,10 @@ function Test-TeamsExternalFileSharing { $auditResult.Details = if (-not $isCompliant) { "Non-approved providers enabled: $($nonCompliantProviders -join ', ')" } else { "All cloud storage services are approved providers" } $auditResult.FailureReason = if (-not $isCompliant) { "The following non-approved providers are enabled: $($nonCompliantProviders -join ', ')" } else { "N/A" } $auditResult.Status = if ($isCompliant) { "Pass" } else { "Fail" } - - $auditResults += $auditResult } end { - # Return auditResults - return $auditResults + # Return auditResult + return $auditResult } -} \ No newline at end of file +} From 8505439516ba084750e725fc8bb888cf5a2b4144 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 14:54:32 -0500 Subject: [PATCH 59/67] fix: class comment aligned with test-template --- source/tests/Test-ExternalNoControl.ps1 | 2 +- source/tests/Test-ExternalSharingCalendars.ps1 | 2 +- source/tests/Test-GuestAccessExpiration.ps1 | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/source/tests/Test-ExternalNoControl.ps1 b/source/tests/Test-ExternalNoControl.ps1 index f3745ef..1fe7e7c 100644 --- a/source/tests/Test-ExternalNoControl.ps1 +++ b/source/tests/Test-ExternalNoControl.ps1 @@ -7,7 +7,7 @@ function Test-ExternalNoControl { begin { # Dot source the class script if necessary - # . .\source\Classes\CISAuditResult.ps1 + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-ExternalSharingCalendars.ps1 b/source/tests/Test-ExternalSharingCalendars.ps1 index 17e6dce..b37e8de 100644 --- a/source/tests/Test-ExternalSharingCalendars.ps1 +++ b/source/tests/Test-ExternalSharingCalendars.ps1 @@ -7,7 +7,7 @@ function Test-ExternalSharingCalendars { begin { # Dot source the class script if necessary - # . .\source\Classes\CISAuditResult.ps1 + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } diff --git a/source/tests/Test-GuestAccessExpiration.ps1 b/source/tests/Test-GuestAccessExpiration.ps1 index d1e6f24..db002a1 100644 --- a/source/tests/Test-GuestAccessExpiration.ps1 +++ b/source/tests/Test-GuestAccessExpiration.ps1 @@ -7,7 +7,7 @@ function Test-GuestAccessExpiration { begin { # Dot source the class script if necessary - # . .\source\Classes\CISAuditResult.ps1 + #. .\source\Classes\CISAuditResult.ps1 # Initialization code, if needed } From 129bb33a996303a166db7478af50e837d626ac58 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 17:08:04 -0500 Subject: [PATCH 60/67] add: New testing function --- source/Classes/CISAuditResult.ps1 | 2 + source/Private/Initialize-CISAuditResult.ps1 | 55 +++++++++++++++ .../Test-AdministrativeAccountCompliance.ps1 | 34 +++++---- source/tests/Test-AntiPhishingPolicy.ps1 | 34 +++++---- source/tests/Test-AuditDisabledFalse.ps1 | 26 +++---- source/tests/Test-AuditLogSearch.ps1 | 27 ++++--- source/tests/Test-BlockChannelEmails.ps1 | 26 +++---- source/tests/Test-BlockMailForwarding.ps1 | 27 +++---- .../tests/Test-BlockSharedMailboxSignIn.ps1 | 26 +++---- source/tests/Test-CommonAttachmentFilter.ps1 | 26 +++---- source/tests/Test-CustomerLockbox.ps1 | 28 ++++---- source/tests/Test-DialInBypassLobby.ps1 | 26 +++---- .../Test-DisallowInfectedFilesDownload.ps1 | 27 ++++--- source/tests/Test-EnableDKIM.ps1 | 26 +++---- source/tests/Test-ExternalNoControl.ps1 | 26 +++---- .../tests/Test-ExternalSharingCalendars.ps1 | 26 +++---- source/tests/Test-GlobalAdminsCount.ps1 | 26 +++---- source/tests/Test-GuestAccessExpiration.ps1 | 26 +++---- .../tests/Test-GuestUsersBiweeklyReview.ps1 | 70 ++++++++----------- source/tests/Test-IdentifyExternalEmail.ps1 | 26 +++---- source/tests/Test-LinkSharingRestrictions.ps1 | 26 +++---- source/tests/Test-MailTipsEnabled.ps1 | 25 +++---- source/tests/Test-MailboxAuditingE3.ps1 | 26 +++---- source/tests/Test-MailboxAuditingE5.ps1 | 27 ++++--- .../Test-ManagedApprovedPublicGroups.ps1 | 26 +++---- source/tests/Test-MeetingChatNoAnonymous.ps1 | 26 +++---- .../tests/Test-ModernAuthExchangeOnline.ps1 | 26 +++---- source/tests/Test-ModernAuthSharePoint.ps1 | 26 +++---- source/tests/Test-NoAnonymousMeetingJoin.ps1 | 26 +++---- source/tests/Test-NoAnonymousMeetingStart.ps1 | 26 +++---- source/tests/Test-NoWhitelistDomains.ps1 | 26 +++---- source/tests/Test-NotifyMalwareInternal.ps1 | 26 +++---- .../Test-OneDriveContentRestrictions.ps1 | 26 +++---- .../tests/Test-OneDriveSyncRestrictions.ps1 | 26 +++---- source/tests/Test-OrgOnlyBypassLobby.ps1 | 26 +++---- source/tests/Test-OrganizersPresent.ps1 | 26 +++---- source/tests/Test-PasswordHashSync.ps1 | 26 +++---- .../tests/Test-PasswordNeverExpirePolicy.ps1 | 26 +++---- source/tests/Test-ReauthWithCode.ps1 | 26 +++---- source/tests/Test-ReportSecurityInTeams.ps1 | 26 +++---- source/tests/Test-RestrictCustomScripts.ps1 | 26 +++---- source/tests/Test-RestrictExternalSharing.ps1 | 26 +++---- source/tests/Test-RestrictOutlookAddins.ps1 | 26 +++---- .../Test-RestrictStorageProvidersOutlook.ps1 | 26 +++---- source/tests/Test-RestrictTenantCreation.ps1 | 26 +++---- source/tests/Test-SafeAttachmentsPolicy.ps1 | 26 +++---- source/tests/Test-SafeAttachmentsTeams.ps1 | 26 +++---- source/tests/Test-SafeLinksOfficeApps.ps1 | 26 +++---- source/tests/Test-SharePointAADB2B.ps1 | 25 +++---- .../Test-SharePointExternalSharingDomains.ps1 | 25 +++---- .../Test-SharePointGuestsItemSharing.ps1 | 25 +++---- source/tests/Test-SpamPolicyAdminNotify.ps1 | 25 +++---- source/tests/Test-TeamsExternalAccess.ps1 | 25 +++---- .../tests/Test-TeamsExternalFileSharing.ps1 | 25 +++---- .../Initialize-CISAuditResult.tests.ps1 | 27 +++++++ 55 files changed, 691 insertions(+), 804 deletions(-) create mode 100644 source/Private/Initialize-CISAuditResult.ps1 create mode 100644 tests/Unit/Private/Initialize-CISAuditResult.tests.ps1 diff --git a/source/Classes/CISAuditResult.ps1 b/source/Classes/CISAuditResult.ps1 index 8d04777..2cc80fd 100644 --- a/source/Classes/CISAuditResult.ps1 +++ b/source/Classes/CISAuditResult.ps1 @@ -2,6 +2,8 @@ class CISAuditResult { [string]$Status [string]$ELevel [string]$ProfileLevel + [bool]$Automated + [string]$Connection [string]$Rec [string]$RecDescription [string]$CISControlVer = 'v8' diff --git a/source/Private/Initialize-CISAuditResult.ps1 b/source/Private/Initialize-CISAuditResult.ps1 new file mode 100644 index 0000000..6cc1e40 --- /dev/null +++ b/source/Private/Initialize-CISAuditResult.ps1 @@ -0,0 +1,55 @@ +function Initialize-CISAuditResult { + param ( + [Parameter(Mandatory = $true)] + [string]$Rec, + + [Parameter(Mandatory = $true)] + [bool]$Result, + + [Parameter(Mandatory = $true)] + [string]$Status, + + [Parameter(Mandatory = $true)] + [string]$Details, + + [Parameter(Mandatory = $true)] + [string]$FailureReason, + + [Parameter(Mandatory = $true)] + [string]$RecDescription, + + [Parameter(Mandatory = $true)] + [string]$CISControl, + + [Parameter(Mandatory = $true)] + [string]$CISDescription + ) + + # Import the test definitions CSV file + $testDefinitionsPath = Join-Path -Path $PSScriptRoot -ChildPath "helper/TestDefinitions.csv" + $testDefinitions = Import-Csv -Path $testDefinitionsPath + + # Find the row that matches the provided recommendation (Rec) + $testDefinition = $testDefinitions | Where-Object { $_.Rec -eq $Rec } + + # Create an instance of CISAuditResult and populate it + $auditResult = [CISAuditResult]::new() + $auditResult.Rec = $Rec + $auditResult.ELevel = $testDefinition.ELevel + $auditResult.ProfileLevel = $testDefinition.ProfileLevel + $auditResult.IG1 = [bool]::Parse($testDefinition.IG1) + $auditResult.IG2 = [bool]::Parse($testDefinition.IG2) + $auditResult.IG3 = [bool]::Parse($testDefinition.IG3) + $auditResult.RecDescription = $RecDescription + $auditResult.CISControl = $CISControl + $auditResult.CISDescription = $CISDescription + $auditResult.Automated = [bool]::Parse($testDefinition.Automated) + $auditResult.Connection = $testDefinition.Connection + $auditResult.CISControlVer = 'v8' + $auditResult.Result = $Result + $auditResult.Status = $Status + $auditResult.Details = $Details + $auditResult.FailureReason = $FailureReason + + return $auditResult +} diff --git a/source/tests/Test-AdministrativeAccountCompliance.ps1 b/source/tests/Test-AdministrativeAccountCompliance.ps1 index 3e6dce1..66cc0a9 100644 --- a/source/tests/Test-AdministrativeAccountCompliance.ps1 +++ b/source/tests/Test-AdministrativeAccountCompliance.ps1 @@ -4,10 +4,12 @@ function Test-AdministrativeAccountCompliance { # Aligned # Parameters can be added if needed ) + begin { #. .\source\Classes\CISAuditResult.ps1 $validLicenses = @('AAD_PREMIUM', 'AAD_PREMIUM_P2') } + process { $adminRoles = Get-MgRoleManagementDirectoryRoleDefinition | Where-Object { $_.DisplayName -like "*Admin*" } $adminRoleUsers = @() @@ -58,21 +60,23 @@ function Test-AdministrativeAccountCompliance { "Compliant Accounts: $($uniqueAdminRoleUsers.Count)" } - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($nonCompliantUsers) { 'Fail' } else { 'Pass' } - $auditResult.ELevel = 'E3' - $auditResult.ProfileLevel = 'L1' - $auditResult.Rec = '1.1.1' - $auditResult.RecDescription = "Ensure Administrative accounts are separate and cloud-only" - $auditResult.CISControlVer = 'v8' - $auditResult.CISControl = "5.4" - $auditResult.CISDescription = "Restrict Administrator Privileges to Dedicated Administrator Accounts" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $nonCompliantUsers.Count -eq 0 - $auditResult.Details = $Details - $auditResult.FailureReason = if ($nonCompliantUsers) { "Non-compliant accounts: `nUsername | Roles | HybridStatus | Missing Licence`n$failureReasons" } else { "N/A" } + $result = $nonCompliantUsers.Count -eq 0 + $status = if ($result) { 'Pass' } else { 'Fail' } + $failureReason = if ($nonCompliantUsers) { "Non-compliant accounts: `nUsername | Roles | HybridStatus | Missing Licence`n$failureReasons" } else { "N/A" } + + # Create the parameter splat + $params = @{ + Rec = "1.1.1" + Result = $result + Status = $status + Details = $details + FailureReason = $failureReason + RecDescription = "Ensure Administrative accounts are separate and cloud-only" + CISControl = "5.4" + CISDescription = "Restrict Administrator Privileges to Dedicated Administrator Accounts" + } + + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-AntiPhishingPolicy.ps1 b/source/tests/Test-AntiPhishingPolicy.ps1 index 4b669db..a9b26e8 100644 --- a/source/tests/Test-AntiPhishingPolicy.ps1 +++ b/source/tests/Test-AntiPhishingPolicy.ps1 @@ -40,7 +40,8 @@ function Test-AntiPhishingPolicy { $nonCompliantNames = $nonCompliantItems | ForEach-Object { $_.Name } $failureReasons = if ($nonCompliantNames.Count -gt 0) { "Reason: Does not meet one or more compliance criteria.`nNon-compliant Policies:`n" + ($nonCompliantNames -join "`n") - } else { + } + else { "N/A" } @@ -58,27 +59,24 @@ function Test-AntiPhishingPolicy { "Compliant Items: $($compliantItems.Count)" } - # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($isCompliant) { "Pass" } else { "Fail" } - $auditResult.ELevel = 'E5' # Modify as needed - $auditResult.ProfileLevel = 'L1' # Modify as needed - $auditResult.Rec = '2.1.7' # Modify as needed - $auditResult.RecDescription = "Ensure that an anti-phishing policy has been created" # Modify as needed - $auditResult.CISControlVer = 'v8' # Modify as needed - $auditResult.CISControl = "9.7" # Modify as needed - $auditResult.CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections" # Modify as needed - $auditResult.IG1 = $false # Modify as needed - $auditResult.IG2 = $false # Modify as needed - $auditResult.IG3 = $true # Modify as needed - $auditResult.Result = $nonCompliantItems.Count -eq 0 - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + # Parameter splat for Initialize-CISAuditResult function + $params = @{ + Rec = "2.1.7" + Result = $nonCompliantItems.Count -eq 0 + Status = if ($isCompliant) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure that an anti-phishing policy has been created" + CISControl = "9.7" + CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections" + } + # Create and populate the CISAuditResult object + $auditResult = Initialize-CISAuditResult @params } end { - # Return auditResults + # Return auditResult return $auditResult } } diff --git a/source/tests/Test-AuditDisabledFalse.ps1 b/source/tests/Test-AuditDisabledFalse.ps1 index 1ba0362..69e09d6 100644 --- a/source/tests/Test-AuditDisabledFalse.ps1 +++ b/source/tests/Test-AuditDisabledFalse.ps1 @@ -34,21 +34,17 @@ function Test-AuditDisabledFalse { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($auditNotDisabled) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "6.1.1" - $auditResult.RecDescription = "Ensure 'AuditDisabled' organizationally is set to 'False'" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "8.2" - $auditResult.CISDescription = "Collect Audit Logs" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $auditNotDisabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "6.1.1" + Result = $auditNotDisabled + Status = if ($auditNotDisabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure 'AuditDisabled' organizationally is set to 'False'" + CISControl = "8.2" + CISDescription = "Collect Audit Logs" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-AuditLogSearch.ps1 b/source/tests/Test-AuditLogSearch.ps1 index 48a0c91..f1c51fe 100644 --- a/source/tests/Test-AuditLogSearch.ps1 +++ b/source/tests/Test-AuditLogSearch.ps1 @@ -34,21 +34,18 @@ function Test-AuditLogSearch { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($auditLogResult) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "3.1.1" - $auditResult.RecDescription = "Ensure Microsoft 365 audit log search is Enabled" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "8.2" - $auditResult.CISDescription = "Collect Audit Logs" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $auditLogResult - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "3.1.1" + Result = $auditLogResult + Status = if ($auditLogResult) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure Microsoft 365 audit log search is Enabled" + CISControl = "8.2" + CISDescription = "Collect Audit Logs" + } + $auditResult = Initialize-CISAuditResult @params + } end { diff --git a/source/tests/Test-BlockChannelEmails.ps1 b/source/tests/Test-BlockChannelEmails.ps1 index f69a5c0..917f1b2 100644 --- a/source/tests/Test-BlockChannelEmails.ps1 +++ b/source/tests/Test-BlockChannelEmails.ps1 @@ -34,21 +34,17 @@ function Test-BlockChannelEmails { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # This control is explicitly not mapped as per the image provided - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "8.1.2" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Set based on the benchmark - $auditResult.IG2 = $false # Set based on the benchmark - $auditResult.IG3 = $false # Set based on the benchmark - $auditResult.RecDescription = "Ensure users can't send emails to a channel email address" - $auditResult.Result = -not $allowEmailIntoChannel - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if (-not $allowEmailIntoChannel) { "Pass" } else { "Fail" } + $params = @{ + Rec = "8.1.2" + Result = -not $allowEmailIntoChannel + Status = if (-not $allowEmailIntoChannel) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure users can't send emails to a channel email address" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-BlockMailForwarding.ps1 b/source/tests/Test-BlockMailForwarding.ps1 index f00377d..c7a25a4 100644 --- a/source/tests/Test-BlockMailForwarding.ps1 +++ b/source/tests/Test-BlockMailForwarding.ps1 @@ -35,22 +35,17 @@ function Test-BlockMailForwarding { "Step 1: No forwarding rules found. Please proceed with Step 2 described in CIS Benchmark." } - # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Rec = "6.2.1" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.RecDescription = "Ensure all forms of mail forwarding are blocked and/or disabled" - $auditResult.Result = $forwardingBlocked - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($forwardingBlocked) { "Pass" } else { "Fail" } + $params = @{ + Rec = "6.2.1" + Result = $forwardingBlocked + Status = if ($forwardingBlocked) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure all forms of mail forwarding are blocked and/or disabled" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-BlockSharedMailboxSignIn.ps1 b/source/tests/Test-BlockSharedMailboxSignIn.ps1 index 958d434..e3da822 100644 --- a/source/tests/Test-BlockSharedMailboxSignIn.ps1 +++ b/source/tests/Test-BlockSharedMailboxSignIn.ps1 @@ -36,21 +36,17 @@ function Test-BlockSharedMailboxSignIn { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Control is explicitly not mapped - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "1.2.2" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Control is not mapped, hence IG1 is false - $auditResult.IG2 = $false # Control is not mapped, hence IG2 is false - $auditResult.IG3 = $false # Control is not mapped, hence IG3 is false - $auditResult.RecDescription = "Ensure sign-in to shared mailboxes is blocked" - $auditResult.Result = $allBlocked - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($allBlocked) { "Pass" } else { "Fail" } + $params = @{ + Rec = "1.2.2" + Result = $allBlocked + Status = if ($allBlocked) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure sign-in to shared mailboxes is blocked" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-CommonAttachmentFilter.ps1 b/source/tests/Test-CommonAttachmentFilter.ps1 index 5d4e356..7229291 100644 --- a/source/tests/Test-CommonAttachmentFilter.ps1 +++ b/source/tests/Test-CommonAttachmentFilter.ps1 @@ -34,21 +34,17 @@ function Test-CommonAttachmentFilter { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($result) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "2.1.2" - $auditResult.RecDescription = "Ensure the Common Attachment Types Filter is enabled" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "9.6" - $auditResult.CISDescription = "Block Unnecessary File Types" - $auditResult.IG1 = $false - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $result - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "2.1.2" + Result = $result + Status = if ($result) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure the Common Attachment Types Filter is enabled" + CISControl = "9.6" + CISDescription = "Block Unnecessary File Types" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-CustomerLockbox.ps1 b/source/tests/Test-CustomerLockbox.ps1 index 2404203..b5e418b 100644 --- a/source/tests/Test-CustomerLockbox.ps1 +++ b/source/tests/Test-CustomerLockbox.ps1 @@ -33,22 +33,18 @@ function Test-CustomerLockbox { "Customer Lockbox Enabled: False" } - # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($customerLockboxEnabled) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E5" - $auditResult.ProfileLevel = "L2" - $auditResult.Rec = "1.3.6" - $auditResult.RecDescription = "Ensure the customer lockbox feature is enabled" - $auditResult.CISControlVer = 'v8' - $auditResult.CISControl = "0.0" # As per the snapshot provided, this is explicitly not mapped - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.Result = $customerLockboxEnabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + # Create and populate the CISAuditResult object # + $params = @{ + Rec = "1.3.6" + Result = $customerLockboxEnabled + Status = if ($customerLockboxEnabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure the customer lockbox feature is enabled" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-DialInBypassLobby.ps1 b/source/tests/Test-DialInBypassLobby.ps1 index 0d3eefb..f2ec463 100644 --- a/source/tests/Test-DialInBypassLobby.ps1 +++ b/source/tests/Test-DialInBypassLobby.ps1 @@ -34,21 +34,17 @@ function Test-DialInBypassLobby { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "8.5.4" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image - $auditResult.RecDescription = "Ensure users dialing in can't bypass the lobby" - $auditResult.Result = $PSTNBypassDisabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($PSTNBypassDisabled) { "Pass" } else { "Fail" } + $params = @{ + Rec = "8.5.4" + Result = $PSTNBypassDisabled + Status = if ($PSTNBypassDisabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure users dialing in can't bypass the lobby" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-DisallowInfectedFilesDownload.ps1 b/source/tests/Test-DisallowInfectedFilesDownload.ps1 index 67778fc..865e22e 100644 --- a/source/tests/Test-DisallowInfectedFilesDownload.ps1 +++ b/source/tests/Test-DisallowInfectedFilesDownload.ps1 @@ -35,21 +35,18 @@ function Test-DisallowInfectedFilesDownload { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "10.1" - $auditResult.CISDescription = "Deploy and Maintain Anti-Malware Software" - $auditResult.Rec = "7.3.1" - $auditResult.ELevel = "E5" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure Office 365 SharePoint infected files are disallowed for download" - $auditResult.Result = $isDisallowInfectedFileDownloadEnabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($isDisallowInfectedFileDownloadEnabled) { "Pass" } else { "Fail" } + $params = @{ + Rec = "7.3.1" + Result = $isDisallowInfectedFileDownloadEnabled + Status = if ($isDisallowInfectedFileDownloadEnabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure Office 365 SharePoint infected files are disallowed for download" + CISControl = "10.1" + CISDescription = "Deploy and Maintain Anti-Malware Software" + } + $auditResult = Initialize-CISAuditResult @params + } end { diff --git a/source/tests/Test-EnableDKIM.ps1 b/source/tests/Test-EnableDKIM.ps1 index 607fad2..806a862 100644 --- a/source/tests/Test-EnableDKIM.ps1 +++ b/source/tests/Test-EnableDKIM.ps1 @@ -35,21 +35,17 @@ function Test-EnableDKIM { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($dkimResult) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "2.1.9" - $auditResult.RecDescription = "Ensure that DKIM is enabled for all Exchange Online Domains" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "9.5" - $auditResult.CISDescription = "Implement DMARC" - $auditResult.IG1 = $false - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $dkimResult - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "2.1.9" + Result = $dkimResult + Status = if ($dkimResult) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure that DKIM is enabled for all Exchange Online Domains" + CISControl = "9.5" + CISDescription = "Implement DMARC" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-ExternalNoControl.ps1 b/source/tests/Test-ExternalNoControl.ps1 index 1fe7e7c..bf9c814 100644 --- a/source/tests/Test-ExternalNoControl.ps1 +++ b/source/tests/Test-ExternalNoControl.ps1 @@ -35,21 +35,17 @@ function Test-ExternalNoControl { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "8.5.7" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image - $auditResult.RecDescription = "Ensure external participants can't give or request control" - $auditResult.Result = $externalControlRestricted - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($externalControlRestricted) { "Pass" } else { "Fail" } + $params = @{ + Rec = "8.5.7" + Result = $externalControlRestricted + Status = if ($externalControlRestricted) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure external participants can't give or request control" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-ExternalSharingCalendars.ps1 b/source/tests/Test-ExternalSharingCalendars.ps1 index b37e8de..abc4d00 100644 --- a/source/tests/Test-ExternalSharingCalendars.ps1 +++ b/source/tests/Test-ExternalSharingCalendars.ps1 @@ -44,21 +44,17 @@ function Test-ExternalSharingCalendars { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Rec = "1.3.3" - $auditResult.RecDescription = "Ensure 'External sharing' of calendars is not available" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $false - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "4.8" - $auditResult.CISDescription = "Uninstall or Disable Unnecessary Services on Enterprise Assets and Software" - $auditResult.Result = $isExternalSharingDisabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($isExternalSharingDisabled) { "Pass" } else { "Fail" } + $params = @{ + Rec = "1.3.3" + Result = $isExternalSharingDisabled + Status = if ($isExternalSharingDisabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure 'External sharing' of calendars is not available" + CISControl = "4.8" + CISDescription = "Uninstall or Disable Unnecessary Services on Enterprise Assets and Software" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-GlobalAdminsCount.ps1 b/source/tests/Test-GlobalAdminsCount.ps1 index a01089a..1a77c34 100644 --- a/source/tests/Test-GlobalAdminsCount.ps1 +++ b/source/tests/Test-GlobalAdminsCount.ps1 @@ -35,21 +35,17 @@ function Test-GlobalAdminsCount { $details = "Count: $globalAdminCount; Users: $globalAdminUsernames" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "5.1" - $auditResult.CISDescription = "Establish and Maintain an Inventory of Accounts" - $auditResult.Rec = "1.1.3" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure that between two and four global admins are designated" - $auditResult.Result = $globalAdminCount -ge 2 -and $globalAdminCount -le 4 - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($globalAdminCount -ge 2 -and $globalAdminCount -le 4) { "Pass" } else { "Fail" } + $params = @{ + Rec = "1.1.3" + Result = $globalAdminCount -ge 2 -and $globalAdminCount -le 4 + Status = if ($globalAdminCount -ge 2 -and $globalAdminCount -le 4) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure that between two and four global admins are designated" + CISControl = "5.1" + CISDescription = "Establish and Maintain an Inventory of Accounts" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-GuestAccessExpiration.ps1 b/source/tests/Test-GuestAccessExpiration.ps1 index db002a1..2c2ca16 100644 --- a/source/tests/Test-GuestAccessExpiration.ps1 +++ b/source/tests/Test-GuestAccessExpiration.ps1 @@ -30,21 +30,17 @@ function Test-GuestAccessExpiration { $details = "ExternalUserExpirationRequired: $($SPOTenantGuestAccess.ExternalUserExpirationRequired); ExternalUserExpireInDays: $($SPOTenantGuestAccess.ExternalUserExpireInDays)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "7.2.9" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.RecDescription = "Ensure guest access to a site or OneDrive will expire automatically" - $auditResult.Result = $isGuestAccessExpirationConfiguredCorrectly - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($isGuestAccessExpirationConfiguredCorrectly) { "Pass" } else { "Fail" } + $params = @{ + Rec = "7.2.9" + Result = $isGuestAccessExpirationConfiguredCorrectly + Status = if ($isGuestAccessExpirationConfiguredCorrectly) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure guest access to a site or OneDrive will expire automatically" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-GuestUsersBiweeklyReview.ps1 b/source/tests/Test-GuestUsersBiweeklyReview.ps1 index 64bd6c9..e25e462 100644 --- a/source/tests/Test-GuestUsersBiweeklyReview.ps1 +++ b/source/tests/Test-GuestUsersBiweeklyReview.ps1 @@ -15,51 +15,39 @@ function Test-GuestUsersBiweeklyReview { process { # 1.1.4 (L1) Ensure Guest Users are reviewed at least biweekly - try { - # Retrieve guest users from Microsoft Graph - # Connect-MgGraph -Scopes "User.Read.All" - $guestUsers = Get-MgUser -All -Filter "UserType eq 'Guest'" - # Prepare failure reasons and details based on compliance - $failureReasons = if ($guestUsers) { - "Guest users present: $($guestUsers.Count)" - } - else { - "N/A" - } + # Retrieve guest users from Microsoft Graph + # Connect-MgGraph -Scopes "User.Read.All" + $guestUsers = Get-MgUser -All -Filter "UserType eq 'Guest'" - $details = if ($guestUsers) { - $auditCommand = "Get-MgUser -All -Property UserType,UserPrincipalName | Where {`$_.UserType -ne 'Member'} | Format-Table UserPrincipalName, UserType" - "Manual review required. To list guest users, run: `"$auditCommand`"." - } - else { - "No guest users found." - } - - # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControl = "5.1, 5.3" - $auditResult.CISDescription = "Establish and Maintain an Inventory of Accounts, Disable Dormant Accounts" - $auditResult.Rec = "1.1.4" - $auditResult.RecDescription = "Ensure Guest Users are reviewed at least biweekly" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.CISControlVer = 'v8' - $auditResult.Result = -not $guestUsers - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($guestUsers) { "Fail" } else { "Pass" } + # Prepare failure reasons and details based on compliance + $failureReasons = if ($guestUsers) { + "Guest users present: $($guestUsers.Count)" } - catch { - $auditResult = [CISAuditResult]::new() - $auditResult.Status = "Error" - $auditResult.Result = $false - $auditResult.Details = "Error while attempting to check guest users. Error message: $($_.Exception.Message)" - $auditResult.FailureReason = "An error occurred during the audit check." + else { + "N/A" } + + $details = if ($guestUsers) { + $auditCommand = "Get-MgUser -All -Property UserType,UserPrincipalName | Where {`$_.UserType -ne 'Member'} | Format-Table UserPrincipalName, UserType" + "Manual review required. To list guest users, run: `"$auditCommand`"." + } + else { + "No guest users found." + } + + # Create and populate the CISAuditResult object + $params = @{ + Rec = "1.1.4" + Result = -not $guestUsers + Status = if ($guestUsers) { "Fail" } else { "Pass" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure Guest Users are reviewed at least biweekly" + CISControl = "5.1, 5.3" + CISDescription = "Establish and Maintain an Inventory of Accounts, Disable Dormant Accounts" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-IdentifyExternalEmail.ps1 b/source/tests/Test-IdentifyExternalEmail.ps1 index a876c7d..784c048 100644 --- a/source/tests/Test-IdentifyExternalEmail.ps1 +++ b/source/tests/Test-IdentifyExternalEmail.ps1 @@ -30,21 +30,17 @@ function Test-IdentifyExternalEmail { $details = "Enabled: $($externalTaggingEnabled); AllowList: $($externalInOutlook.AllowList)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($externalTaggingEnabled) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "6.2.3" - $auditResult.RecDescription = "Ensure email from external senders is identified" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.Result = $externalTaggingEnabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "6.2.3" + Result = $externalTaggingEnabled + Status = if ($externalTaggingEnabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure email from external senders is identified" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-LinkSharingRestrictions.ps1 b/source/tests/Test-LinkSharingRestrictions.ps1 index a2bcaba..8f1f142 100644 --- a/source/tests/Test-LinkSharingRestrictions.ps1 +++ b/source/tests/Test-LinkSharingRestrictions.ps1 @@ -30,21 +30,17 @@ function Test-LinkSharingRestrictions { $details = "DefaultSharingLinkType: $($SPOTenantLinkSharing.DefaultSharingLinkType)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($isLinkSharingRestricted) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "7.2.7" - $auditResult.RecDescription = "Ensure link sharing is restricted in SharePoint and OneDrive" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.3" - $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $isLinkSharingRestricted - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "7.2.7" + Result = $isLinkSharingRestricted + Status = if ($isLinkSharingRestricted) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure link sharing is restricted in SharePoint and OneDrive" + CISControl = "3.3" + CISDescription = "Configure Data Access Control Lists" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-MailTipsEnabled.ps1 b/source/tests/Test-MailTipsEnabled.ps1 index 410a066..bfa8475 100644 --- a/source/tests/Test-MailTipsEnabled.ps1 +++ b/source/tests/Test-MailTipsEnabled.ps1 @@ -37,20 +37,17 @@ function Test-MailTipsEnabled { } # Create and populate the CISAuditResult object - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "6.5.2" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.RecDescription = "Ensure MailTips are enabled for end users" - $auditResult.Result = $allTipsEnabled -and $externalRecipientsTipsEnabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($auditResult.Result) { "Pass" } else { "Fail" } + $params = @{ + Rec = "6.5.2" + Result = $allTipsEnabled -and $externalRecipientsTipsEnabled + Status = if ($allTipsEnabled -and $externalRecipientsTipsEnabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure MailTips are enabled for end users" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-MailboxAuditingE3.ps1 b/source/tests/Test-MailboxAuditingE3.ps1 index 186a2f6..68361aa 100644 --- a/source/tests/Test-MailboxAuditingE3.ps1 +++ b/source/tests/Test-MailboxAuditingE3.ps1 @@ -15,17 +15,6 @@ function Test-MailboxAuditingE3 { $DelegateActions = @("ApplyRecord", "Create", "FolderBind", "HardDelete", "Move", "MoveToDeletedItems", "SendAs", "SendOnBehalf", "SoftDelete", "Update", "UpdateFolderPermissions", "UpdateInboxRules") $OwnerActions = @("ApplyRecord", "Create", "HardDelete", "MailboxLogin", "Move", "MoveToDeletedItems", "SoftDelete", "Update", "UpdateCalendarDelegation", "UpdateFolderPermissions", "UpdateInboxRules") - $auditResult = [CISAuditResult]::new() - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "6.1.2" - $auditResult.RecDescription = "Ensure mailbox auditing for Office E3 users is Enabled" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "8.2" - $auditResult.CISDescription = "Collect audit logs." - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true $allFailures = @() $allUsers = Get-AzureADUser -All $true @@ -82,10 +71,17 @@ function Test-MailboxAuditingE3 { $details = if ($allFailures.Count -eq 0) { "All Office E3 users have correct mailbox audit settings." } else { $allFailures -join " | " } # Populate the audit result - $auditResult.Result = $allFailures.Count -eq 0 - $auditResult.Status = if ($auditResult.Result) { "Pass" } else { "Fail" } - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "6.1.2" + Result = $allFailures.Count -eq 0 + Status = if ($allFailures.Count -eq 0) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure mailbox auditing for Office E3 users is Enabled" + CISControl = "8.2" + CISDescription = "Collect audit logs." + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-MailboxAuditingE5.ps1 b/source/tests/Test-MailboxAuditingE5.ps1 index aab4538..c4c3dc4 100644 --- a/source/tests/Test-MailboxAuditingE5.ps1 +++ b/source/tests/Test-MailboxAuditingE5.ps1 @@ -15,17 +15,7 @@ function Test-MailboxAuditingE5 { $DelegateActions = @("ApplyRecord", "Create", "FolderBind", "HardDelete", "MailItemsAccessed", "Move", "MoveToDeletedItems", "SendAs", "SendOnBehalf", "SoftDelete", "Update", "UpdateFolderPermissions", "UpdateInboxRules") $OwnerActions = @("ApplyRecord", "Create", "HardDelete", "MailboxLogin", "Move", "MailItemsAccessed", "MoveToDeletedItems", "Send", "SoftDelete", "Update", "UpdateCalendarDelegation", "UpdateFolderPermissions", "UpdateInboxRules") - $auditResult = [CISAuditResult]::new() - $auditResult.ELevel = "E5" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "6.1.3" - $auditResult.RecDescription = "Ensure mailbox auditing for Office E5 users is Enabled" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "8.2" - $auditResult.CISDescription = "Collect audit logs." - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true + $allFailures = @() $allUsers = Get-AzureADUser -All $true @@ -87,10 +77,17 @@ function Test-MailboxAuditingE5 { $details = if ($allFailures.Count -eq 0) { "All Office E5 users have correct mailbox audit settings." } else { $allFailures -join " | " } # Populate the audit result - $auditResult.Result = $allFailures.Count -eq 0 - $auditResult.Status = if ($auditResult.Result) { "Pass" } else { "Fail" } - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "6.1.3" + Result = $allFailures.Count -eq 0 + Status = if ($allFailures.Count -eq 0) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure mailbox auditing for Office E5 users is Enabled" + CISControl = "8.2" + CISDescription = "Collect audit logs." + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-ManagedApprovedPublicGroups.ps1 b/source/tests/Test-ManagedApprovedPublicGroups.ps1 index 7039c7e..8a0cf52 100644 --- a/source/tests/Test-ManagedApprovedPublicGroups.ps1 +++ b/source/tests/Test-ManagedApprovedPublicGroups.ps1 @@ -35,21 +35,17 @@ function Test-ManagedApprovedPublicGroups { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.3" - $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.Rec = "1.2.1" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure that only organizationally managed/approved public groups exist" - $auditResult.Result = $null -eq $allGroups -or $allGroups.Count -eq 0 - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($auditResult.Result) { "Pass" } else { "Fail" } + $params = @{ + Rec = "1.2.1" + Result = $null -eq $allGroups -or $allGroups.Count -eq 0 + Status = if ($null -eq $allGroups -or $allGroups.Count -eq 0) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure that only organizationally managed/approved public groups exist" + CISControl = "3.3" + CISDescription = "Configure Data Access Control Lists" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-MeetingChatNoAnonymous.ps1 b/source/tests/Test-MeetingChatNoAnonymous.ps1 index 5a6035a..67d1b84 100644 --- a/source/tests/Test-MeetingChatNoAnonymous.ps1 +++ b/source/tests/Test-MeetingChatNoAnonymous.ps1 @@ -31,21 +31,17 @@ function Test-MeetingChatNoAnonymous { $details = "MeetingChatEnabledType is set to $($CsTeamsMeetingPolicyChat.MeetingChatEnabledType)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped as per the image provided - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "8.5.5" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image - $auditResult.RecDescription = "Ensure meeting chat does not allow anonymous users" - $auditResult.Result = $chatAnonDisabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($chatAnonDisabled) { "Pass" } else { "Fail" } + $params = @{ + Rec = "8.5.5" + Result = $chatAnonDisabled + Status = if ($chatAnonDisabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure meeting chat does not allow anonymous users" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-ModernAuthExchangeOnline.ps1 b/source/tests/Test-ModernAuthExchangeOnline.ps1 index 768788c..da2df32 100644 --- a/source/tests/Test-ModernAuthExchangeOnline.ps1 +++ b/source/tests/Test-ModernAuthExchangeOnline.ps1 @@ -29,21 +29,17 @@ function Test-ModernAuthExchangeOnline { $details = "OAuth2ClientProfileEnabled: $($orgConfig.OAuth2ClientProfileEnabled) for Organization: $($orgConfig.Name)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.10" - $auditResult.CISDescription = "Encrypt Sensitive Data in Transit" - $auditResult.IG1 = $false # As per CIS Control v8 mapping for IG1 - $auditResult.IG2 = $true # As per CIS Control v8 mapping for IG2 - $auditResult.IG3 = $true # As per CIS Control v8 mapping for IG3 - $auditResult.ELevel = "E3" # Based on your environment (E3, E5, etc.) - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "6.5.1" - $auditResult.RecDescription = "Ensure modern authentication for Exchange Online is enabled (Automated)" - $auditResult.Result = $orgConfig.OAuth2ClientProfileEnabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($orgConfig.OAuth2ClientProfileEnabled) { "Pass" } else { "Fail" } + $params = @{ + Rec = "6.5.1" + Result = $orgConfig.OAuth2ClientProfileEnabled + Status = if ($orgConfig.OAuth2ClientProfileEnabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure modern authentication for Exchange Online is enabled (Automated)" + CISControl = "3.10" + CISDescription = "Encrypt Sensitive Data in Transit" + } + $auditResult = Initialize-CISAuditResult @params } catch { diff --git a/source/tests/Test-ModernAuthSharePoint.ps1 b/source/tests/Test-ModernAuthSharePoint.ps1 index 7f9f60e..c8c06a0 100644 --- a/source/tests/Test-ModernAuthSharePoint.ps1 +++ b/source/tests/Test-ModernAuthSharePoint.ps1 @@ -27,21 +27,17 @@ function Test-ModernAuthSharePoint { $details = "LegacyAuthProtocolsEnabled: $($SPOTenant.LegacyAuthProtocolsEnabled)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.10" - $auditResult.CISDescription = "Encrypt Sensitive Data in Transit" - $auditResult.Rec = "7.2.1" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.RecDescription = "Modern Authentication for SharePoint Applications" - $auditResult.Result = $modernAuthForSPRequired - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($modernAuthForSPRequired) { "Pass" } else { "Fail" } + $params = @{ + Rec = "7.2.1" + Result = $modernAuthForSPRequired + Status = if ($modernAuthForSPRequired) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Modern Authentication for SharePoint Applications" + CISControl = "3.10" + CISDescription = "Encrypt Sensitive Data in Transit" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-NoAnonymousMeetingJoin.ps1 b/source/tests/Test-NoAnonymousMeetingJoin.ps1 index af62feb..cb5e42b 100644 --- a/source/tests/Test-NoAnonymousMeetingJoin.ps1 +++ b/source/tests/Test-NoAnonymousMeetingJoin.ps1 @@ -30,21 +30,17 @@ function Test-NoAnonymousMeetingJoin { $details = "AllowAnonymousUsersToJoinMeeting is set to $allowAnonymousUsersToJoinMeeting" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # The control is Explicitly Not Mapped as per the image provided - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "8.5.1" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image - $auditResult.RecDescription = "Ensure anonymous users can't join a meeting" - $auditResult.Result = -not $allowAnonymousUsersToJoinMeeting - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if (-not $allowAnonymousUsersToJoinMeeting) { "Pass" } else { "Fail" } + $params = @{ + Rec = "8.5.1" + Result = -not $allowAnonymousUsersToJoinMeeting + Status = if (-not $allowAnonymousUsersToJoinMeeting) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure anonymous users can't join a meeting" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-NoAnonymousMeetingStart.ps1 b/source/tests/Test-NoAnonymousMeetingStart.ps1 index 38a6b2d..c520b05 100644 --- a/source/tests/Test-NoAnonymousMeetingStart.ps1 +++ b/source/tests/Test-NoAnonymousMeetingStart.ps1 @@ -30,21 +30,17 @@ function Test-NoAnonymousMeetingStart { $details = "AllowAnonymousUsersToStartMeeting is set to $($CsTeamsMeetingPolicyAnonymous.AllowAnonymousUsersToStartMeeting)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped as per the image provided - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "8.5.2" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image - $auditResult.RecDescription = "Ensure anonymous users and dial-in callers can't start a meeting" - $auditResult.Result = $anonymousStartDisabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons - $auditResult.Status = if ($anonymousStartDisabled) { "Pass" } else { "Fail" } + $params = @{ + Rec = "8.5.2" + Result = $anonymousStartDisabled + Status = if ($anonymousStartDisabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure anonymous users and dial-in callers can't start a meeting" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-NoWhitelistDomains.ps1 b/source/tests/Test-NoWhitelistDomains.ps1 index 2fb6554..9632762 100644 --- a/source/tests/Test-NoWhitelistDomains.ps1 +++ b/source/tests/Test-NoWhitelistDomains.ps1 @@ -34,21 +34,17 @@ function Test-NoWhitelistDomains { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($whitelistedRules) { "Fail" } else { "Pass" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "6.2.2" - $auditResult.RecDescription = "Ensure mail transport rules do not whitelist specific domains" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.Result = -not $whitelistedRules - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "6.2.2" + Result = -not $whitelistedRules + Status = if ($whitelistedRules) { "Fail" } else { "Pass" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure mail transport rules do not whitelist specific domains" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-NotifyMalwareInternal.ps1 b/source/tests/Test-NotifyMalwareInternal.ps1 index d198668..3d83262 100644 --- a/source/tests/Test-NotifyMalwareInternal.ps1 +++ b/source/tests/Test-NotifyMalwareInternal.ps1 @@ -43,21 +43,17 @@ function Test-NotifyMalwareInternal { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($result) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "2.1.3" - $auditResult.RecDescription = "Ensure notifications for internal users sending malware is Enabled" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "17.5" - $auditResult.CISDescription = "Assign Key Roles and Responsibilities" - $auditResult.IG1 = $false - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $result - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "2.1.3" + Result = $result + Status = if ($result) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure notifications for internal users sending malware is Enabled" + CISControl = "17.5" + CISDescription = "Assign Key Roles and Responsibilities" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-OneDriveContentRestrictions.ps1 b/source/tests/Test-OneDriveContentRestrictions.ps1 index 5d52bad..5905619 100644 --- a/source/tests/Test-OneDriveContentRestrictions.ps1 +++ b/source/tests/Test-OneDriveContentRestrictions.ps1 @@ -34,21 +34,17 @@ function Test-OneDriveContentRestrictions { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($isOneDriveSharingRestricted) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.Rec = "7.2.4" - $auditResult.RecDescription = "Ensure OneDrive content sharing is restricted" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.3" - $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $isOneDriveSharingRestricted - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "7.2.4" + Result = $isOneDriveSharingRestricted + Status = if ($isOneDriveSharingRestricted) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure OneDrive content sharing is restricted" + CISControl = "3.3" + CISDescription = "Configure Data Access Control Lists" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-OneDriveSyncRestrictions.ps1 b/source/tests/Test-OneDriveSyncRestrictions.ps1 index 67be5d3..6b6b95b 100644 --- a/source/tests/Test-OneDriveSyncRestrictions.ps1 +++ b/source/tests/Test-OneDriveSyncRestrictions.ps1 @@ -34,21 +34,17 @@ function Test-OneDriveSyncRestrictions { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($isSyncRestricted) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.Rec = "7.3.2" - $auditResult.RecDescription = "Ensure OneDrive sync is restricted for unmanaged devices" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.Result = $isSyncRestricted - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "7.3.2" + Result = $isSyncRestricted + Status = if ($isSyncRestricted) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure OneDrive sync is restricted for unmanaged devices" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-OrgOnlyBypassLobby.ps1 b/source/tests/Test-OrgOnlyBypassLobby.ps1 index 4a2b5be..5fc49e8 100644 --- a/source/tests/Test-OrgOnlyBypassLobby.ps1 +++ b/source/tests/Test-OrgOnlyBypassLobby.ps1 @@ -36,21 +36,17 @@ function Test-OrgOnlyBypassLobby { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($lobbyBypassRestricted) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "8.5.3" - $auditResult.RecDescription = "Ensure only people in my org can bypass the lobby" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "6.8" - $auditResult.CISDescription = "Define and Maintain Role-Based Access Control" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $true # Set based on the CIS Controls image - $auditResult.Result = $lobbyBypassRestricted - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "8.5.3" + Result = $lobbyBypassRestricted + Status = if ($lobbyBypassRestricted) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure only people in my org can bypass the lobby" + CISControl = "6.8" + CISDescription = "Define and Maintain Role-Based Access Control" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-OrganizersPresent.ps1 b/source/tests/Test-OrganizersPresent.ps1 index c47f0d8..b10da1e 100644 --- a/source/tests/Test-OrganizersPresent.ps1 +++ b/source/tests/Test-OrganizersPresent.ps1 @@ -36,21 +36,17 @@ function Test-OrganizersPresent { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($presenterRoleRestricted) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "8.5.6" - $auditResult.RecDescription = "Ensure only organizers and co-organizers can present" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # Explicitly Not Mapped - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image - $auditResult.Result = $presenterRoleRestricted - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "8.5.6" + Result = $presenterRoleRestricted + Status = if ($presenterRoleRestricted) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure only organizers and co-organizers can present" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-PasswordHashSync.ps1 b/source/tests/Test-PasswordHashSync.ps1 index c65ac31..e4ece6c 100644 --- a/source/tests/Test-PasswordHashSync.ps1 +++ b/source/tests/Test-PasswordHashSync.ps1 @@ -30,21 +30,17 @@ function Test-PasswordHashSync { $details = "OnPremisesSyncEnabled: $($passwordHashSync)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($hashSyncResult) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "5.1.8.1" - $auditResult.RecDescription = "Ensure password hash sync is enabled for hybrid deployments" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "6.7" - $auditResult.CISDescription = "Centralize Access Control" - $auditResult.IG1 = $false - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $hashSyncResult - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "5.1.8.1" + Result = $hashSyncResult + Status = if ($hashSyncResult) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure password hash sync is enabled for hybrid deployments" + CISControl = "6.7" + CISDescription = "Centralize Access Control" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-PasswordNeverExpirePolicy.ps1 b/source/tests/Test-PasswordNeverExpirePolicy.ps1 index 66e039a..c7fc799 100644 --- a/source/tests/Test-PasswordNeverExpirePolicy.ps1 +++ b/source/tests/Test-PasswordNeverExpirePolicy.ps1 @@ -30,21 +30,17 @@ function Test-PasswordNeverExpirePolicy { $details = "Validity Period: $passwordPolicy days" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($passwordPolicy -eq 0) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "1.3.1" - $auditResult.RecDescription = "Ensure the 'Password expiration policy' is set to 'Set passwords to never expire'" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "5.2" - $auditResult.CISDescription = "Use Unique Passwords" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $passwordPolicy -eq 0 - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "1.3.1" + Result = $passwordPolicy -eq 0 + Status = if ($passwordPolicy -eq 0) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure the 'Password expiration policy' is set to 'Set passwords to never expire'" + CISControl = "5.2" + CISDescription = "Use Unique Passwords" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-ReauthWithCode.ps1 b/source/tests/Test-ReauthWithCode.ps1 index 53e600f..ca64432 100644 --- a/source/tests/Test-ReauthWithCode.ps1 +++ b/source/tests/Test-ReauthWithCode.ps1 @@ -29,21 +29,17 @@ function Test-ReauthWithCode { $details = "EmailAttestationRequired: $($SPOTenantReauthentication.EmailAttestationRequired); EmailAttestationReAuthDays: $($SPOTenantReauthentication.EmailAttestationReAuthDays)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($isReauthenticationRestricted) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "7.2.10" - $auditResult.RecDescription = "Ensure reauthentication with verification code is restricted" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.Result = $isReauthenticationRestricted - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "7.2.10" + Result = $isReauthenticationRestricted + Status = if ($isReauthenticationRestricted) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure reauthentication with verification code is restricted" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-ReportSecurityInTeams.ps1 b/source/tests/Test-ReportSecurityInTeams.ps1 index 479847b..01b3bfb 100644 --- a/source/tests/Test-ReportSecurityInTeams.ps1 +++ b/source/tests/Test-ReportSecurityInTeams.ps1 @@ -39,21 +39,17 @@ function Test-ReportSecurityInTeams { "ReportChatMessageToCustomizedAddressEnabled: $($ReportSubmissionPolicy.ReportChatMessageToCustomizedAddressEnabled)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($securityReportEnabled) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "8.6.1" - $auditResult.RecDescription = "Ensure users can report security concerns in Teams" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.Result = $securityReportEnabled - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "8.6.1" + Result = $securityReportEnabled + Status = if ($securityReportEnabled) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure users can report security concerns in Teams" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-RestrictCustomScripts.ps1 b/source/tests/Test-RestrictCustomScripts.ps1 index 454be84..7ef723b 100644 --- a/source/tests/Test-RestrictCustomScripts.ps1 +++ b/source/tests/Test-RestrictCustomScripts.ps1 @@ -44,21 +44,17 @@ function Test-RestrictCustomScripts { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($complianceResult) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "7.3.4" - $auditResult.RecDescription = "Ensure custom script execution is restricted on site collections" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "2.7" - $auditResult.CISDescription = "Allowlist Authorized Scripts" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $true - $auditResult.Result = $complianceResult - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "7.3.4" + Result = $complianceResult + Status = if ($complianceResult) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure custom script execution is restricted on site collections" + CISControl = "2.7" + CISDescription = "Allowlist Authorized Scripts" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-RestrictExternalSharing.ps1 b/source/tests/Test-RestrictExternalSharing.ps1 index 2034767..20d1107 100644 --- a/source/tests/Test-RestrictExternalSharing.ps1 +++ b/source/tests/Test-RestrictExternalSharing.ps1 @@ -29,21 +29,17 @@ function Test-RestrictExternalSharing { $details = "SharingCapability: $($SPOTenantSharingCapability.SharingCapability)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($isRestricted) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "7.2.3" - $auditResult.RecDescription = "Ensure external content sharing is restricted" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.3" - $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $isRestricted - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "7.2.3" + Result = $isRestricted + Status = if ($isRestricted) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure external content sharing is restricted" + CISControl = "3.3" + CISDescription = "Configure Data Access Control Lists" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-RestrictOutlookAddins.ps1 b/source/tests/Test-RestrictOutlookAddins.ps1 index 56934ab..1b8d8d1 100644 --- a/source/tests/Test-RestrictOutlookAddins.ps1 +++ b/source/tests/Test-RestrictOutlookAddins.ps1 @@ -61,21 +61,17 @@ function Test-RestrictOutlookAddins { $isCompliant = -not ($customPolicyFailures -or $defaultPolicyFailureDetails) # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($isCompliant) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.Rec = "6.3.1" - $auditResult.RecDescription = "Ensure users installing Outlook add-ins is not allowed" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "9.4" - $auditResult.CISDescription = "Restrict Unnecessary or Unauthorized Browser and Email Client Extensions" - $auditResult.IG1 = $false - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $isCompliant - $auditResult.Details = $detailsString - $auditResult.FailureReason = if ($isCompliant) { "N/A" } else { "Unauthorized Outlook add-ins found in custom or default policies." } + $params = @{ + Rec = "6.3.1" + Result = $isCompliant + Status = if ($isCompliant) { "Pass" } else { "Fail" } + Details = $detailsString + FailureReason = if ($isCompliant) { "N/A" } else { "Unauthorized Outlook add-ins found in custom or default policies." } + RecDescription = "Ensure users installing Outlook add-ins is not allowed" + CISControl = "9.4" + CISDescription = "Restrict Unnecessary or Unauthorized Browser and Email Client Extensions" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-RestrictStorageProvidersOutlook.ps1 b/source/tests/Test-RestrictStorageProvidersOutlook.ps1 index 706c5b6..43dceaf 100644 --- a/source/tests/Test-RestrictStorageProvidersOutlook.ps1 +++ b/source/tests/Test-RestrictStorageProvidersOutlook.ps1 @@ -37,21 +37,17 @@ function Test-RestrictStorageProvidersOutlook { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($allPoliciesRestricted) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" # Based on your environment - $auditResult.ProfileLevel = "L2" - $auditResult.Rec = "6.5.3" - $auditResult.RecDescription = "Ensure additional storage providers are restricted in Outlook on the web" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.3" - $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $allPoliciesRestricted - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "6.5.3" + Result = $allPoliciesRestricted + Status = if ($allPoliciesRestricted) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure additional storage providers are restricted in Outlook on the web" + CISControl = "3.3" + CISDescription = "Configure Data Access Control Lists" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-RestrictTenantCreation.ps1 b/source/tests/Test-RestrictTenantCreation.ps1 index 969a146..cef19d0 100644 --- a/source/tests/Test-RestrictTenantCreation.ps1 +++ b/source/tests/Test-RestrictTenantCreation.ps1 @@ -29,21 +29,17 @@ function Test-RestrictTenantCreation { $details = "AllowedToCreateTenants: $($tenantCreationPolicy.AllowedToCreateTenants)" # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($tenantCreationResult) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "5.1.2.3" - $auditResult.RecDescription = "Ensure 'Restrict non-admin users from creating tenants' is set to 'Yes'" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.Result = $tenantCreationResult - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "5.1.2.3" + Result = $tenantCreationResult + Status = if ($tenantCreationResult) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure 'Restrict non-admin users from creating tenants' is set to 'Yes'" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-SafeAttachmentsPolicy.ps1 b/source/tests/Test-SafeAttachmentsPolicy.ps1 index 7cf285f..0145a94 100644 --- a/source/tests/Test-SafeAttachmentsPolicy.ps1 +++ b/source/tests/Test-SafeAttachmentsPolicy.ps1 @@ -34,21 +34,17 @@ function Test-SafeAttachmentsPolicy { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($result) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E5" - $auditResult.ProfileLevel = "L2" - $auditResult.Rec = "2.1.4" - $auditResult.RecDescription = "Ensure Safe Attachments policy is enabled" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "9.7" - $auditResult.CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $true - $auditResult.Result = $result - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "2.1.4" + Result = $result + Status = if ($result) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure Safe Attachments policy is enabled" + CISControl = "9.7" + CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-SafeAttachmentsTeams.ps1 b/source/tests/Test-SafeAttachmentsTeams.ps1 index 649de39..a38e87d 100644 --- a/source/tests/Test-SafeAttachmentsTeams.ps1 +++ b/source/tests/Test-SafeAttachmentsTeams.ps1 @@ -41,21 +41,17 @@ function Test-SafeAttachmentsTeams { } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($result) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E5" - $auditResult.ProfileLevel = "L2" - $auditResult.Rec = "2.1.5" - $auditResult.RecDescription = "Ensure Safe Attachments for SharePoint, OneDrive, and Microsoft Teams is Enabled" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "9.7, 10.1" - $auditResult.CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections, Deploy and Maintain Anti-Malware Software" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $result - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "2.1.5" + Result = $result + Status = if ($result) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure Safe Attachments for SharePoint, OneDrive, and Microsoft Teams is Enabled" + CISControl = "9.7, 10.1" + CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections, Deploy and Maintain Anti-Malware Software" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-SafeLinksOfficeApps.ps1 b/source/tests/Test-SafeLinksOfficeApps.ps1 index 0779515..42dc59f 100644 --- a/source/tests/Test-SafeLinksOfficeApps.ps1 +++ b/source/tests/Test-SafeLinksOfficeApps.ps1 @@ -48,21 +48,17 @@ function Test-SafeLinksOfficeApps { $failureReasons = if ($result) { "N/A" } else { "The following Safe Links policies settings do not meet the recommended configuration: $($misconfiguredDetails -join ' | ')" } # Create and populate the CISAuditResult object - $auditResult = [CISAuditResult]::new() - $auditResult.Status = if ($result) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E5" - $auditResult.ProfileLevel = "L2" - $auditResult.Rec = "2.1.1" - $auditResult.RecDescription = "Ensure Safe Links for Office Applications is Enabled" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "10.1" - $auditResult.CISDescription = "Deploy and Maintain Anti-Malware Software" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $result - $auditResult.Details = $details - $auditResult.FailureReason = $failureReasons + $params = @{ + Rec = "2.1.1" + Result = $result + Status = if ($result) { "Pass" } else { "Fail" } + Details = $details + FailureReason = $failureReasons + RecDescription = "Ensure Safe Links for Office Applications is Enabled" + CISControl = "10.1" + CISDescription = "Deploy and Maintain Anti-Malware Software" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-SharePointAADB2B.ps1 b/source/tests/Test-SharePointAADB2B.ps1 index 49817ce..45937fc 100644 --- a/source/tests/Test-SharePointAADB2B.ps1 +++ b/source/tests/Test-SharePointAADB2B.ps1 @@ -18,20 +18,17 @@ function Test-SharePointAADB2B { $SPOTenantAzureADB2B = Get-SPOTenant | Select-Object EnableAzureADB2BIntegration # Populate the auditResult object with the required properties - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "7.2.2" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.IG1 = $false - $auditResult.IG2 = $false - $auditResult.IG3 = $false - $auditResult.RecDescription = "Ensure SharePoint and OneDrive integration with Azure AD B2B is enabled" - $auditResult.Result = $SPOTenantAzureADB2B.EnableAzureADB2BIntegration - $auditResult.Details = "EnableAzureADB2BIntegration: $($SPOTenantAzureADB2B.EnableAzureADB2BIntegration)" - $auditResult.FailureReason = if (-not $SPOTenantAzureADB2B.EnableAzureADB2BIntegration) { "Azure AD B2B integration is not enabled" } else { "N/A" } - $auditResult.Status = if ($SPOTenantAzureADB2B.EnableAzureADB2BIntegration) { "Pass" } else { "Fail" } + $params = @{ + Rec = "7.2.2" + Result = $SPOTenantAzureADB2B.EnableAzureADB2BIntegration + Status = if ($SPOTenantAzureADB2B.EnableAzureADB2BIntegration) { "Pass" } else { "Fail" } + Details = "EnableAzureADB2BIntegration: $($SPOTenantAzureADB2B.EnableAzureADB2BIntegration)" + FailureReason = if (-not $SPOTenantAzureADB2B.EnableAzureADB2BIntegration) { "Azure AD B2B integration is not enabled" } else { "N/A" } + RecDescription = "Ensure SharePoint and OneDrive integration with Azure AD B2B is enabled" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-SharePointExternalSharingDomains.ps1 b/source/tests/Test-SharePointExternalSharingDomains.ps1 index 05b65b8..a8a8b4b 100644 --- a/source/tests/Test-SharePointExternalSharingDomains.ps1 +++ b/source/tests/Test-SharePointExternalSharingDomains.ps1 @@ -19,20 +19,17 @@ function Test-SharePointExternalSharingDomains { $isDomainRestrictionConfigured = $SPOTenant.SharingDomainRestrictionMode -eq 'AllowList' # Populate the auditResult object with the required properties - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.3" - $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.Rec = "7.2.6" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure SharePoint external sharing is managed through domain whitelist/blacklists" - $auditResult.Result = $isDomainRestrictionConfigured - $auditResult.Details = "SharingDomainRestrictionMode: $($SPOTenant.SharingDomainRestrictionMode); SharingAllowedDomainList: $($SPOTenant.SharingAllowedDomainList)" - $auditResult.FailureReason = if (-not $isDomainRestrictionConfigured) { "Domain restrictions for SharePoint external sharing are not configured to 'AllowList'. Current setting: $($SPOTenant.SharingDomainRestrictionMode)" } else { "N/A" } - $auditResult.Status = if ($isDomainRestrictionConfigured) { "Pass" } else { "Fail" } + $params = @{ + Rec = "7.2.6" + Result = $isDomainRestrictionConfigured + Status = if ($isDomainRestrictionConfigured) { "Pass" } else { "Fail" } + Details = "SharingDomainRestrictionMode: $($SPOTenant.SharingDomainRestrictionMode); SharingAllowedDomainList: $($SPOTenant.SharingAllowedDomainList)" + FailureReason = if (-not $isDomainRestrictionConfigured) { "Domain restrictions for SharePoint external sharing are not configured to 'AllowList'. Current setting: $($SPOTenant.SharingDomainRestrictionMode)" } else { "N/A" } + RecDescription = "Ensure SharePoint external sharing is managed through domain whitelist/blacklists" + CISControl = "3.3" + CISDescription = "Configure Data Access Control Lists" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-SharePointGuestsItemSharing.ps1 b/source/tests/Test-SharePointGuestsItemSharing.ps1 index bff9180..f429c7c 100644 --- a/source/tests/Test-SharePointGuestsItemSharing.ps1 +++ b/source/tests/Test-SharePointGuestsItemSharing.ps1 @@ -19,20 +19,17 @@ function Test-SharePointGuestsItemSharing { $isGuestResharingPrevented = $SPOTenant.PreventExternalUsersFromResharing # Populate the auditResult object with the required properties - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.3" - $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.Rec = "7.2.5" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $true - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.RecDescription = "Ensure that SharePoint guest users cannot share items they don't own" - $auditResult.Result = $isGuestResharingPrevented - $auditResult.Details = "PreventExternalUsersFromResharing: $isGuestResharingPrevented" - $auditResult.FailureReason = if (-not $isGuestResharingPrevented) { "Guest users can reshare items they don't own." } else { "N/A" } - $auditResult.Status = if ($isGuestResharingPrevented) { "Pass" } else { "Fail" } + $params = @{ + Rec = "7.2.5" + Result = $isGuestResharingPrevented + Status = if ($isGuestResharingPrevented) { "Pass" } else { "Fail" } + Details = "PreventExternalUsersFromResharing: $isGuestResharingPrevented" + FailureReason = if (-not $isGuestResharingPrevented) { "Guest users can reshare items they don't own." } else { "N/A" } + RecDescription = "Ensure that SharePoint guest users cannot share items they don't own" + CISControl = "3.3" + CISDescription = "Configure Data Access Control Lists" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-SpamPolicyAdminNotify.ps1 b/source/tests/Test-SpamPolicyAdminNotify.ps1 index 4e822ec..4532acd 100644 --- a/source/tests/Test-SpamPolicyAdminNotify.ps1 +++ b/source/tests/Test-SpamPolicyAdminNotify.ps1 @@ -34,20 +34,17 @@ function Test-SpamPolicyAdminNotify { } # Create an instance of CISAuditResult and populate it - $auditResult.Status = if ($areSettingsEnabled) { "Pass" } else { "Fail" } - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L1" - $auditResult.Rec = "2.1.6" - $auditResult.RecDescription = "Ensure Exchange Online Spam Policies are set to notify administrators" - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "17.5" - $auditResult.CISDescription = "Assign Key Roles and Responsibilities" - $auditResult.IG1 = $false - $auditResult.IG2 = $true - $auditResult.IG3 = $true - $auditResult.Result = $areSettingsEnabled - $auditResult.Details = if ($areSettingsEnabled) { "Both BccSuspiciousOutboundMail and NotifyOutboundSpam are enabled." } else { $failureDetails -join ' ' } - $auditResult.FailureReason = if (-not $areSettingsEnabled) { "One or both spam policies are not set to notify administrators." } else { "N/A" } + $params = @{ + Rec = "2.1.6" + Result = $areSettingsEnabled + Status = if ($areSettingsEnabled) { "Pass" } else { "Fail" } + Details = if ($areSettingsEnabled) { "Both BccSuspiciousOutboundMail and NotifyOutboundSpam are enabled." } else { $failureDetails -join ' ' } + FailureReason = if (-not $areSettingsEnabled) { "One or both spam policies are not set to notify administrators." } else { "N/A" } + RecDescription = "Ensure Exchange Online Spam Policies are set to notify administrators" + CISControl = "17.5" + CISDescription = "Assign Key Roles and Responsibilities" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-TeamsExternalAccess.ps1 b/source/tests/Test-TeamsExternalAccess.ps1 index 06b98eb..4a2ad40 100644 --- a/source/tests/Test-TeamsExternalAccess.ps1 +++ b/source/tests/Test-TeamsExternalAccess.ps1 @@ -29,20 +29,17 @@ function Test-TeamsExternalAccess { $isCompliant = -not $externalAccessConfig.AllowTeamsConsumer -and -not $externalAccessConfig.AllowPublicUsers -and (-not $externalAccessConfig.AllowFederatedUsers -or $allowedDomainsLimited) # Create an instance of CISAuditResult and populate it - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "0.0" # The control is Explicitly Not Mapped as per the image provided - $auditResult.CISDescription = "Explicitly Not Mapped" - $auditResult.Rec = "8.2.1" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $false # Set based on the CIS Controls image - $auditResult.IG2 = $false # Set based on the CIS Controls image - $auditResult.IG3 = $false # Set based on the CIS Controls image - $auditResult.RecDescription = "Ensure 'external access' is restricted in the Teams admin center" - $auditResult.Result = $isCompliant - $auditResult.Details = "AllowTeamsConsumer: $($externalAccessConfig.AllowTeamsConsumer); AllowPublicUsers: $($externalAccessConfig.AllowPublicUsers); AllowFederatedUsers: $($externalAccessConfig.AllowFederatedUsers); AllowedDomains limited: $allowedDomainsLimited" - $auditResult.FailureReason = if (-not $isCompliant) { "One or more external access configurations are not compliant." } else { "N/A" } - $auditResult.Status = if ($isCompliant) { "Pass" } else { "Fail" } + $params = @{ + Rec = "8.2.1" + Result = $isCompliant + Status = if ($isCompliant) { "Pass" } else { "Fail" } + Details = "AllowTeamsConsumer: $($externalAccessConfig.AllowTeamsConsumer); AllowPublicUsers: $($externalAccessConfig.AllowPublicUsers); AllowFederatedUsers: $($externalAccessConfig.AllowFederatedUsers); AllowedDomains limited: $allowedDomainsLimited" + FailureReason = if (-not $isCompliant) { "One or more external access configurations are not compliant." } else { "N/A" } + RecDescription = "Ensure 'external access' is restricted in the Teams admin center" + CISControl = "0.0" + CISDescription = "Explicitly Not Mapped" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/source/tests/Test-TeamsExternalFileSharing.ps1 b/source/tests/Test-TeamsExternalFileSharing.ps1 index 9226a64..697b2bc 100644 --- a/source/tests/Test-TeamsExternalFileSharing.ps1 +++ b/source/tests/Test-TeamsExternalFileSharing.ps1 @@ -33,20 +33,17 @@ function Test-TeamsExternalFileSharing { } # Create an instance of CISAuditResult and populate it - $auditResult.CISControlVer = "v8" - $auditResult.CISControl = "3.3" - $auditResult.CISDescription = "Configure Data Access Control Lists" - $auditResult.Rec = "8.1.1" - $auditResult.ELevel = "E3" - $auditResult.ProfileLevel = "L2" - $auditResult.IG1 = $true # Set based on the benchmark - $auditResult.IG2 = $true # Set based on the benchmark - $auditResult.IG3 = $true # Set based on the benchmark - $auditResult.RecDescription = "Ensure external file sharing in Teams is enabled for only approved cloud storage services" - $auditResult.Result = $isCompliant - $auditResult.Details = if (-not $isCompliant) { "Non-approved providers enabled: $($nonCompliantProviders -join ', ')" } else { "All cloud storage services are approved providers" } - $auditResult.FailureReason = if (-not $isCompliant) { "The following non-approved providers are enabled: $($nonCompliantProviders -join ', ')" } else { "N/A" } - $auditResult.Status = if ($isCompliant) { "Pass" } else { "Fail" } + $params = @{ + Rec = "8.1.1" + Result = $isCompliant + Status = if ($isCompliant) { "Pass" } else { "Fail" } + Details = if (-not $isCompliant) { "Non-approved providers enabled: $($nonCompliantProviders -join ', ')" } else { "All cloud storage services are approved providers" } + FailureReason = if (-not $isCompliant) { "The following non-approved providers are enabled: $($nonCompliantProviders -join ', ')" } else { "N/A" } + RecDescription = "Ensure external file sharing in Teams is enabled for only approved cloud storage services" + CISControl = "3.3" + CISDescription = "Configure Data Access Control Lists" + } + $auditResult = Initialize-CISAuditResult @params } end { diff --git a/tests/Unit/Private/Initialize-CISAuditResult.tests.ps1 b/tests/Unit/Private/Initialize-CISAuditResult.tests.ps1 new file mode 100644 index 0000000..4a2aa69 --- /dev/null +++ b/tests/Unit/Private/Initialize-CISAuditResult.tests.ps1 @@ -0,0 +1,27 @@ +$ProjectPath = "$PSScriptRoot\..\..\.." | Convert-Path +$ProjectName = ((Get-ChildItem -Path $ProjectPath\*\*.psd1).Where{ + ($_.Directory.Name -match 'source|src' -or $_.Directory.Name -eq $_.BaseName) -and + $(try { Test-ModuleManifest $_.FullName -ErrorAction Stop } catch { $false } ) + }).BaseName + + +Import-Module $ProjectName + +InModuleScope $ProjectName { + Describe Get-PrivateFunction { + Context 'Default' { + BeforeEach { + $return = Get-PrivateFunction -PrivateData 'string' + } + + It 'Returns a single object' { + ($return | Measure-Object).Count | Should -Be 1 + } + + It 'Returns a string based on the parameter PrivateData' { + $return | Should -Be 'string' + } + } + } +} + From cafcaf2671d043e34ac64f9693d429c80581a6de Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 17:13:00 -0500 Subject: [PATCH 61/67] add: missing properties to csv --- source/helper/TestDefinitions.csv | 104 +++++++++++++++--------------- 1 file changed, 52 insertions(+), 52 deletions(-) diff --git a/source/helper/TestDefinitions.csv b/source/helper/TestDefinitions.csv index 1bd9e43..32c46b7 100644 --- a/source/helper/TestDefinitions.csv +++ b/source/helper/TestDefinitions.csv @@ -1,52 +1,52 @@ -Index,TestFileName,Rec,ELevel,ProfileLevel,IG1,IG2,IG3,Automated,Connection -1,Test-AdministrativeAccountCompliance.ps1,1.1.1,E3,L1,TRUE,TRUE,TRUE,FALSE,AzureAD -2,Test-GlobalAdminsCount.ps1,1.1.3,E3,L1,TRUE,TRUE,TRUE,TRUE,Microsoft Graph -3,Test-ManagedApprovedPublicGroups.ps1,1.2.1,E3,L2,TRUE,TRUE,TRUE,TRUE,Microsoft Graph -4,Test-BlockSharedMailboxSignIn.ps1,1.2.2,E3,L1,FALSE,FALSE,FALSE,TRUE,AzureAD | EXO -5,Test-PasswordNeverExpirePolicy.ps1,1.3.1,E3,L1,TRUE,TRUE,TRUE,TRUE,Microsoft Graph -6,Test-ExternalSharingCalendars.ps1,1.3.3,E3,L2,FALSE,TRUE,TRUE,TRUE,EXO -7,Test-CustomerLockbox.ps1,1.3.6,E5,L2,FALSE,FALSE,FALSE,TRUE,EXO -8,Test-SafeLinksOfficeApps.ps1,2.1.1,E5,L2,TRUE,TRUE,TRUE,TRUE,EXO -9,Test-CommonAttachmentFilter.ps1,2.1.2,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO -10,Test-NotifyMalwareInternal.ps1,2.1.3,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO -11,Test-SafeAttachmentsPolicy.ps1,2.1.4,E5,L2,FALSE,FALSE,TRUE,TRUE,EXO -12,Test-SafeAttachmentsTeams.ps1,2.1.5,E5,L2,TRUE,TRUE,TRUE,TRUE,EXO -13,Test-SpamPolicyAdminNotify.ps1,2.1.6,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO -14,Test-AntiPhishingPolicy.ps1,2.1.7,E5,L1,FALSE,FALSE,TRUE,TRUE,EXO -15,Test-EnableDKIM.ps1,2.1.9,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO -16,Test-AuditLogSearch.ps1,3.1.1,E3,L1,TRUE,TRUE,TRUE,TRUE,EXO -17,Test-RestrictTenantCreation.ps1,5.1.2.3,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Graph -18,Test-PasswordHashSync.ps1,5.1.8.1,E3,L1,FALSE,TRUE,TRUE,TRUE,Microsoft Graph -19,Test-AuditDisabledFalse.ps1,6.1.1,E3,L1,TRUE,TRUE,TRUE,TRUE,Microsoft Graph -20,Test-MailboxAuditingE3.ps1,6.1.2,E3,L1,TRUE,TRUE,TRUE,TRUE,EXO -21,Test-MailboxAuditingE5.ps1,6.1.3,E5,L1,TRUE,TRUE,TRUE,TRUE,EXO -22,Test-BlockMailForwarding.ps1,6.2.1,E3,L1,FALSE,FALSE,FALSE,TRUE,EXO -23,Test-NoWhitelistDomains.ps1,6.2.2,E3,L1,FALSE,FALSE,FALSE,TRUE,EXO -24,Test-IdentifyExternalEmail.ps1,6.2.3,E3,L1,FALSE,FALSE,FALSE,TRUE,EXO -25,Test-RestrictOutlookAddins.ps1,6.3.1,E3,L2,FALSE,TRUE,TRUE,TRUE,EXO -26,Test-ModernAuthExchangeOnline.ps1,6.5.1,E3,L1,FALSE,TRUE,TRUE,TRUE,EXO -27,Test-MailTipsEnabled.ps1,6.5.2,E3,L2,FALSE,FALSE,FALSE,TRUE,EXO -28,Test-RestrictStorageProvidersOutlook.ps1,6.5.3,E3,L2,TRUE,TRUE,TRUE,TRUE,EXO -29,Test-ModernAuthSharePoint.ps1,7.2.1,E3,L1,FALSE,TRUE,TRUE,TRUE,SPO -30,Test-SharePointAADB2B.ps1,7.2.2,E3,L1,FALSE,FALSE,FALSE,TRUE,SPO -31,Test-RestrictExternalSharing.ps1,7.2.3,E3,L1,TRUE,TRUE,TRUE,TRUE,SPO -32,Test-OneDriveContentRestrictions.ps1,7.2.4,E3,L2,TRUE,TRUE,TRUE,TRUE,SPO -33,Test-SharePointGuestsItemSharing.ps1,7.2.5,E3,L2,TRUE,TRUE,TRUE,TRUE,SPO -34,Test-SharePointExternalSharingDomains.ps1,7.2.6,E3,L2,TRUE,TRUE,TRUE,TRUE,SPO -35,Test-LinkSharingRestrictions.ps1,7.2.7,E3,L1,TRUE,TRUE,TRUE,TRUE,SPO -36,Test-GuestAccessExpiration.ps1,7.2.9,E3,L1,FALSE,FALSE,FALSE,TRUE,SPO -37,Test-ReauthWithCode.ps1,7.2.10,E3,L1,FALSE,FALSE,FALSE,TRUE,SPO -38,Test-DisallowInfectedFilesDownload.ps1,7.3.1,E5,L2,TRUE,TRUE,TRUE,TRUE,SPO -39,Test-OneDriveSyncRestrictions.ps1,7.3.2,E3,L2,FALSE,FALSE,FALSE,TRUE,SPO -40,Test-RestrictCustomScripts.ps1,7.3.4,E3,L1,FALSE,FALSE,TRUE,TRUE,SPO -41,Test-TeamsExternalFileSharing.ps1,8.1.1,E3,L2,TRUE,TRUE,TRUE,TRUE,Microsoft Teams -42,Test-BlockChannelEmails.ps1,8.1.2,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams -43,Test-TeamsExternalAccess.ps1,8.2.1,E3,L2,FALSE,FALSE,FALSE,TRUE,Microsoft Teams -44,Test-NoAnonymousMeetingJoin.ps1,8.5.1,E3,L2,FALSE,FALSE,FALSE,TRUE,Microsoft Teams -45,Test-NoAnonymousMeetingStart.ps1,8.5.2,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams -46,Test-OrgOnlyBypassLobby.ps1,8.5.3,E3,L1,FALSE,FALSE,TRUE,TRUE,Microsoft Teams -47,Test-DialInBypassLobby.ps1,8.5.4,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams -48,Test-MeetingChatNoAnonymous.ps1,8.5.5,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams -49,Test-OrganizersPresent.ps1,8.5.6,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams -50,Test-ExternalNoControl.ps1,8.5.7,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams -51,Test-ReportSecurityInTeams.ps1,8.6.1,E3,L1,FALSE,FALSE,FALSE,TRUE,Microsoft Teams | EXO +Index,TestFileName,Rec,RecDescription,ELevel,ProfileLevel,CISControl,CISDescription,IG1,IG2,IG3,Automated,Connection +1,Test-AdministrativeAccountCompliance.ps1,1.1.1,Ensure Administrative accounts are separate and cloud-only,E3,L1,5.4,Restrict Administrator Privileges to Dedicated Administrator Accounts,TRUE,TRUE,TRUE,FALSE,AzureAD +2,Test-GlobalAdminsCount.ps1,1.1.3,Ensure that between two and four global admins are designated,E3,L1,5.1,Establish and Maintain an Inventory of Accounts,TRUE,TRUE,TRUE,TRUE,Microsoft Graph +3,Test-ManagedApprovedPublicGroups.ps1,1.2.1,Ensure that only organizationally managed/approved public groups exist,E3,L2,3.3,Configure Data Access Control Lists,TRUE,TRUE,TRUE,TRUE,Microsoft Graph +4,Test-BlockSharedMailboxSignIn.ps1,1.2.2,Ensure sign-in to shared mailboxes is blocked,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,AzureAD | EXO +5,Test-PasswordNeverExpirePolicy.ps1,1.3.1,Ensure the 'Password expiration policy' is set to 'Set passwords to never expire',E3,L1,5.2,Use Unique Passwords,TRUE,TRUE,TRUE,TRUE,Microsoft Graph +6,Test-ExternalSharingCalendars.ps1,1.3.3,Ensure 'External sharing' of calendars is not available,E3,L2,4.8,Uninstall or Disable Unnecessary Services on Enterprise Assets and Software,FALSE,TRUE,TRUE,TRUE,EXO +7,Test-CustomerLockbox.ps1,1.3.6,Ensure the customer lockbox feature is enabled,E5,L2,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,EXO +8,Test-SafeLinksOfficeApps.ps1,2.1.1,Ensure Safe Links for Office Applications is Enabled,E5,L2,10.1,Deploy and Maintain Anti-Malware Software,TRUE,TRUE,TRUE,TRUE,EXO +9,Test-CommonAttachmentFilter.ps1,2.1.2,Ensure the Common Attachment Types Filter is enabled,E3,L1,9.6,Block Unnecessary File Types,FALSE,TRUE,TRUE,TRUE,EXO +10,Test-NotifyMalwareInternal.ps1,2.1.3,Ensure notifications for internal users sending malware is Enabled,E3,L1,17.5,Assign Key Roles and Responsibilities,FALSE,TRUE,TRUE,TRUE,EXO +11,Test-SafeAttachmentsPolicy.ps1,2.1.4,Ensure Safe Attachments policy is enabled,E5,L2,9.7,Deploy and Maintain Email Server Anti-Malware Protections,FALSE,FALSE,TRUE,TRUE,EXO +12,Test-SafeAttachmentsTeams.ps1,2.1.5,"Ensure Safe Attachments for SharePoint, OneDrive, and Microsoft Teams is Enabled",E5,L2,"9.7, 10.1","Deploy and Maintain Email Server Anti-Malware Protections, Deploy and Maintain Anti-Malware Software",TRUE,TRUE,TRUE,TRUE,EXO +13,Test-SpamPolicyAdminNotify.ps1,2.1.6,Ensure Exchange Online Spam Policies are set to notify administrators,E3,L1,17.5,Assign Key Roles and Responsibilities,FALSE,TRUE,TRUE,TRUE,EXO +14,Test-AntiPhishingPolicy.ps1,2.1.7,Ensure that an anti-phishing policy has been created,E5,L1,9.7,Deploy and Maintain Email Server Anti-Malware Protections,FALSE,FALSE,TRUE,TRUE,EXO +15,Test-EnableDKIM.ps1,2.1.9,Ensure that DKIM is enabled for all Exchange Online Domains,E3,L1,9.5,Implement DMARC,FALSE,TRUE,TRUE,TRUE,EXO +16,Test-AuditLogSearch.ps1,3.1.1,Ensure Microsoft 365 audit log search is Enabled,E3,L1,8.2,Collect Audit Logs,TRUE,TRUE,TRUE,TRUE,EXO +17,Test-RestrictTenantCreation.ps1,5.1.2.3,Ensure 'Restrict non-admin users from creating tenants' is set to 'Yes',E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Graph +18,Test-PasswordHashSync.ps1,5.1.8.1,Ensure password hash sync is enabled for hybrid deployments,E3,L1,6.7,Centralize Access Control,FALSE,TRUE,TRUE,TRUE,Microsoft Graph +19,Test-AuditDisabledFalse.ps1,6.1.1,Ensure 'AuditDisabled' organizationally is set to 'False',E3,L1,8.2,Collect Audit Logs,TRUE,TRUE,TRUE,TRUE,Microsoft Graph +20,Test-MailboxAuditingE3.ps1,6.1.2,Ensure mailbox auditing for Office E3 users is Enabled,E3,L1,8.2,Collect audit logs.,TRUE,TRUE,TRUE,TRUE,EXO +21,Test-MailboxAuditingE5.ps1,6.1.3,Ensure mailbox auditing for Office E5 users is Enabled,E5,L1,8.2,Collect audit logs.,TRUE,TRUE,TRUE,TRUE,EXO +22,Test-BlockMailForwarding.ps1,6.2.1,Ensure all forms of mail forwarding are blocked and/or disabled,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,EXO +23,Test-NoWhitelistDomains.ps1,6.2.2,Ensure mail transport rules do not whitelist specific domains,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,EXO +24,Test-IdentifyExternalEmail.ps1,6.2.3,Ensure email from external senders is identified,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,EXO +25,Test-RestrictOutlookAddins.ps1,6.3.1,Ensure users installing Outlook add-ins is not allowed,E3,L2,9.4,Restrict Unnecessary or Unauthorized Browser and Email Client Extensions,FALSE,TRUE,TRUE,TRUE,EXO +26,Test-ModernAuthExchangeOnline.ps1,6.5.1,Ensure modern authentication for Exchange Online is enabled (Automated),E3,L1,3.1,Encrypt Sensitive Data in Transit,FALSE,TRUE,TRUE,TRUE,EXO +27,Test-MailTipsEnabled.ps1,6.5.2,Ensure MailTips are enabled for end users,E3,L2,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,EXO +28,Test-RestrictStorageProvidersOutlook.ps1,6.5.3,Ensure additional storage providers are restricted in Outlook on the web,E3,L2,3.3,Configure Data Access Control Lists,TRUE,TRUE,TRUE,TRUE,EXO +29,Test-ModernAuthSharePoint.ps1,7.2.1,Modern Authentication for SharePoint Applications,E3,L1,3.1,Encrypt Sensitive Data in Transit,FALSE,TRUE,TRUE,TRUE,SPO +30,Test-SharePointAADB2B.ps1,7.2.2,Ensure reauthentication with verification code is restricted,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,SPO +31,Test-RestrictExternalSharing.ps1,7.2.3,Ensure SharePoint and OneDrive integration with Azure AD B2B is enabled,E3,L1,0,Explicitly Not Mapped,TRUE,TRUE,TRUE,TRUE,SPO +32,Test-OneDriveContentRestrictions.ps1,7.2.4,Ensure external content sharing is restricted,E3,L2,3.3,Configure Data Access Control Lists,TRUE,TRUE,TRUE,TRUE,SPO +33,Test-SharePointGuestsItemSharing.ps1,7.2.5,Ensure OneDrive content sharing is restricted,E3,L2,3.3,Configure Data Access Control Lists,TRUE,TRUE,TRUE,TRUE,SPO +34,Test-SharePointExternalSharingDomains.ps1,7.2.6,Ensure that SharePoint guest users cannot share items they don't own,E3,L2,3.3,Configure Data Access Control Lists,TRUE,TRUE,TRUE,TRUE,SPO +35,Test-LinkSharingRestrictions.ps1,7.2.7,Ensure SharePoint external sharing is managed through domain whitelist/blacklists,E3,L1,3.3,Configure Data Access Control Lists,TRUE,TRUE,TRUE,TRUE,SPO +36,Test-GuestAccessExpiration.ps1,7.2.9,Ensure link sharing is restricted in SharePoint and OneDrive,E3,L1,3.3,Configure Data Access Control Lists,FALSE,FALSE,FALSE,TRUE,SPO +37,Test-ReauthWithCode.ps1,7.2.10,Ensure guest access to a site or OneDrive will expire automatically,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,SPO +38,Test-DisallowInfectedFilesDownload.ps1,7.3.1,Ensure Office 365 SharePoint infected files are disallowed for download,E5,L2,10.1,Deploy and Maintain Anti-Malware Software,TRUE,TRUE,TRUE,TRUE,SPO +39,Test-OneDriveSyncRestrictions.ps1,7.3.2,Ensure OneDrive sync is restricted for unmanaged devices,E3,L2,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,SPO +40,Test-RestrictCustomScripts.ps1,7.3.4,Ensure custom script execution is restricted on site collections,E3,L1,2.7,Allowlist Authorized Scripts,FALSE,FALSE,TRUE,TRUE,SPO +41,Test-TeamsExternalFileSharing.ps1,8.1.1,Ensure external file sharing in Teams is enabled for only approved cloud storage services,E3,L2,3.3,Configure Data Access Control Lists,TRUE,TRUE,TRUE,TRUE,Microsoft Teams +42,Test-BlockChannelEmails.ps1,8.1.2,Ensure users can't send emails to a channel email address,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +43,Test-TeamsExternalAccess.ps1,8.2.1,Ensure 'external access' is restricted in the Teams admin center,E3,L2,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +44,Test-NoAnonymousMeetingJoin.ps1,8.5.1,Ensure anonymous users can't join a meeting,E3,L2,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +45,Test-NoAnonymousMeetingStart.ps1,8.5.2,Ensure anonymous users and dial-in callers can't start a meeting,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +46,Test-OrgOnlyBypassLobby.ps1,8.5.3,Ensure only people in my org can bypass the lobby,E3,L1,6.8,Define and Maintain Role-Based Access Control,FALSE,FALSE,TRUE,TRUE,Microsoft Teams +47,Test-DialInBypassLobby.ps1,8.5.4,Ensure users dialing in can't bypass the lobby,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +48,Test-MeetingChatNoAnonymous.ps1,8.5.5,Ensure meeting chat does not allow anonymous users,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +49,Test-OrganizersPresent.ps1,8.5.6,Ensure only organizers and co-organizers can present,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +50,Test-ExternalNoControl.ps1,8.5.7,Ensure external participants can't give or request control,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Teams +51,Test-ReportSecurityInTeams.ps1,8.6.1,Ensure users can report security concerns in Teams,E3,L1,0,Explicitly Not Mapped,FALSE,FALSE,FALSE,TRUE,Microsoft Teams | EXO From b064f9f27132d3c5e43f6b95382523b7906b5985 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 18:50:18 -0500 Subject: [PATCH 62/67] add: refactor of object initialization --- CHANGELOG.md | 2 ++ source/Private/Initialize-CISAuditResult.ps1 | 17 ++++------------- .../Test-AdministrativeAccountCompliance.ps1 | 3 --- source/tests/Test-AntiPhishingPolicy.ps1 | 3 --- source/tests/Test-AuditDisabledFalse.ps1 | 3 --- source/tests/Test-AuditLogSearch.ps1 | 3 --- source/tests/Test-BlockChannelEmails.ps1 | 3 --- source/tests/Test-BlockMailForwarding.ps1 | 3 --- source/tests/Test-BlockSharedMailboxSignIn.ps1 | 3 --- source/tests/Test-CommonAttachmentFilter.ps1 | 3 --- source/tests/Test-CustomerLockbox.ps1 | 3 --- source/tests/Test-DialInBypassLobby.ps1 | 3 --- .../Test-DisallowInfectedFilesDownload.ps1 | 3 --- source/tests/Test-EnableDKIM.ps1 | 3 --- source/tests/Test-ExternalNoControl.ps1 | 3 --- source/tests/Test-ExternalSharingCalendars.ps1 | 3 --- source/tests/Test-GlobalAdminsCount.ps1 | 3 --- source/tests/Test-GuestAccessExpiration.ps1 | 3 --- source/tests/Test-GuestUsersBiweeklyReview.ps1 | 3 --- source/tests/Test-IdentifyExternalEmail.ps1 | 3 --- source/tests/Test-LinkSharingRestrictions.ps1 | 5 +---- source/tests/Test-MailTipsEnabled.ps1 | 3 --- source/tests/Test-MailboxAuditingE3.ps1 | 11 ++++------- source/tests/Test-MailboxAuditingE5.ps1 | 3 --- .../tests/Test-ManagedApprovedPublicGroups.ps1 | 3 --- source/tests/Test-MeetingChatNoAnonymous.ps1 | 3 --- source/tests/Test-ModernAuthExchangeOnline.ps1 | 3 --- source/tests/Test-ModernAuthSharePoint.ps1 | 3 --- source/tests/Test-NoAnonymousMeetingJoin.ps1 | 5 +---- source/tests/Test-NoAnonymousMeetingStart.ps1 | 3 --- source/tests/Test-NoWhitelistDomains.ps1 | 5 +---- source/tests/Test-NotifyMalwareInternal.ps1 | 5 +---- .../tests/Test-OneDriveContentRestrictions.ps1 | 5 +---- source/tests/Test-OneDriveSyncRestrictions.ps1 | 3 --- source/tests/Test-OrgOnlyBypassLobby.ps1 | 3 --- source/tests/Test-OrganizersPresent.ps1 | 3 --- source/tests/Test-PasswordHashSync.ps1 | 3 --- source/tests/Test-PasswordNeverExpirePolicy.ps1 | 3 --- source/tests/Test-ReauthWithCode.ps1 | 3 --- source/tests/Test-ReportSecurityInTeams.ps1 | 3 --- source/tests/Test-RestrictCustomScripts.ps1 | 3 --- source/tests/Test-RestrictExternalSharing.ps1 | 3 --- source/tests/Test-RestrictOutlookAddins.ps1 | 5 +---- .../Test-RestrictStorageProvidersOutlook.ps1 | 3 --- source/tests/Test-RestrictTenantCreation.ps1 | 3 --- source/tests/Test-SafeAttachmentsPolicy.ps1 | 3 --- source/tests/Test-SafeAttachmentsTeams.ps1 | 3 --- source/tests/Test-SafeLinksOfficeApps.ps1 | 3 --- source/tests/Test-SharePointAADB2B.ps1 | 5 +---- .../Test-SharePointExternalSharingDomains.ps1 | 3 --- .../tests/Test-SharePointGuestsItemSharing.ps1 | 3 --- source/tests/Test-SpamPolicyAdminNotify.ps1 | 3 --- source/tests/Test-TeamsExternalAccess.ps1 | 3 --- source/tests/Test-TeamsExternalFileSharing.ps1 | 3 --- 54 files changed, 17 insertions(+), 180 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 1270b29..e4c5c68 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,8 @@ The format is based on and uses the types of changes according to [Keep a Change ## [Unreleased] +## [0.1.2] - 2024-04-29 + ### Added - Automated and organized CSV testing and added test 1.1.1. diff --git a/source/Private/Initialize-CISAuditResult.ps1 b/source/Private/Initialize-CISAuditResult.ps1 index 6cc1e40..dd92a7b 100644 --- a/source/Private/Initialize-CISAuditResult.ps1 +++ b/source/Private/Initialize-CISAuditResult.ps1 @@ -13,16 +13,7 @@ function Initialize-CISAuditResult { [string]$Details, [Parameter(Mandatory = $true)] - [string]$FailureReason, - - [Parameter(Mandatory = $true)] - [string]$RecDescription, - - [Parameter(Mandatory = $true)] - [string]$CISControl, - - [Parameter(Mandatory = $true)] - [string]$CISDescription + [string]$FailureReason ) # Import the test definitions CSV file @@ -40,9 +31,9 @@ function Initialize-CISAuditResult { $auditResult.IG1 = [bool]::Parse($testDefinition.IG1) $auditResult.IG2 = [bool]::Parse($testDefinition.IG2) $auditResult.IG3 = [bool]::Parse($testDefinition.IG3) - $auditResult.RecDescription = $RecDescription - $auditResult.CISControl = $CISControl - $auditResult.CISDescription = $CISDescription + $auditResult.RecDescription = $testDefinition.RecDescription + $auditResult.CISControl = $testDefinition.CISControl + $auditResult.CISDescription = $testDefinition.CISDescription $auditResult.Automated = [bool]::Parse($testDefinition.Automated) $auditResult.Connection = $testDefinition.Connection $auditResult.CISControlVer = 'v8' diff --git a/source/tests/Test-AdministrativeAccountCompliance.ps1 b/source/tests/Test-AdministrativeAccountCompliance.ps1 index 66cc0a9..21ab959 100644 --- a/source/tests/Test-AdministrativeAccountCompliance.ps1 +++ b/source/tests/Test-AdministrativeAccountCompliance.ps1 @@ -71,9 +71,6 @@ function Test-AdministrativeAccountCompliance { Status = $status Details = $details FailureReason = $failureReason - RecDescription = "Ensure Administrative accounts are separate and cloud-only" - CISControl = "5.4" - CISDescription = "Restrict Administrator Privileges to Dedicated Administrator Accounts" } $auditResult = Initialize-CISAuditResult @params diff --git a/source/tests/Test-AntiPhishingPolicy.ps1 b/source/tests/Test-AntiPhishingPolicy.ps1 index a9b26e8..88b103e 100644 --- a/source/tests/Test-AntiPhishingPolicy.ps1 +++ b/source/tests/Test-AntiPhishingPolicy.ps1 @@ -66,9 +66,6 @@ function Test-AntiPhishingPolicy { Status = if ($isCompliant) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure that an anti-phishing policy has been created" - CISControl = "9.7" - CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections" } # Create and populate the CISAuditResult object diff --git a/source/tests/Test-AuditDisabledFalse.ps1 b/source/tests/Test-AuditDisabledFalse.ps1 index 69e09d6..3f91a83 100644 --- a/source/tests/Test-AuditDisabledFalse.ps1 +++ b/source/tests/Test-AuditDisabledFalse.ps1 @@ -40,9 +40,6 @@ function Test-AuditDisabledFalse { Status = if ($auditNotDisabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure 'AuditDisabled' organizationally is set to 'False'" - CISControl = "8.2" - CISDescription = "Collect Audit Logs" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-AuditLogSearch.ps1 b/source/tests/Test-AuditLogSearch.ps1 index f1c51fe..023f569 100644 --- a/source/tests/Test-AuditLogSearch.ps1 +++ b/source/tests/Test-AuditLogSearch.ps1 @@ -40,9 +40,6 @@ function Test-AuditLogSearch { Status = if ($auditLogResult) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure Microsoft 365 audit log search is Enabled" - CISControl = "8.2" - CISDescription = "Collect Audit Logs" } $auditResult = Initialize-CISAuditResult @params diff --git a/source/tests/Test-BlockChannelEmails.ps1 b/source/tests/Test-BlockChannelEmails.ps1 index 917f1b2..c8ed086 100644 --- a/source/tests/Test-BlockChannelEmails.ps1 +++ b/source/tests/Test-BlockChannelEmails.ps1 @@ -40,9 +40,6 @@ function Test-BlockChannelEmails { Status = if (-not $allowEmailIntoChannel) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure users can't send emails to a channel email address" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-BlockMailForwarding.ps1 b/source/tests/Test-BlockMailForwarding.ps1 index c7a25a4..8039d06 100644 --- a/source/tests/Test-BlockMailForwarding.ps1 +++ b/source/tests/Test-BlockMailForwarding.ps1 @@ -41,9 +41,6 @@ function Test-BlockMailForwarding { Status = if ($forwardingBlocked) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure all forms of mail forwarding are blocked and/or disabled" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-BlockSharedMailboxSignIn.ps1 b/source/tests/Test-BlockSharedMailboxSignIn.ps1 index e3da822..7f4711b 100644 --- a/source/tests/Test-BlockSharedMailboxSignIn.ps1 +++ b/source/tests/Test-BlockSharedMailboxSignIn.ps1 @@ -42,9 +42,6 @@ function Test-BlockSharedMailboxSignIn { Status = if ($allBlocked) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure sign-in to shared mailboxes is blocked" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-CommonAttachmentFilter.ps1 b/source/tests/Test-CommonAttachmentFilter.ps1 index 7229291..9b60797 100644 --- a/source/tests/Test-CommonAttachmentFilter.ps1 +++ b/source/tests/Test-CommonAttachmentFilter.ps1 @@ -40,9 +40,6 @@ function Test-CommonAttachmentFilter { Status = if ($result) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure the Common Attachment Types Filter is enabled" - CISControl = "9.6" - CISDescription = "Block Unnecessary File Types" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-CustomerLockbox.ps1 b/source/tests/Test-CustomerLockbox.ps1 index b5e418b..c0723f9 100644 --- a/source/tests/Test-CustomerLockbox.ps1 +++ b/source/tests/Test-CustomerLockbox.ps1 @@ -40,9 +40,6 @@ function Test-CustomerLockbox { Status = if ($customerLockboxEnabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure the customer lockbox feature is enabled" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-DialInBypassLobby.ps1 b/source/tests/Test-DialInBypassLobby.ps1 index f2ec463..dd2a47b 100644 --- a/source/tests/Test-DialInBypassLobby.ps1 +++ b/source/tests/Test-DialInBypassLobby.ps1 @@ -40,9 +40,6 @@ function Test-DialInBypassLobby { Status = if ($PSTNBypassDisabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure users dialing in can't bypass the lobby" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-DisallowInfectedFilesDownload.ps1 b/source/tests/Test-DisallowInfectedFilesDownload.ps1 index 865e22e..3ce9b3a 100644 --- a/source/tests/Test-DisallowInfectedFilesDownload.ps1 +++ b/source/tests/Test-DisallowInfectedFilesDownload.ps1 @@ -41,9 +41,6 @@ function Test-DisallowInfectedFilesDownload { Status = if ($isDisallowInfectedFileDownloadEnabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure Office 365 SharePoint infected files are disallowed for download" - CISControl = "10.1" - CISDescription = "Deploy and Maintain Anti-Malware Software" } $auditResult = Initialize-CISAuditResult @params diff --git a/source/tests/Test-EnableDKIM.ps1 b/source/tests/Test-EnableDKIM.ps1 index 806a862..db7bac6 100644 --- a/source/tests/Test-EnableDKIM.ps1 +++ b/source/tests/Test-EnableDKIM.ps1 @@ -41,9 +41,6 @@ function Test-EnableDKIM { Status = if ($dkimResult) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure that DKIM is enabled for all Exchange Online Domains" - CISControl = "9.5" - CISDescription = "Implement DMARC" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-ExternalNoControl.ps1 b/source/tests/Test-ExternalNoControl.ps1 index bf9c814..8d52da7 100644 --- a/source/tests/Test-ExternalNoControl.ps1 +++ b/source/tests/Test-ExternalNoControl.ps1 @@ -41,9 +41,6 @@ function Test-ExternalNoControl { Status = if ($externalControlRestricted) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure external participants can't give or request control" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-ExternalSharingCalendars.ps1 b/source/tests/Test-ExternalSharingCalendars.ps1 index abc4d00..9053bbb 100644 --- a/source/tests/Test-ExternalSharingCalendars.ps1 +++ b/source/tests/Test-ExternalSharingCalendars.ps1 @@ -50,9 +50,6 @@ function Test-ExternalSharingCalendars { Status = if ($isExternalSharingDisabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure 'External sharing' of calendars is not available" - CISControl = "4.8" - CISDescription = "Uninstall or Disable Unnecessary Services on Enterprise Assets and Software" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-GlobalAdminsCount.ps1 b/source/tests/Test-GlobalAdminsCount.ps1 index 1a77c34..c57110f 100644 --- a/source/tests/Test-GlobalAdminsCount.ps1 +++ b/source/tests/Test-GlobalAdminsCount.ps1 @@ -41,9 +41,6 @@ function Test-GlobalAdminsCount { Status = if ($globalAdminCount -ge 2 -and $globalAdminCount -le 4) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure that between two and four global admins are designated" - CISControl = "5.1" - CISDescription = "Establish and Maintain an Inventory of Accounts" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-GuestAccessExpiration.ps1 b/source/tests/Test-GuestAccessExpiration.ps1 index 2c2ca16..4a0b2b6 100644 --- a/source/tests/Test-GuestAccessExpiration.ps1 +++ b/source/tests/Test-GuestAccessExpiration.ps1 @@ -36,9 +36,6 @@ function Test-GuestAccessExpiration { Status = if ($isGuestAccessExpirationConfiguredCorrectly) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure guest access to a site or OneDrive will expire automatically" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-GuestUsersBiweeklyReview.ps1 b/source/tests/Test-GuestUsersBiweeklyReview.ps1 index e25e462..730f039 100644 --- a/source/tests/Test-GuestUsersBiweeklyReview.ps1 +++ b/source/tests/Test-GuestUsersBiweeklyReview.ps1 @@ -43,9 +43,6 @@ function Test-GuestUsersBiweeklyReview { Status = if ($guestUsers) { "Fail" } else { "Pass" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure Guest Users are reviewed at least biweekly" - CISControl = "5.1, 5.3" - CISDescription = "Establish and Maintain an Inventory of Accounts, Disable Dormant Accounts" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-IdentifyExternalEmail.ps1 b/source/tests/Test-IdentifyExternalEmail.ps1 index 784c048..623d986 100644 --- a/source/tests/Test-IdentifyExternalEmail.ps1 +++ b/source/tests/Test-IdentifyExternalEmail.ps1 @@ -36,9 +36,6 @@ function Test-IdentifyExternalEmail { Status = if ($externalTaggingEnabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure email from external senders is identified" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-LinkSharingRestrictions.ps1 b/source/tests/Test-LinkSharingRestrictions.ps1 index 8f1f142..b117da3 100644 --- a/source/tests/Test-LinkSharingRestrictions.ps1 +++ b/source/tests/Test-LinkSharingRestrictions.ps1 @@ -36,9 +36,6 @@ function Test-LinkSharingRestrictions { Status = if ($isLinkSharingRestricted) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure link sharing is restricted in SharePoint and OneDrive" - CISControl = "3.3" - CISDescription = "Configure Data Access Control Lists" } $auditResult = Initialize-CISAuditResult @params } @@ -47,4 +44,4 @@ function Test-LinkSharingRestrictions { # Return the audit result return $auditResult } -} \ No newline at end of file +} diff --git a/source/tests/Test-MailTipsEnabled.ps1 b/source/tests/Test-MailTipsEnabled.ps1 index bfa8475..12224c0 100644 --- a/source/tests/Test-MailTipsEnabled.ps1 +++ b/source/tests/Test-MailTipsEnabled.ps1 @@ -43,9 +43,6 @@ function Test-MailTipsEnabled { Status = if ($allTipsEnabled -and $externalRecipientsTipsEnabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure MailTips are enabled for end users" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-MailboxAuditingE3.ps1 b/source/tests/Test-MailboxAuditingE3.ps1 index 68361aa..79373b7 100644 --- a/source/tests/Test-MailboxAuditingE3.ps1 +++ b/source/tests/Test-MailboxAuditingE3.ps1 @@ -72,14 +72,11 @@ function Test-MailboxAuditingE3 { # Populate the audit result $params = @{ - Rec = "6.1.2" - Result = $allFailures.Count -eq 0 - Status = if ($allFailures.Count -eq 0) { "Pass" } else { "Fail" } - Details = $details + Rec = "6.1.2" + Result = $allFailures.Count -eq 0 + Status = if ($allFailures.Count -eq 0) { "Pass" } else { "Fail" } + Details = $details FailureReason = $failureReasons - RecDescription = "Ensure mailbox auditing for Office E3 users is Enabled" - CISControl = "8.2" - CISDescription = "Collect audit logs." } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-MailboxAuditingE5.ps1 b/source/tests/Test-MailboxAuditingE5.ps1 index c4c3dc4..8f6796c 100644 --- a/source/tests/Test-MailboxAuditingE5.ps1 +++ b/source/tests/Test-MailboxAuditingE5.ps1 @@ -83,9 +83,6 @@ function Test-MailboxAuditingE5 { Status = if ($allFailures.Count -eq 0) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure mailbox auditing for Office E5 users is Enabled" - CISControl = "8.2" - CISDescription = "Collect audit logs." } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-ManagedApprovedPublicGroups.ps1 b/source/tests/Test-ManagedApprovedPublicGroups.ps1 index 8a0cf52..80fb4fa 100644 --- a/source/tests/Test-ManagedApprovedPublicGroups.ps1 +++ b/source/tests/Test-ManagedApprovedPublicGroups.ps1 @@ -41,9 +41,6 @@ function Test-ManagedApprovedPublicGroups { Status = if ($null -eq $allGroups -or $allGroups.Count -eq 0) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure that only organizationally managed/approved public groups exist" - CISControl = "3.3" - CISDescription = "Configure Data Access Control Lists" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-MeetingChatNoAnonymous.ps1 b/source/tests/Test-MeetingChatNoAnonymous.ps1 index 67d1b84..29428b1 100644 --- a/source/tests/Test-MeetingChatNoAnonymous.ps1 +++ b/source/tests/Test-MeetingChatNoAnonymous.ps1 @@ -37,9 +37,6 @@ function Test-MeetingChatNoAnonymous { Status = if ($chatAnonDisabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure meeting chat does not allow anonymous users" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-ModernAuthExchangeOnline.ps1 b/source/tests/Test-ModernAuthExchangeOnline.ps1 index da2df32..811679b 100644 --- a/source/tests/Test-ModernAuthExchangeOnline.ps1 +++ b/source/tests/Test-ModernAuthExchangeOnline.ps1 @@ -35,9 +35,6 @@ function Test-ModernAuthExchangeOnline { Status = if ($orgConfig.OAuth2ClientProfileEnabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure modern authentication for Exchange Online is enabled (Automated)" - CISControl = "3.10" - CISDescription = "Encrypt Sensitive Data in Transit" } $auditResult = Initialize-CISAuditResult @params diff --git a/source/tests/Test-ModernAuthSharePoint.ps1 b/source/tests/Test-ModernAuthSharePoint.ps1 index c8c06a0..3f7ae76 100644 --- a/source/tests/Test-ModernAuthSharePoint.ps1 +++ b/source/tests/Test-ModernAuthSharePoint.ps1 @@ -33,9 +33,6 @@ function Test-ModernAuthSharePoint { Status = if ($modernAuthForSPRequired) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Modern Authentication for SharePoint Applications" - CISControl = "3.10" - CISDescription = "Encrypt Sensitive Data in Transit" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-NoAnonymousMeetingJoin.ps1 b/source/tests/Test-NoAnonymousMeetingJoin.ps1 index cb5e42b..fbeb7dd 100644 --- a/source/tests/Test-NoAnonymousMeetingJoin.ps1 +++ b/source/tests/Test-NoAnonymousMeetingJoin.ps1 @@ -36,9 +36,6 @@ function Test-NoAnonymousMeetingJoin { Status = if (-not $allowAnonymousUsersToJoinMeeting) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure anonymous users can't join a meeting" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } @@ -47,4 +44,4 @@ function Test-NoAnonymousMeetingJoin { # Return the audit result return $auditResult } -} \ No newline at end of file +} diff --git a/source/tests/Test-NoAnonymousMeetingStart.ps1 b/source/tests/Test-NoAnonymousMeetingStart.ps1 index c520b05..01c680f 100644 --- a/source/tests/Test-NoAnonymousMeetingStart.ps1 +++ b/source/tests/Test-NoAnonymousMeetingStart.ps1 @@ -36,9 +36,6 @@ function Test-NoAnonymousMeetingStart { Status = if ($anonymousStartDisabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure anonymous users and dial-in callers can't start a meeting" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-NoWhitelistDomains.ps1 b/source/tests/Test-NoWhitelistDomains.ps1 index 9632762..820ff7b 100644 --- a/source/tests/Test-NoWhitelistDomains.ps1 +++ b/source/tests/Test-NoWhitelistDomains.ps1 @@ -40,9 +40,6 @@ function Test-NoWhitelistDomains { Status = if ($whitelistedRules) { "Fail" } else { "Pass" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure mail transport rules do not whitelist specific domains" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } @@ -51,4 +48,4 @@ function Test-NoWhitelistDomains { # Return auditResult return $auditResult } -} \ No newline at end of file +} diff --git a/source/tests/Test-NotifyMalwareInternal.ps1 b/source/tests/Test-NotifyMalwareInternal.ps1 index 3d83262..ba962d6 100644 --- a/source/tests/Test-NotifyMalwareInternal.ps1 +++ b/source/tests/Test-NotifyMalwareInternal.ps1 @@ -49,9 +49,6 @@ function Test-NotifyMalwareInternal { Status = if ($result) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure notifications for internal users sending malware is Enabled" - CISControl = "17.5" - CISDescription = "Assign Key Roles and Responsibilities" } $auditResult = Initialize-CISAuditResult @params } @@ -60,4 +57,4 @@ function Test-NotifyMalwareInternal { # Return the audit result return $auditResult } -} \ No newline at end of file +} diff --git a/source/tests/Test-OneDriveContentRestrictions.ps1 b/source/tests/Test-OneDriveContentRestrictions.ps1 index 5905619..7a69c37 100644 --- a/source/tests/Test-OneDriveContentRestrictions.ps1 +++ b/source/tests/Test-OneDriveContentRestrictions.ps1 @@ -40,9 +40,6 @@ function Test-OneDriveContentRestrictions { Status = if ($isOneDriveSharingRestricted) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure OneDrive content sharing is restricted" - CISControl = "3.3" - CISDescription = "Configure Data Access Control Lists" } $auditResult = Initialize-CISAuditResult @params } @@ -51,4 +48,4 @@ function Test-OneDriveContentRestrictions { # Return auditResult return $auditResult } -} \ No newline at end of file +} diff --git a/source/tests/Test-OneDriveSyncRestrictions.ps1 b/source/tests/Test-OneDriveSyncRestrictions.ps1 index 6b6b95b..5357cda 100644 --- a/source/tests/Test-OneDriveSyncRestrictions.ps1 +++ b/source/tests/Test-OneDriveSyncRestrictions.ps1 @@ -40,9 +40,6 @@ function Test-OneDriveSyncRestrictions { Status = if ($isSyncRestricted) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure OneDrive sync is restricted for unmanaged devices" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-OrgOnlyBypassLobby.ps1 b/source/tests/Test-OrgOnlyBypassLobby.ps1 index 5fc49e8..7a7e668 100644 --- a/source/tests/Test-OrgOnlyBypassLobby.ps1 +++ b/source/tests/Test-OrgOnlyBypassLobby.ps1 @@ -42,9 +42,6 @@ function Test-OrgOnlyBypassLobby { Status = if ($lobbyBypassRestricted) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure only people in my org can bypass the lobby" - CISControl = "6.8" - CISDescription = "Define and Maintain Role-Based Access Control" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-OrganizersPresent.ps1 b/source/tests/Test-OrganizersPresent.ps1 index b10da1e..337e671 100644 --- a/source/tests/Test-OrganizersPresent.ps1 +++ b/source/tests/Test-OrganizersPresent.ps1 @@ -42,9 +42,6 @@ function Test-OrganizersPresent { Status = if ($presenterRoleRestricted) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure only organizers and co-organizers can present" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-PasswordHashSync.ps1 b/source/tests/Test-PasswordHashSync.ps1 index e4ece6c..583d65e 100644 --- a/source/tests/Test-PasswordHashSync.ps1 +++ b/source/tests/Test-PasswordHashSync.ps1 @@ -36,9 +36,6 @@ function Test-PasswordHashSync { Status = if ($hashSyncResult) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure password hash sync is enabled for hybrid deployments" - CISControl = "6.7" - CISDescription = "Centralize Access Control" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-PasswordNeverExpirePolicy.ps1 b/source/tests/Test-PasswordNeverExpirePolicy.ps1 index c7fc799..530d481 100644 --- a/source/tests/Test-PasswordNeverExpirePolicy.ps1 +++ b/source/tests/Test-PasswordNeverExpirePolicy.ps1 @@ -36,9 +36,6 @@ function Test-PasswordNeverExpirePolicy { Status = if ($passwordPolicy -eq 0) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure the 'Password expiration policy' is set to 'Set passwords to never expire'" - CISControl = "5.2" - CISDescription = "Use Unique Passwords" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-ReauthWithCode.ps1 b/source/tests/Test-ReauthWithCode.ps1 index ca64432..28ac0f0 100644 --- a/source/tests/Test-ReauthWithCode.ps1 +++ b/source/tests/Test-ReauthWithCode.ps1 @@ -35,9 +35,6 @@ function Test-ReauthWithCode { Status = if ($isReauthenticationRestricted) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure reauthentication with verification code is restricted" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-ReportSecurityInTeams.ps1 b/source/tests/Test-ReportSecurityInTeams.ps1 index 01b3bfb..f79cf17 100644 --- a/source/tests/Test-ReportSecurityInTeams.ps1 +++ b/source/tests/Test-ReportSecurityInTeams.ps1 @@ -45,9 +45,6 @@ function Test-ReportSecurityInTeams { Status = if ($securityReportEnabled) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure users can report security concerns in Teams" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-RestrictCustomScripts.ps1 b/source/tests/Test-RestrictCustomScripts.ps1 index 7ef723b..43a8eef 100644 --- a/source/tests/Test-RestrictCustomScripts.ps1 +++ b/source/tests/Test-RestrictCustomScripts.ps1 @@ -50,9 +50,6 @@ function Test-RestrictCustomScripts { Status = if ($complianceResult) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure custom script execution is restricted on site collections" - CISControl = "2.7" - CISDescription = "Allowlist Authorized Scripts" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-RestrictExternalSharing.ps1 b/source/tests/Test-RestrictExternalSharing.ps1 index 20d1107..f1b0568 100644 --- a/source/tests/Test-RestrictExternalSharing.ps1 +++ b/source/tests/Test-RestrictExternalSharing.ps1 @@ -35,9 +35,6 @@ function Test-RestrictExternalSharing { Status = if ($isRestricted) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure external content sharing is restricted" - CISControl = "3.3" - CISDescription = "Configure Data Access Control Lists" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-RestrictOutlookAddins.ps1 b/source/tests/Test-RestrictOutlookAddins.ps1 index 1b8d8d1..4438b50 100644 --- a/source/tests/Test-RestrictOutlookAddins.ps1 +++ b/source/tests/Test-RestrictOutlookAddins.ps1 @@ -67,9 +67,6 @@ function Test-RestrictOutlookAddins { Status = if ($isCompliant) { "Pass" } else { "Fail" } Details = $detailsString FailureReason = if ($isCompliant) { "N/A" } else { "Unauthorized Outlook add-ins found in custom or default policies." } - RecDescription = "Ensure users installing Outlook add-ins is not allowed" - CISControl = "9.4" - CISDescription = "Restrict Unnecessary or Unauthorized Browser and Email Client Extensions" } $auditResult = Initialize-CISAuditResult @params } @@ -78,4 +75,4 @@ function Test-RestrictOutlookAddins { # Return the audit result return $auditResult } -} \ No newline at end of file +} diff --git a/source/tests/Test-RestrictStorageProvidersOutlook.ps1 b/source/tests/Test-RestrictStorageProvidersOutlook.ps1 index 43dceaf..8400d72 100644 --- a/source/tests/Test-RestrictStorageProvidersOutlook.ps1 +++ b/source/tests/Test-RestrictStorageProvidersOutlook.ps1 @@ -43,9 +43,6 @@ function Test-RestrictStorageProvidersOutlook { Status = if ($allPoliciesRestricted) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure additional storage providers are restricted in Outlook on the web" - CISControl = "3.3" - CISDescription = "Configure Data Access Control Lists" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-RestrictTenantCreation.ps1 b/source/tests/Test-RestrictTenantCreation.ps1 index cef19d0..96bfb0f 100644 --- a/source/tests/Test-RestrictTenantCreation.ps1 +++ b/source/tests/Test-RestrictTenantCreation.ps1 @@ -35,9 +35,6 @@ function Test-RestrictTenantCreation { Status = if ($tenantCreationResult) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure 'Restrict non-admin users from creating tenants' is set to 'Yes'" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-SafeAttachmentsPolicy.ps1 b/source/tests/Test-SafeAttachmentsPolicy.ps1 index 0145a94..48597ce 100644 --- a/source/tests/Test-SafeAttachmentsPolicy.ps1 +++ b/source/tests/Test-SafeAttachmentsPolicy.ps1 @@ -40,9 +40,6 @@ function Test-SafeAttachmentsPolicy { Status = if ($result) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure Safe Attachments policy is enabled" - CISControl = "9.7" - CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-SafeAttachmentsTeams.ps1 b/source/tests/Test-SafeAttachmentsTeams.ps1 index a38e87d..a1cb453 100644 --- a/source/tests/Test-SafeAttachmentsTeams.ps1 +++ b/source/tests/Test-SafeAttachmentsTeams.ps1 @@ -47,9 +47,6 @@ function Test-SafeAttachmentsTeams { Status = if ($result) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure Safe Attachments for SharePoint, OneDrive, and Microsoft Teams is Enabled" - CISControl = "9.7, 10.1" - CISDescription = "Deploy and Maintain Email Server Anti-Malware Protections, Deploy and Maintain Anti-Malware Software" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-SafeLinksOfficeApps.ps1 b/source/tests/Test-SafeLinksOfficeApps.ps1 index 42dc59f..46ee852 100644 --- a/source/tests/Test-SafeLinksOfficeApps.ps1 +++ b/source/tests/Test-SafeLinksOfficeApps.ps1 @@ -54,9 +54,6 @@ function Test-SafeLinksOfficeApps { Status = if ($result) { "Pass" } else { "Fail" } Details = $details FailureReason = $failureReasons - RecDescription = "Ensure Safe Links for Office Applications is Enabled" - CISControl = "10.1" - CISDescription = "Deploy and Maintain Anti-Malware Software" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-SharePointAADB2B.ps1 b/source/tests/Test-SharePointAADB2B.ps1 index 45937fc..a9af0c4 100644 --- a/source/tests/Test-SharePointAADB2B.ps1 +++ b/source/tests/Test-SharePointAADB2B.ps1 @@ -24,9 +24,6 @@ function Test-SharePointAADB2B { Status = if ($SPOTenantAzureADB2B.EnableAzureADB2BIntegration) { "Pass" } else { "Fail" } Details = "EnableAzureADB2BIntegration: $($SPOTenantAzureADB2B.EnableAzureADB2BIntegration)" FailureReason = if (-not $SPOTenantAzureADB2B.EnableAzureADB2BIntegration) { "Azure AD B2B integration is not enabled" } else { "N/A" } - RecDescription = "Ensure SharePoint and OneDrive integration with Azure AD B2B is enabled" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } @@ -35,4 +32,4 @@ function Test-SharePointAADB2B { # Return auditResult return $auditResult } -} \ No newline at end of file +} diff --git a/source/tests/Test-SharePointExternalSharingDomains.ps1 b/source/tests/Test-SharePointExternalSharingDomains.ps1 index a8a8b4b..25f4213 100644 --- a/source/tests/Test-SharePointExternalSharingDomains.ps1 +++ b/source/tests/Test-SharePointExternalSharingDomains.ps1 @@ -25,9 +25,6 @@ function Test-SharePointExternalSharingDomains { Status = if ($isDomainRestrictionConfigured) { "Pass" } else { "Fail" } Details = "SharingDomainRestrictionMode: $($SPOTenant.SharingDomainRestrictionMode); SharingAllowedDomainList: $($SPOTenant.SharingAllowedDomainList)" FailureReason = if (-not $isDomainRestrictionConfigured) { "Domain restrictions for SharePoint external sharing are not configured to 'AllowList'. Current setting: $($SPOTenant.SharingDomainRestrictionMode)" } else { "N/A" } - RecDescription = "Ensure SharePoint external sharing is managed through domain whitelist/blacklists" - CISControl = "3.3" - CISDescription = "Configure Data Access Control Lists" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-SharePointGuestsItemSharing.ps1 b/source/tests/Test-SharePointGuestsItemSharing.ps1 index f429c7c..6f35325 100644 --- a/source/tests/Test-SharePointGuestsItemSharing.ps1 +++ b/source/tests/Test-SharePointGuestsItemSharing.ps1 @@ -25,9 +25,6 @@ function Test-SharePointGuestsItemSharing { Status = if ($isGuestResharingPrevented) { "Pass" } else { "Fail" } Details = "PreventExternalUsersFromResharing: $isGuestResharingPrevented" FailureReason = if (-not $isGuestResharingPrevented) { "Guest users can reshare items they don't own." } else { "N/A" } - RecDescription = "Ensure that SharePoint guest users cannot share items they don't own" - CISControl = "3.3" - CISDescription = "Configure Data Access Control Lists" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-SpamPolicyAdminNotify.ps1 b/source/tests/Test-SpamPolicyAdminNotify.ps1 index 4532acd..05be9aa 100644 --- a/source/tests/Test-SpamPolicyAdminNotify.ps1 +++ b/source/tests/Test-SpamPolicyAdminNotify.ps1 @@ -40,9 +40,6 @@ function Test-SpamPolicyAdminNotify { Status = if ($areSettingsEnabled) { "Pass" } else { "Fail" } Details = if ($areSettingsEnabled) { "Both BccSuspiciousOutboundMail and NotifyOutboundSpam are enabled." } else { $failureDetails -join ' ' } FailureReason = if (-not $areSettingsEnabled) { "One or both spam policies are not set to notify administrators." } else { "N/A" } - RecDescription = "Ensure Exchange Online Spam Policies are set to notify administrators" - CISControl = "17.5" - CISDescription = "Assign Key Roles and Responsibilities" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-TeamsExternalAccess.ps1 b/source/tests/Test-TeamsExternalAccess.ps1 index 4a2ad40..8b0cad2 100644 --- a/source/tests/Test-TeamsExternalAccess.ps1 +++ b/source/tests/Test-TeamsExternalAccess.ps1 @@ -35,9 +35,6 @@ function Test-TeamsExternalAccess { Status = if ($isCompliant) { "Pass" } else { "Fail" } Details = "AllowTeamsConsumer: $($externalAccessConfig.AllowTeamsConsumer); AllowPublicUsers: $($externalAccessConfig.AllowPublicUsers); AllowFederatedUsers: $($externalAccessConfig.AllowFederatedUsers); AllowedDomains limited: $allowedDomainsLimited" FailureReason = if (-not $isCompliant) { "One or more external access configurations are not compliant." } else { "N/A" } - RecDescription = "Ensure 'external access' is restricted in the Teams admin center" - CISControl = "0.0" - CISDescription = "Explicitly Not Mapped" } $auditResult = Initialize-CISAuditResult @params } diff --git a/source/tests/Test-TeamsExternalFileSharing.ps1 b/source/tests/Test-TeamsExternalFileSharing.ps1 index 697b2bc..fd4e653 100644 --- a/source/tests/Test-TeamsExternalFileSharing.ps1 +++ b/source/tests/Test-TeamsExternalFileSharing.ps1 @@ -39,9 +39,6 @@ function Test-TeamsExternalFileSharing { Status = if ($isCompliant) { "Pass" } else { "Fail" } Details = if (-not $isCompliant) { "Non-approved providers enabled: $($nonCompliantProviders -join ', ')" } else { "All cloud storage services are approved providers" } FailureReason = if (-not $isCompliant) { "The following non-approved providers are enabled: $($nonCompliantProviders -join ', ')" } else { "N/A" } - RecDescription = "Ensure external file sharing in Teams is enabled for only approved cloud storage services" - CISControl = "3.3" - CISDescription = "Configure Data Access Control Lists" } $auditResult = Initialize-CISAuditResult @params } From 290540b25a5cc6deeca02974c8d9ad1db5c30393 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 19:25:27 -0500 Subject: [PATCH 63/67] fix: Refactor Initialize-CISAuditResult to use global test definitions --- source/Private/Initialize-CISAuditResult.ps1 | 3 +-- source/Public/Invoke-M365SecurityAudit.ps1 | 3 ++- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/source/Private/Initialize-CISAuditResult.ps1 b/source/Private/Initialize-CISAuditResult.ps1 index dd92a7b..b1e2e09 100644 --- a/source/Private/Initialize-CISAuditResult.ps1 +++ b/source/Private/Initialize-CISAuditResult.ps1 @@ -17,8 +17,7 @@ function Initialize-CISAuditResult { ) # Import the test definitions CSV file - $testDefinitionsPath = Join-Path -Path $PSScriptRoot -ChildPath "helper/TestDefinitions.csv" - $testDefinitions = Import-Csv -Path $testDefinitionsPath + $testDefinitions = $script:TestDefinitionsObject # Find the row that matches the provided recommendation (Rec) $testDefinition = $testDefinitions | Where-Object { $_.Rec -eq $Rec } diff --git a/source/Public/Invoke-M365SecurityAudit.ps1 b/source/Public/Invoke-M365SecurityAudit.ps1 index f2059c0..474cc09 100644 --- a/source/Public/Invoke-M365SecurityAudit.ps1 +++ b/source/Public/Invoke-M365SecurityAudit.ps1 @@ -161,7 +161,8 @@ function Invoke-M365SecurityAudit { # Load test definitions from CSV $testDefinitionsPath = Join-Path -Path $PSScriptRoot -ChildPath "helper\TestDefinitions.csv" $testDefinitions = Import-Csv -Path $testDefinitionsPath - + # Load the Test Definitions into the script scope for use in other functions + $script:TestDefinitionsObject = $testDefinitions # Apply filters based on parameter sets switch ($PSCmdlet.ParameterSetName) { 'ELevelFilter' { From fc9923b980b44ca7a10a8406914d57763fdef605 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 19:52:47 -0500 Subject: [PATCH 64/67] docs: updated online help link --- source/Public/Invoke-M365SecurityAudit.ps1 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/Public/Invoke-M365SecurityAudit.ps1 b/source/Public/Invoke-M365SecurityAudit.ps1 index 474cc09..fb0ee29 100644 --- a/source/Public/Invoke-M365SecurityAudit.ps1 +++ b/source/Public/Invoke-M365SecurityAudit.ps1 @@ -57,7 +57,7 @@ - For full license details, visit: https://creativecommons.org/licenses/by-nc-sa/4.0/deed.en - Register for CIS Benchmarks at: https://www.cisecurity.org/cis-benchmarks .LINK - Online Version: https://github.com/CriticalSolutionsNetwork/M365FoundationsCISReport + https://criticalsolutionsnetwork.github.io/M365FoundationsCISReport/#Invoke-M365SecurityAudit #> function Invoke-M365SecurityAudit { From ac8014ae776f23676cb9960ed3e827fb38ebd9ab Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 19:53:15 -0500 Subject: [PATCH 65/67] docs: update CHANGELOG --- CHANGELOG.md | 25 +++++++++++++++++++++++++ 1 file changed, 25 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index e4c5c68..3b53a5e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,30 @@ The format is based on and uses the types of changes according to [Keep a Change ## [Unreleased] +### Added + +- Array list to store the results of the audit. +- Arraylist tests and helper template. +- New testing function. +- Missing properties to CSV. + +### Changed + +- Refactored object initialization to source `RecDescription`, `CISControl`, and `CISDescription` properties from the CSV. +- Added `Automated` and `Connection` properties to the output object. +- All test functions aligned with the test-template. +- Initialize-CISAuditResult refactored to use global test definitions. + +### Fixed + +- Corrected test-template. +- Details added to pass. + +### Docs + +- Updated comments and documentation for new functions. + + ## [0.1.2] - 2024-04-29 ### Added @@ -26,6 +50,7 @@ The format is based on and uses the types of changes according to [Keep a Change - Updated comments for new functions. - Updated help documentation. +- Updated online link in public function. ## [0.1.1] - 2024-04-02 From d1555e1d25dfb2d6af701a9d951d15a0bf8e1286 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 20:07:46 -0500 Subject: [PATCH 66/67] docs: update help --- README.md | Bin 20738 -> 20760 bytes docs/index.html | Bin 61996 -> 61994 bytes helpers/Build-Help.ps1 | 2 +- 3 files changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 6ec049da30a1b7e73d7752d987c5183679b4d37a..0226d19691b8da57f72cac03d0db78b6b1fa1780 100644 GIT binary patch delta 65 zcmZo##5iLShTT&1dXo4H&F|*c3<_GZ=1sU8^+tz+$$^Wy(eD zHVjD&MGSV687;&&|5H}r+N`E`PGYi(uE=Hq_ZZeqete9Z>wFtnC(rYGHu=JGj>#W_ zuK?L5oA0SzVA*^o@{{vq561 J>n{243jpNBJWc=r delta 447 zcmZ4Wgn7*q<_Ra1O&IhUj2JAzqydm+!l1xl2!vJ)1`Nhv(sJYLS|xTHh9rg}2D{0% zy0Vj7lw&3fSc`4`r>wvQlh`b)cU}UCWK)Dj2XerQ%dJM@xb-6%MXP_>ScqULJ5olg8P&@~y1|$M9shGhJ zXmSZdIgnSxkPXz~3-qwrWZ`+*lZ)nw)t3Op3mDWH>;}d?ley;^Zw{Cr!U7M|!b6Ia Nk1S5uth3~wF910qX(9js diff --git a/helpers/Build-Help.ps1 b/helpers/Build-Help.ps1 index 60067be..c00d0b8 100644 --- a/helpers/Build-Help.ps1 +++ b/helpers/Build-Help.ps1 @@ -3,7 +3,7 @@ Import-Module .\output\module\M365FoundationsCISReport\*\*.psd1 .\helpers\psDoc-master\src\psDoc.ps1 -moduleName M365FoundationsCISReport -outputDir ".\" -template ".\helpers\psDoc-master\src\out-markdown-template.ps1" -fileName ".\README.md" -#<# +<# $ver = "v0.1.2" git checkout main git pull origin main From 54f9e086a9065f73f345b7b857c9b512ac23534c Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Tue, 28 May 2024 20:10:54 -0500 Subject: [PATCH 67/67] docs: Update README --- README.md | Bin 20760 -> 20736 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/README.md b/README.md index 0226d19691b8da57f72cac03d0db78b6b1fa1780..a150f8950945c33b994f14eab72f88f2eee2d7d9 100644 GIT binary patch delta 27 jcmbQSh_PW2Z8lKgW8A!kGshhOkXQ+H delta 27 jcmZoz#5iLS