From bad103f0cfaaec4117ff6ef2e49af6beaf5ba281 Mon Sep 17 00:00:00 2001 From: DrIOS <58635327+DrIOSX@users.noreply.github.com> Date: Sun, 23 Jun 2024 16:06:31 -0500 Subject: [PATCH] add: Get-CISSpoOutput function and updated respective tests --- source/Private/Get-CISSpoOutput.ps1 | 120 ++++++++++++++++++ source/Private/Get-UrlLine.ps1 | 32 +++++ .../Test-DisallowInfectedFilesDownload.ps1 | 2 +- source/tests/Test-GuestAccessExpiration.ps1 | 2 +- source/tests/Test-LinkSharingRestrictions.ps1 | 2 +- source/tests/Test-ModernAuthSharePoint.ps1 | 2 +- .../Test-OneDriveContentRestrictions.ps1 | 2 +- .../tests/Test-OneDriveSyncRestrictions.ps1 | 2 +- source/tests/Test-ReauthWithCode.ps1 | 2 +- source/tests/Test-RestrictCustomScripts.ps1 | 2 +- source/tests/Test-RestrictExternalSharing.ps1 | 2 +- source/tests/Test-SharePointAADB2B.ps1 | 2 +- .../Test-SharePointExternalSharingDomains.ps1 | 2 +- .../Test-SharePointGuestsItemSharing.ps1 | 2 +- tests/Unit/Private/Get-CISSpoOutput.tests.ps1 | 27 ++++ tests/Unit/Private/Get-UrlLine.tests.ps1 | 27 ++++ 16 files changed, 218 insertions(+), 12 deletions(-) create mode 100644 source/Private/Get-CISSpoOutput.ps1 create mode 100644 source/Private/Get-UrlLine.ps1 create mode 100644 tests/Unit/Private/Get-CISSpoOutput.tests.ps1 create mode 100644 tests/Unit/Private/Get-UrlLine.tests.ps1 diff --git a/source/Private/Get-CISSpoOutput.ps1 b/source/Private/Get-CISSpoOutput.ps1 new file mode 100644 index 0000000..7ed1088 --- /dev/null +++ b/source/Private/Get-CISSpoOutput.ps1 @@ -0,0 +1,120 @@ +<# + .SYNOPSIS + This is a sample Private function only visible within the module. + .DESCRIPTION + This sample function is not exported to the module and only return the data passed as parameter. + .EXAMPLE + $null = Get-CISSpoOutput -PrivateData 'NOTHING TO SEE HERE' + .PARAMETER PrivateData + The PrivateData parameter is what will be returned without transformation. +#> +function Get-CISSpoOutput { + [cmdletBinding()] + [OutputType([string])] + param( + [Parameter(Mandatory = $true)] + [String] + $Rec + ) + begin { + # Begin Block # + <# + # Tests + 7.2.1 + 7.2.2 + 7.2.3 + 7.2.4 + 7.2.5 + 7.2.6 + 7.2.7 + 7.2.9 + 7.2.10 + 7.3.1 + 7.3.2 + 7.3.4 + + # Test number array + $testNumbers = @('7.2.1', '7.2.2', '7.2.3', '7.2.4', '7.2.5', '7.2.6', '7.2.7', '7.2.9', '7.2.10', '7.3.1', '7.3.2', '7.3.4') + #> + } + process { + switch ($Rec) { + '7.2.1' { + # Test-ModernAuthSharePoint.ps1 + $SPOTenant = Get-SPOTenant | Select-Object -Property LegacyAuthProtocolsEnabled + return $SPOTenant + } + '7.2.2' { + # Test-SharePointAADB2B.ps1 + # 7.2.2 (L1) Ensure SharePoint and OneDrive integration with Azure AD B2B is enabled + $SPOTenantAzureADB2B = Get-SPOTenant | Select-Object EnableAzureADB2BIntegration + return $SPOTenantAzureADB2B + } + '7.2.3' { + # Test-RestrictExternalSharing.ps1 + # 7.2.3 (L1) Ensure external content sharing is restricted + # Retrieve the SharingCapability setting for the SharePoint tenant + $SPOTenantSharingCapability = Get-SPOTenant | Select-Object SharingCapability + return $SPOTenantSharingCapability + } + '7.2.4' { + # Test-OneDriveContentRestrictions.ps1 + $SPOTenant = Get-SPOTenant | Select-Object OneDriveSharingCapability + return $SPOTenant + } + '7.2.5' { + # Test-SharePointGuestsItemSharing.ps1 + # 7.2.5 (L2) Ensure that SharePoint guest users cannot share items they don't own + $SPOTenant = Get-SPOTenant | Select-Object PreventExternalUsersFromResharing + return $SPOTenant + } + '7.2.6' { + # Test-SharePointExternalSharingDomains.ps1 + # 7.2.6 (L2) Ensure SharePoint external sharing is managed through domain whitelist/blacklists + $SPOTenant = Get-SPOTenant | Select-Object SharingDomainRestrictionMode, SharingAllowedDomainList + return $SPOTenant + } + '7.2.7' { + # Test-LinkSharingRestrictions.ps1 + # Retrieve link sharing configuration for SharePoint and OneDrive + $SPOTenantLinkSharing = Get-SPOTenant | Select-Object DefaultSharingLinkType + return $SPOTenantLinkSharing + } + '7.2.9' { + # Test-GuestAccessExpiration.ps1 + # Retrieve SharePoint tenant settings related to guest access expiration + $SPOTenantGuestAccess = Get-SPOTenant | Select-Object ExternalUserExpirationRequired, ExternalUserExpireInDays + return $SPOTenantGuestAccess + } + '7.2.10' { + # Test-ReauthWithCode.ps1 + # 7.2.10 (L1) Ensure reauthentication with verification code is restricted + # Retrieve reauthentication settings for SharePoint Online + $SPOTenantReauthentication = Get-SPOTenant | Select-Object EmailAttestationRequired, EmailAttestationReAuthDays + return $SPOTenantReauthentication + } + '7.3.1' { + # Test-DisallowInfectedFilesDownload.ps1 + # Retrieve the SharePoint tenant configuration + $SPOTenantDisallowInfectedFileDownload = Get-SPOTenant | Select-Object DisallowInfectedFileDownload + return $SPOTenantDisallowInfectedFileDownload + } + '7.3.2' { + # Test-OneDriveSyncRestrictions.ps1 + # Retrieve OneDrive sync client restriction settings + $SPOTenantSyncClientRestriction = Get-SPOTenantSyncClientRestriction | Select-Object TenantRestrictionEnabled, AllowedDomainList + return $SPOTenantSyncClientRestriction + } + '7.3.4' { + # Test-RestrictCustomScripts.ps1 + # Retrieve all site collections and select necessary properties + $SPOSitesCustomScript = Get-SPOSite -Limit All | Select-Object Title, Url, DenyAddAndCustomizePages + return $SPOSitesCustomScript + } + default { throw "No match found for test: $Rec" } + } + } + end { + Write-Verbose "Retuning data for Rec: $Rec" + } +} # end function Get-CISMSTeamsOutput \ No newline at end of file diff --git a/source/Private/Get-UrlLine.ps1 b/source/Private/Get-UrlLine.ps1 new file mode 100644 index 0000000..37a34a2 --- /dev/null +++ b/source/Private/Get-UrlLine.ps1 @@ -0,0 +1,32 @@ +<# + .SYNOPSIS + This is a sample Private function only visible within the module. + + .DESCRIPTION + This sample function is not exported to the module and only return the data passed as parameter. + + .EXAMPLE + $null = Get-UrlLine -PrivateData 'NOTHING TO SEE HERE' + + .PARAMETER PrivateData + The PrivateData parameter is what will be returned without transformation. +#> +function Get-UrlLine { + [cmdletBinding()] + [OutputType([string])] + param ( + [Parameter(Mandatory=$true)] + [string]$Output + ) + # Split the output into lines + $Lines = $Output -split "`n" + # Iterate over each line + foreach ($Line in $Lines) { + # If the line starts with 'https', return it + if ($Line.StartsWith('https')) { + return $Line.Trim() + } + } + # If no line starts with 'https', return an empty string + return $null + } \ No newline at end of file diff --git a/source/tests/Test-DisallowInfectedFilesDownload.ps1 b/source/tests/Test-DisallowInfectedFilesDownload.ps1 index b9e72af..2da1c17 100644 --- a/source/tests/Test-DisallowInfectedFilesDownload.ps1 +++ b/source/tests/Test-DisallowInfectedFilesDownload.ps1 @@ -34,7 +34,7 @@ function Test-DisallowInfectedFilesDownload { # - Condition C: Verification using the PowerShell command indicates that the setting is incorrectly configured. # Retrieve the SharePoint tenant configuration - $SPOTenantDisallowInfectedFileDownload = Get-SPOTenant | Select-Object DisallowInfectedFileDownload + $SPOTenantDisallowInfectedFileDownload = Get-CISSpoOutput -Rec $recnum # Condition A: The `DisallowInfectedFileDownload` setting is set to `True` $isDisallowInfectedFileDownloadEnabled = $SPOTenantDisallowInfectedFileDownload.DisallowInfectedFileDownload diff --git a/source/tests/Test-GuestAccessExpiration.ps1 b/source/tests/Test-GuestAccessExpiration.ps1 index 782b9d7..8c0fcbc 100644 --- a/source/tests/Test-GuestAccessExpiration.ps1 +++ b/source/tests/Test-GuestAccessExpiration.ps1 @@ -34,7 +34,7 @@ function Test-GuestAccessExpiration { # - Condition C: Verification using the SharePoint Admin Center indicates that guest access is not set to expire automatically after the specified number of days. # Retrieve SharePoint tenant settings related to guest access expiration - $SPOTenantGuestAccess = Get-SPOTenant | Select-Object ExternalUserExpirationRequired, ExternalUserExpireInDays + $SPOTenantGuestAccess = Get-CISSpoOutput -Rec $recnum $isGuestAccessExpirationConfiguredCorrectly = $SPOTenantGuestAccess.ExternalUserExpirationRequired -and $SPOTenantGuestAccess.ExternalUserExpireInDays -le 30 # Prepare failure reasons and details based on compliance diff --git a/source/tests/Test-LinkSharingRestrictions.ps1 b/source/tests/Test-LinkSharingRestrictions.ps1 index 5f41fe8..2144646 100644 --- a/source/tests/Test-LinkSharingRestrictions.ps1 +++ b/source/tests/Test-LinkSharingRestrictions.ps1 @@ -33,7 +33,7 @@ function Test-LinkSharingRestrictions { # - Condition C: Verification using the UI indicates that the link sharing settings are not configured as recommended. # Retrieve link sharing configuration for SharePoint and OneDrive - $SPOTenantLinkSharing = Get-SPOTenant | Select-Object DefaultSharingLinkType + $SPOTenantLinkSharing = Get-CISSpoOutput -Rec $recnum $isLinkSharingRestricted = $SPOTenantLinkSharing.DefaultSharingLinkType -eq 'Direct' # Or 'SpecificPeople' as per the recommendation # Prepare failure reasons and details based on compliance diff --git a/source/tests/Test-ModernAuthSharePoint.ps1 b/source/tests/Test-ModernAuthSharePoint.ps1 index 66d6614..85336c9 100644 --- a/source/tests/Test-ModernAuthSharePoint.ps1 +++ b/source/tests/Test-ModernAuthSharePoint.ps1 @@ -33,7 +33,7 @@ function Test-ModernAuthSharePoint { process { try { # 7.2.1 (L1) Ensure modern authentication for SharePoint applications is required - $SPOTenant = Get-SPOTenant | Select-Object -Property LegacyAuthProtocolsEnabled + $SPOTenant = Get-CISSpoOutput -Rec $recnum $modernAuthForSPRequired = -not $SPOTenant.LegacyAuthProtocolsEnabled # Prepare failure reasons and details based on compliance diff --git a/source/tests/Test-OneDriveContentRestrictions.ps1 b/source/tests/Test-OneDriveContentRestrictions.ps1 index a87ffd1..bed9d6e 100644 --- a/source/tests/Test-OneDriveContentRestrictions.ps1 +++ b/source/tests/Test-OneDriveContentRestrictions.ps1 @@ -34,7 +34,7 @@ function Test-OneDriveContentRestrictions { # 7.2.4 (L2) Ensure OneDrive content sharing is restricted # Retrieve OneDrive sharing capability settings - $SPOTenant = Get-SPOTenant | Select-Object OneDriveSharingCapability + $SPOTenant = Get-CISSpoOutput -Rec $recnum $isOneDriveSharingRestricted = $SPOTenant.OneDriveSharingCapability -eq 'Disabled' # Prepare failure reasons and details based on compliance diff --git a/source/tests/Test-OneDriveSyncRestrictions.ps1 b/source/tests/Test-OneDriveSyncRestrictions.ps1 index 4a6d0fb..373a815 100644 --- a/source/tests/Test-OneDriveSyncRestrictions.ps1 +++ b/source/tests/Test-OneDriveSyncRestrictions.ps1 @@ -32,7 +32,7 @@ function Test-OneDriveSyncRestrictions { # - Condition C: "AllowedDomainList" does not contain the trusted domain GUIDs from the on-premises environment. # Retrieve OneDrive sync client restriction settings - $SPOTenantSyncClientRestriction = Get-SPOTenantSyncClientRestriction | Select-Object TenantRestrictionEnabled, AllowedDomainList + $SPOTenantSyncClientRestriction = Get-CISSpoOutput -Rec $recnum $isSyncRestricted = $SPOTenantSyncClientRestriction.TenantRestrictionEnabled -and $SPOTenantSyncClientRestriction.AllowedDomainList # Condition A: Check if TenantRestrictionEnabled is True diff --git a/source/tests/Test-ReauthWithCode.ps1 b/source/tests/Test-ReauthWithCode.ps1 index feccb93..e5d0f3a 100644 --- a/source/tests/Test-ReauthWithCode.ps1 +++ b/source/tests/Test-ReauthWithCode.ps1 @@ -34,7 +34,7 @@ function Test-ReauthWithCode { # 7.2.10 (L1) Ensure reauthentication with verification code is restricted # Retrieve reauthentication settings for SharePoint Online - $SPOTenantReauthentication = Get-SPOTenant | Select-Object EmailAttestationRequired, EmailAttestationReAuthDays + $SPOTenantReauthentication = Get-CISSpoOutput -Rec $recnum $isReauthenticationRestricted = $SPOTenantReauthentication.EmailAttestationRequired -and $SPOTenantReauthentication.EmailAttestationReAuthDays -le 15 # Prepare failure reasons and details based on compliance diff --git a/source/tests/Test-RestrictCustomScripts.ps1 b/source/tests/Test-RestrictCustomScripts.ps1 index f492085..7705721 100644 --- a/source/tests/Test-RestrictCustomScripts.ps1 +++ b/source/tests/Test-RestrictCustomScripts.ps1 @@ -32,7 +32,7 @@ function Test-RestrictCustomScripts { # - Condition C: Verification using the SharePoint Admin Center indicates that the `DenyAddAndCustomizePages` setting is not enforced. # Retrieve all site collections and select necessary properties - $SPOSitesCustomScript = Get-SPOSite -Limit All | Select-Object Title, Url, DenyAddAndCustomizePages + $SPOSitesCustomScript = Get-CISSpoOutput -Rec $recnum # Process URLs to replace 'sharepoint.com' with '' $processedUrls = $SPOSitesCustomScript | ForEach-Object { diff --git a/source/tests/Test-RestrictExternalSharing.ps1 b/source/tests/Test-RestrictExternalSharing.ps1 index dc9c016..3c99f67 100644 --- a/source/tests/Test-RestrictExternalSharing.ps1 +++ b/source/tests/Test-RestrictExternalSharing.ps1 @@ -36,7 +36,7 @@ function Test-RestrictExternalSharing { # 7.2.3 (L1) Ensure external content sharing is restricted # Retrieve the SharingCapability setting for the SharePoint tenant - $SPOTenantSharingCapability = Get-SPOTenant | Select-Object SharingCapability + $SPOTenantSharingCapability = Get-CISSpoOutput -Rec $recnum $isRestricted = $SPOTenantSharingCapability.SharingCapability -in @('ExternalUserSharingOnly', 'ExistingExternalUserSharingOnly', 'Disabled') # Prepare failure reasons and details based on compliance diff --git a/source/tests/Test-SharePointAADB2B.ps1 b/source/tests/Test-SharePointAADB2B.ps1 index fa1f733..d0bf748 100644 --- a/source/tests/Test-SharePointAADB2B.ps1 +++ b/source/tests/Test-SharePointAADB2B.ps1 @@ -33,7 +33,7 @@ function Test-SharePointAADB2B { process { try { # 7.2.2 (L1) Ensure SharePoint and OneDrive integration with Azure AD B2B is enabled - $SPOTenantAzureADB2B = Get-SPOTenant | Select-Object EnableAzureADB2BIntegration + $SPOTenantAzureADB2B = Get-CISSpoOutput -Rec $recnum # Populate the auditResult object with the required properties $params = @{ diff --git a/source/tests/Test-SharePointExternalSharingDomains.ps1 b/source/tests/Test-SharePointExternalSharingDomains.ps1 index 035dc29..64c53c6 100644 --- a/source/tests/Test-SharePointExternalSharingDomains.ps1 +++ b/source/tests/Test-SharePointExternalSharingDomains.ps1 @@ -33,7 +33,7 @@ function Test-SharePointExternalSharingDomains { process { try { # 7.2.6 (L2) Ensure SharePoint external sharing is managed through domain whitelist/blacklists - $SPOTenant = Get-SPOTenant | Select-Object SharingDomainRestrictionMode, SharingAllowedDomainList + $SPOTenant = Get-CISSpoOutput -Rec $recnum $isDomainRestrictionConfigured = $SPOTenant.SharingDomainRestrictionMode -eq 'AllowList' # Populate the auditResult object with the required properties diff --git a/source/tests/Test-SharePointGuestsItemSharing.ps1 b/source/tests/Test-SharePointGuestsItemSharing.ps1 index 0ac33e2..b09a66a 100644 --- a/source/tests/Test-SharePointGuestsItemSharing.ps1 +++ b/source/tests/Test-SharePointGuestsItemSharing.ps1 @@ -33,7 +33,7 @@ function Test-SharePointGuestsItemSharing { process { try { # 7.2.5 (L2) Ensure that SharePoint guest users cannot share items they don't own - $SPOTenant = Get-SPOTenant | Select-Object PreventExternalUsersFromResharing + $SPOTenant = Get-CISSpoOutput -Rec $recnum $isGuestResharingPrevented = $SPOTenant.PreventExternalUsersFromResharing # Populate the auditResult object with the required properties diff --git a/tests/Unit/Private/Get-CISSpoOutput.tests.ps1 b/tests/Unit/Private/Get-CISSpoOutput.tests.ps1 new file mode 100644 index 0000000..4a2aa69 --- /dev/null +++ b/tests/Unit/Private/Get-CISSpoOutput.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' + } + } + } +} + diff --git a/tests/Unit/Private/Get-UrlLine.tests.ps1 b/tests/Unit/Private/Get-UrlLine.tests.ps1 new file mode 100644 index 0000000..4a2aa69 --- /dev/null +++ b/tests/Unit/Private/Get-UrlLine.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' + } + } + } +} +