From 7e4b581038561c4a64f257bb601072df7e6895b1 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Sun, 27 Sep 2015 22:25:48 +1000 Subject: [PATCH 01/31] Removed faulty DCache stub generation --- Tests/xSharePoint.TestHarness.psm1 | 29 +---------------------------- 1 file changed, 1 insertion(+), 28 deletions(-) diff --git a/Tests/xSharePoint.TestHarness.psm1 b/Tests/xSharePoint.TestHarness.psm1 index 59f098825..ac58cfa37 100644 --- a/Tests/xSharePoint.TestHarness.psm1 +++ b/Tests/xSharePoint.TestHarness.psm1 @@ -37,8 +37,7 @@ function Invoke-xSharePointTests() { function Write-xSharePointStubFiles() { param ( - [parameter(Mandatory = $true)] [System.String] $SharePointStubPath, - [parameter(Mandatory = $true)] [System.String] $DCacheStubPath + [parameter(Mandatory = $true)] [System.String] $SharePointStubPath ) Add-PSSnapin Microsoft.SharePoint.PowerShell @@ -67,30 +66,4 @@ function Write-xSharePointStubFiles() { $line | Out-File $SharePointStubPath -Encoding utf8 -Append } - - - Use-CacheCluster - - $dcacheStubContent = ((Get-Command | Where-Object { $_.Source -match "DistributedCache*" } ) | ForEach-Object -Process { - $signature = $null - $command = $_ - $metadata = New-Object -TypeName System.Management.Automation.CommandMetaData -ArgumentList $command - $definition = [System.Management.Automation.ProxyCommand]::Create($metadata) - foreach ($line in $definition -split "`n") - { - if ($line.Trim() -eq 'begin') - { - break - } - $signature += $line - } - "function $($command.Name) { `n $signature `n } `n" - }) | Out-String - - foreach ($line in $dcacheStubContent.Split([Environment]::NewLine)) { - $line = $line -replace "\[System.Nullable\[Microsoft.*]]", "[System.Nullable[object]]" - $line = $line -replace "\[Microsoft.*.\]", "[object]" - - $line | Out-File $DCacheStubPath -Encoding utf8 -Append - } } \ No newline at end of file From abf5a3a6881599c0d340db6e63b2a4e448980675 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Sun, 27 Sep 2015 23:59:06 +1000 Subject: [PATCH 02/31] Fixes to parameters and return values --- .../MSFT_xSPCacheAccounts/MSFT_xSPCacheAccounts.psm1 | 2 +- Tests/xSharePoint/xSharePoint.xSPCacheAccounts.Tests.ps1 | 8 ++++---- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPCacheAccounts/MSFT_xSPCacheAccounts.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPCacheAccounts/MSFT_xSPCacheAccounts.psm1 index 1034c3baf..364ef1cc6 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPCacheAccounts/MSFT_xSPCacheAccounts.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPCacheAccounts/MSFT_xSPCacheAccounts.psm1 @@ -18,7 +18,7 @@ function Get-TargetResource $wa = Get-SPWebApplication -Identity $params.WebAppUrl -ErrorAction SilentlyContinue - if ($null -eq $wa) { return @{} } + if ($null -eq $wa) { return $null } $returnVal = @{} $returnVal.Add("WebAppUrl", $params.WebAppUrl) diff --git a/Tests/xSharePoint/xSharePoint.xSPCacheAccounts.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPCacheAccounts.Tests.ps1 index 976d52a9f..7dff5d9a1 100644 --- a/Tests/xSharePoint/xSharePoint.xSPCacheAccounts.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPCacheAccounts.Tests.ps1 @@ -92,8 +92,8 @@ Describe "xSPCacheAccounts" { Context "Cache accounts have been configured, but the reader account is wrong" { Mock Get-SPWebApplication { return @{ Properties = @{ - SuperUserAlias = $testParams.SuperUserAlias - SuperReaderAlias = "WRONG\AccountName" + portalsuperuseraccount = $testParams.SuperUserAlias + portalsuperreaderaccount = "WRONG\AccountName" } }} @@ -110,8 +110,8 @@ Describe "xSPCacheAccounts" { Context "Cache accounts have been configured, but the super account is wrong" { Mock Get-SPWebApplication { return @{ Properties = @{ - SuperUserAlias = "WRONG\AccountName" - SuperReaderAlias = $testParams.SuperReaderAlias + portalsuperuseraccount = "WRONG\AccountName" + portalsuperreaderaccount = $testParams.SuperReaderAlias } }} From 8c280012b14f1ce2a14aa81f168621cac3825c75 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 00:11:01 +1000 Subject: [PATCH 03/31] Expanded tests to cover all scenarios coded for --- .../xSharePoint.xSPCreateFarm.Tests.ps1 | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 index fc118d243..d86efdb0e 100644 --- a/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 @@ -42,7 +42,7 @@ Describe "xSPCreateFarm" { Mock Get-xSharePointInstalledProductVersion { return @{ FileMajorPart = $majorBuildNumber } } Context "no farm is configured locally and a supported version of SharePoint is installed" { - Mock Get-SPFarm { return $null } + Mock Get-SPFarm { throw "Unable to detect local farm" } It "the get method returns null when the farm is not configured" { Get-TargetResource @testParams | Should BeNullOrEmpty @@ -103,6 +103,22 @@ Describe "xSPCreateFarm" { } } + Context "a farm exists locally with the wrong farm account" { + Mock Get-SPFarm { return @{ + DefaultServiceAccount = @{ Name = "WRONG\account" } + Name = $testParams.FarmConfigDatabaseName + }} + + It "the get method returns current values" { + Get-TargetResource @testParams | Should Not BeNullOrEmpty + } + + It "returns true from the test method as changing the farm account isn't supported so set shouldn't be called" { + Test-TargetResource @testParams | Should Be $true + } + + } + Context "no farm is configured locally, a supported version is installed and no central admin port is specified" { $testParams.Remove("CentralAdministrationPort") From 2bae03955438fb61894a5a6c3a536ccc9a78a24a Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 00:11:32 +1000 Subject: [PATCH 04/31] Formatting fixes --- Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 index d86efdb0e..acb2e84c5 100644 --- a/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 @@ -103,13 +103,13 @@ Describe "xSPCreateFarm" { } } - Context "a farm exists locally with the wrong farm account" { - Mock Get-SPFarm { return @{ + Context "a farm exists locally with the wrong farm account" { + Mock Get-SPFarm { return @{ DefaultServiceAccount = @{ Name = "WRONG\account" } Name = $testParams.FarmConfigDatabaseName }} - It "the get method returns current values" { + It "the get method returns current values" { Get-TargetResource @testParams | Should Not BeNullOrEmpty } From 2e91b62afe3de31c8eabb2284ba777cdaaedacd5 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 00:31:44 +1000 Subject: [PATCH 05/31] Fixes to diagnostic logging and create farm tests --- .../xSharePoint.xSPCreateFarm.Tests.ps1 | 5 +++ ...int.xSPDiagnosticLoggingSettings.Tests.ps1 | 35 +++++++++++++++++++ 2 files changed, 40 insertions(+) diff --git a/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 index acb2e84c5..47f668ff6 100644 --- a/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 @@ -108,6 +108,11 @@ Describe "xSPCreateFarm" { DefaultServiceAccount = @{ Name = "WRONG\account" } Name = $testParams.FarmConfigDatabaseName }} + Mock Get-SPWebApplication { return @(@{ + IsAdministrationWebApplication = $true + ContentDatabases = @(@{ Name = $testParams.AdminContentDatabaseName }) + Url = "http://$($env:ComputerName):$($testParams.CentralAdministrationPort)" + })} It "the get method returns current values" { Get-TargetResource @testParams | Should Not BeNullOrEmpty diff --git a/Tests/xSharePoint/xSharePoint.xSPDiagnosticLoggingSettings.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPDiagnosticLoggingSettings.Tests.ps1 index 42587234b..dd9685437 100644 --- a/Tests/xSharePoint/xSharePoint.xSPDiagnosticLoggingSettings.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPDiagnosticLoggingSettings.Tests.ps1 @@ -145,5 +145,40 @@ Describe "xSPDiagnosticLoggingSettings" { Assert-MockCalled Set-SPDiagnosticConfig } } + + Context "Diagnostic configuration needs updating and the InstallAccount option is used" { + $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force))) ) + + Mock Get-SPDiagnosticConfig { return @{ + AppAnalyticsAutomaticUploadEnabled = $testParams.AppAnalyticsAutomaticUploadEnabled + CustomerExperienceImprovementProgramEnabled = $testParams.CustomerExperienceImprovementProgramEnabled + ErrorReportingEnabled = $testParams.ErrorReportingEnabled + ErrorReportingAutomaticUploadEnabled = $testParams.ErrorReportingAutomaticUploadEnabled + DownloadErrorReportingUpdatesEnabled = $testParams.DownloadErrorReportingUpdatesEnabled + DaysToKeepLogs = $testParams.DaysToKeepLogs + LogMaxDiskSpaceUsageEnabled = $testParams.LogMaxDiskSpaceUsageEnabled + LogDiskSpaceUsageGB = 1 + LogLocation = $testParams.LogPath + LogCutInterval = $testParams.LogCutInterval + EventLogFloodProtectionEnabled = $testParams.EventLogFloodProtectionEnabled + EventLogFloodProtectionThreshold = $testParams.EventLogFloodProtectionThreshold + EventLogFloodProtectionTriggerPeriod = $testParams.EventLogFloodProtectionTriggerPeriod + EventLogFloodProtectionQuietPeriod = $testParams.EventLogFloodProtectionQuietPeriod + EventLogFloodProtectionNotifyInterval = $testParams.EventLogFloodProtectionNotifyInterval + ScriptErrorReportingEnabled = $testParams.ScriptErrorReportingEnabled + ScriptErrorReportingRequireAuth = $testParams.ScriptErrorReportingRequireAuth + ScriptErrorReportingDelay = $testParams.ScriptErrorReportingDelay + } } + + It "returns false from the test method" { + Test-TargetResource @testParams | Should Be $false + } + + It "repairs the diagnostic configuration" { + Mock Set-SPDiagnosticConfig {} + Set-TargetResource @testParams + Assert-MockCalled Set-SPDiagnosticConfig + } + } } } \ No newline at end of file From f3c8b4fb282a49ae21fced696cc301143701c1d5 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 00:48:04 +1000 Subject: [PATCH 06/31] Fixes to get method and test structure --- .../MSFT_xSPDistributedCacheService.psm1 | 40 ++++++++----------- .../xSharePoint.xSPCreateFarm.Tests.ps1 | 2 +- 2 files changed, 17 insertions(+), 25 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 index 43c1fd263..d3f57cd58 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 @@ -21,31 +21,24 @@ function Get-TargetResource Ensure = "Absent" InstallAccount = $params.InstallAccount } - try - { - Use-CacheCluster -ErrorAction SilentlyContinue - $cacheHost = Get-CacheHost -ErrorAction SilentlyContinue - - if ($null -eq $cacheHost) { return $nullReturnValue } - $computerName = ([System.Net.Dns]::GetHostByName($env:computerName)).HostName - $cacheHostConfig = Get-AFCacheHostConfiguration -ComputerName $computerName -CachePort $cacheHost.PortNo -ErrorAction SilentlyContinue - - if ($null -eq $cacheHostConfig) { return $nullReturnValue } - $windowsService = Get-WmiObject "win32_service" -Filter "Name='AppFabricCachingService'" - $firewallRule = Get-NetFirewallRule -DisplayName "SharePoint Distributed Cache" -ErrorAction SilentlyContinue + Use-CacheCluster -ErrorAction SilentlyContinue + $cacheHost = Get-CacheHost -ErrorAction SilentlyContinue + + if ($null -eq $cacheHost) { return $nullReturnValue } + $computerName = ([System.Net.Dns]::GetHostByName($env:computerName)).HostName + $cacheHostConfig = Get-AFCacheHostConfiguration -ComputerName $computerName -CachePort $cacheHost.PortNo -ErrorAction SilentlyContinue + + $windowsService = Get-WmiObject "win32_service" -Filter "Name='AppFabricCachingService'" + $firewallRule = Get-NetFirewallRule -DisplayName "SharePoint Distributed Cache" -ErrorAction SilentlyContinue - return @{ - Name = $params.Name - CacheSizeInMB = $cacheHostConfig.Size - ServiceAccount = $windowsService.StartName - CreateFirewallRules = ($firewallRule -ne $null) - Ensure = "Present" - InstallAccount = $params.InstallAccount - } - } - catch{ - return $nullReturnValue + return @{ + Name = $params.Name + CacheSizeInMB = $cacheHostConfig.Size + ServiceAccount = $windowsService.StartName + CreateFirewallRules = ($firewallRule -ne $null) + Ensure = "Present" + InstallAccount = $params.InstallAccount } } return $result @@ -142,7 +135,6 @@ function Test-TargetResource $CurrentValues = Get-TargetResource @PSBoundParameters Write-Verbose -Message "Testing for distributed cache configuration" - if ($null -eq $CurrentValues) { return $false } return Test-xSharePointSpecificParameters -CurrentValues $CurrentValues -DesiredValues $PSBoundParameters -ValuesToCheck @("Ensure", "CreateFirewallRules") } diff --git a/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 index 47f668ff6..a897949bc 100644 --- a/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPCreateFarm.Tests.ps1 @@ -108,7 +108,7 @@ Describe "xSPCreateFarm" { DefaultServiceAccount = @{ Name = "WRONG\account" } Name = $testParams.FarmConfigDatabaseName }} - Mock Get-SPWebApplication { return @(@{ + Mock Get-SPWebApplication { return @(@{ IsAdministrationWebApplication = $true ContentDatabases = @(@{ Name = $testParams.AdminContentDatabaseName }) Url = "http://$($env:ComputerName):$($testParams.CentralAdministrationPort)" From 0eb19e1149a37a3b5140d99e3c1f8f22d0ff698d Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 20:48:22 +1000 Subject: [PATCH 07/31] Fixing issue with removal of try..catch from get --- .../MSFT_xSPDistributedCacheService.psm1 | 40 +++++++++++-------- 1 file changed, 23 insertions(+), 17 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 index d3f57cd58..b0c092b0b 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 @@ -22,23 +22,29 @@ function Get-TargetResource InstallAccount = $params.InstallAccount } - Use-CacheCluster -ErrorAction SilentlyContinue - $cacheHost = Get-CacheHost -ErrorAction SilentlyContinue - - if ($null -eq $cacheHost) { return $nullReturnValue } - $computerName = ([System.Net.Dns]::GetHostByName($env:computerName)).HostName - $cacheHostConfig = Get-AFCacheHostConfiguration -ComputerName $computerName -CachePort $cacheHost.PortNo -ErrorAction SilentlyContinue - - $windowsService = Get-WmiObject "win32_service" -Filter "Name='AppFabricCachingService'" - $firewallRule = Get-NetFirewallRule -DisplayName "SharePoint Distributed Cache" -ErrorAction SilentlyContinue - - return @{ - Name = $params.Name - CacheSizeInMB = $cacheHostConfig.Size - ServiceAccount = $windowsService.StartName - CreateFirewallRules = ($firewallRule -ne $null) - Ensure = "Present" - InstallAccount = $params.InstallAccount + try + { + Use-CacheCluster -ErrorAction SilentlyContinue + $cacheHost = Get-CacheHost -ErrorAction SilentlyContinue + + if ($null -eq $cacheHost) { return $nullReturnValue } + $computerName = ([System.Net.Dns]::GetHostByName($env:computerName)).HostName + $cacheHostConfig = Get-AFCacheHostConfiguration -ComputerName $computerName -CachePort $cacheHost.PortNo -ErrorAction SilentlyContinue + + $windowsService = Get-WmiObject "win32_service" -Filter "Name='AppFabricCachingService'" + $firewallRule = Get-NetFirewallRule -DisplayName "SharePoint Distributed Cache" -ErrorAction SilentlyContinue + + return @{ + Name = $params.Name + CacheSizeInMB = $cacheHostConfig.Size + ServiceAccount = $windowsService.StartName + CreateFirewallRules = ($firewallRule -ne $null) + Ensure = "Present" + InstallAccount = $params.InstallAccount + } + } + catch { + return $nullReturnValue } } return $result From d617f2e69f44eff960f2f364db3c37b9c205f88c Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 20:57:01 +1000 Subject: [PATCH 08/31] Fixed get test to throw when its not configured --- .../xSharePoint.xSPDistributedCacheService.Tests.ps1 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Tests/xSharePoint/xSharePoint.xSPDistributedCacheService.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPDistributedCacheService.Tests.ps1 index 8926cd417..f53a68cd7 100644 --- a/Tests/xSharePoint/xSharePoint.xSPDistributedCacheService.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPDistributedCacheService.Tests.ps1 @@ -52,7 +52,7 @@ Describe "xSPDistributedCacheService" { } } Context "Distributed cache is not configured" { - Mock Get-CacheHost { return $null } + Mock Use-CacheCluster { throw [Exception] "ERRPS001 Error in reading provider and connection string values." } It "returns null from the get method" { (Get-TargetResource @testParams).Ensure | Should Be "Absent" From 3d2678b074e7eae8affb919873f7e57d792701e0 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 21:34:17 +1000 Subject: [PATCH 09/31] Refactore feature resource with code coverage increase --- .../MSFT_xSPFeature/MSFT_xSPFeature.psm1 | 18 +++--------------- .../xSharePoint.xSPFeature.Tests.ps1 | 14 +++++++------- 2 files changed, 10 insertions(+), 22 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPFeature/MSFT_xSPFeature.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPFeature/MSFT_xSPFeature.psm1 index ea16a0fb2..cb94bf93d 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPFeature/MSFT_xSPFeature.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPFeature/MSFT_xSPFeature.psm1 @@ -15,28 +15,16 @@ function Get-TargetResource $result = Invoke-xSharePointCommand -Credential $InstallAccount -Arguments $PSBoundParameters -ScriptBlock { $params = $args[0] - - - $feature = Get-SPFeature -Identity $params.Name -ErrorAction SilentlyContinue - - if ($null -eq $feature) { return @{ - Name = $params.Name - FeatureScope = $params.FeatureScope - Url = $params.Url - InstalAcount = $params.InstallAccount - Ensure = "Absent" - } } - $checkParams = @{} - $checkParams.Add("Identity", $params.Name) - if ($FeatureScope -eq "Farm") { + $checkParams = @{ Identity = $params.Name } + if ($params.FeatureScope -eq "Farm") { $checkParams.Add($params.FeatureScope, $true) } else { $checkParams.Add($params.FeatureScope, $params.Url) } $featureAtScope = Get-SPFeature @checkParams -ErrorAction SilentlyContinue $enabled = ($null -ne $featureAtScope) - if ($enabled) { $currentState = "Present" } else { $currentState = "Absent" } + if ($enabled -eq $true) { $currentState = "Present" } else { $currentState = "Absent" } return @{ Name = $params.Name diff --git a/Tests/xSharePoint/xSharePoint.xSPFeature.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPFeature.Tests.ps1 index 6c9ed42e0..f43987dcf 100644 --- a/Tests/xSharePoint/xSharePoint.xSPFeature.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPFeature.Tests.ps1 @@ -36,7 +36,7 @@ Describe "xSPFeature" { Mock Disable-SPFeature {} Context "A feature that is not installed in the farm should be turned on" { - Mock Get-SPFeature { return $null } -ParameterFilter { $Farm -ne $true } + Mock Get-SPFeature { return $null } It "returns null from the get method" { (Get-TargetResource @testParams).Ensure | Should Be "Absent" @@ -48,7 +48,7 @@ Describe "xSPFeature" { } Context "A farm scoped feature is not enabled and should be" { - Mock Get-SPFeature { return $null } -ParameterFilter { $Farm -eq $true } + Mock Get-SPFeature { return $null } $testParams.FeatureScope = "Farm" It "returns null from the get method" { @@ -67,7 +67,7 @@ Describe "xSPFeature" { } Context "A site collection scoped feature is not enabled and should be" { - Mock Get-SPFeature { return $null } -ParameterFilter { $Site -eq $true } + Mock Get-SPFeature { return $null } $testParams.FeatureScope = "Site" It "returns null from the get method" { @@ -87,7 +87,7 @@ Describe "xSPFeature" { Context "A farm scoped feature is enabled and should not be" { Mock Get-SPFeature { return @{} } - Mock Get-SPFeature { return @{} } -ParameterFilter { $Farm -eq $true } + $testParams.FeatureScope = "Farm" $testParams.Ensure = "Absent" @@ -108,7 +108,7 @@ Describe "xSPFeature" { Context "A site collection scoped feature is enabled and should not be" { Mock Get-SPFeature { return @{} } - Mock Get-SPFeature { return @{} } -ParameterFilter { $Site -eq $true } + $testParams.FeatureScope = "Site" It "returns null from the get method" { @@ -128,7 +128,7 @@ Describe "xSPFeature" { Context "A farm scoped feature is enabled and should be" { Mock Get-SPFeature { return @{} } - Mock Get-SPFeature { return @{} } -ParameterFilter { $Farm -eq $true } + $testParams.FeatureScope = "Farm" $testParams.Ensure = "Present" @@ -139,7 +139,7 @@ Describe "xSPFeature" { Context "A site collection scoped feature is enabled and should be" { Mock Get-SPFeature { return @{} } - Mock Get-SPFeature { return @{} } -ParameterFilter { $Site -eq $testParams.Url } + $testParams.FeatureScope = "Site" It "returns true from the test method" { From 58af96cf6890a6a460bbbfbb977181eb7e680c8d Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 22:38:12 +1000 Subject: [PATCH 10/31] Refactor and expand test coverage of InstallPrereqs resource --- .../MSFT_xSPInstallPrereqs.psm1 | 18 ++----- .../xSharePoint.xSPInstallPrereqs.Tests.ps1 | 51 ++++++++++++++++--- 2 files changed, 48 insertions(+), 21 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPInstallPrereqs/MSFT_xSPInstallPrereqs.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPInstallPrereqs/MSFT_xSPInstallPrereqs.psm1 index 58c81bda8..41f852290 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPInstallPrereqs/MSFT_xSPInstallPrereqs.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPInstallPrereqs/MSFT_xSPInstallPrereqs.psm1 @@ -35,10 +35,10 @@ function Get-TargetResource Write-Verbose -Message "Getting installed windows features" if ($majorVersion -eq 15) { - $WindowsFeatures = Invoke-Command -ScriptBlock { Get-WindowsFeature -Name Net-Framework-Features,Web-Server,Web-WebServer,Web-Common-Http,Web-Static-Content,Web-Default-Doc,Web-Dir-Browsing,Web-Http-Errors,Web-App-Dev,Web-Asp-Net,Web-Net-Ext,Web-ISAPI-Ext,Web-ISAPI-Filter,Web-Health,Web-Http-Logging,Web-Log-Libraries,Web-Request-Monitor,Web-Http-Tracing,Web-Security,Web-Basic-Auth,Web-Windows-Auth,Web-Filtering,Web-Digest-Auth,Web-Performance,Web-Stat-Compression,Web-Dyn-Compression,Web-Mgmt-Tools,Web-Mgmt-Console,Web-Mgmt-Compat,Web-Metabase,Application-Server,AS-Web-Support,AS-TCP-Port-Sharing,AS-WAS-Support, AS-HTTP-Activation,AS-TCP-Activation,AS-Named-Pipes,AS-Net-Framework,WAS,WAS-Process-Model,WAS-NET-Environment,WAS-Config-APIs,Web-Lgcy-Scripting,Windows-Identity-Foundation,Server-Media-Foundation,Xps-Viewer } -NoNewScope + $WindowsFeatures = Get-WindowsFeature -Name Net-Framework-Features,Web-Server,Web-WebServer,Web-Common-Http,Web-Static-Content,Web-Default-Doc,Web-Dir-Browsing,Web-Http-Errors,Web-App-Dev,Web-Asp-Net,Web-Net-Ext,Web-ISAPI-Ext,Web-ISAPI-Filter,Web-Health,Web-Http-Logging,Web-Log-Libraries,Web-Request-Monitor,Web-Http-Tracing,Web-Security,Web-Basic-Auth,Web-Windows-Auth,Web-Filtering,Web-Digest-Auth,Web-Performance,Web-Stat-Compression,Web-Dyn-Compression,Web-Mgmt-Tools,Web-Mgmt-Console,Web-Mgmt-Compat,Web-Metabase,Application-Server,AS-Web-Support,AS-TCP-Port-Sharing,AS-WAS-Support, AS-HTTP-Activation,AS-TCP-Activation,AS-Named-Pipes,AS-Net-Framework,WAS,WAS-Process-Model,WAS-NET-Environment,WAS-Config-APIs,Web-Lgcy-Scripting,Windows-Identity-Foundation,Server-Media-Foundation,Xps-Viewer } if ($majorVersion -eq 16) { - $WindowsFeatures = Invoke-Command -ScriptBlock { Get-WindowsFeature -Name Application-Server,AS-NET-Framework,AS-Web-Support,Web-Server,Web-WebServer,Web-Common-Http,Web-Default-Doc,Web-Dir-Browsing,Web-Http-Errors,Web-Static-Content,Web-Http-Redirect,Web-Health,Web-Http-Logging,Web-Log-Libraries,Web-Request-Monitor,Web-Performance,Web-Stat-Compression,Web-Dyn-Compression,Web-Security,Web-Filtering,Web-Basic-Auth,Web-Client-Auth,Web-Digest-Auth,Web-Cert-Auth,Web-IP-Security,Web-Url-Auth,Web-Windows-Auth,Web-App-Dev,Web-Net-Ext,Web-Net-Ext45,Web-Asp-Net45,Web-ISAPI-Ext,Web-ISAPI-Filter,Web-Mgmt-Tools,Web-Mgmt-Console,Web-Mgmt-Compat,Web-Metabase,Web-Lgcy-Mgmt-Console,Web-Lgcy-Scripting,Web-WMI,Web-Scripting-Tools,NET-Framework-Features,NET-Framework-Core,NET-HTTP-Activation,NET-Non-HTTP-Activ,NET-Framework-45-ASPNET,NET-WCF-HTTP-Activation45,Windows-Identity-Foundation,PowerShell-V2,WAS,WAS-Process-Model,WAS-NET-Environment,WAS-Config-APIs } -NoNewScope + $WindowsFeatures = Get-WindowsFeature -Name Application-Server,AS-NET-Framework,AS-Web-Support,Web-Server,Web-WebServer,Web-Common-Http,Web-Default-Doc,Web-Dir-Browsing,Web-Http-Errors,Web-Static-Content,Web-Http-Redirect,Web-Health,Web-Http-Logging,Web-Log-Libraries,Web-Request-Monitor,Web-Performance,Web-Stat-Compression,Web-Dyn-Compression,Web-Security,Web-Filtering,Web-Basic-Auth,Web-Client-Auth,Web-Digest-Auth,Web-Cert-Auth,Web-IP-Security,Web-Url-Auth,Web-Windows-Auth,Web-App-Dev,Web-Net-Ext,Web-Net-Ext45,Web-Asp-Net45,Web-ISAPI-Ext,Web-ISAPI-Filter,Web-Mgmt-Tools,Web-Mgmt-Console,Web-Mgmt-Compat,Web-Metabase,Web-Lgcy-Mgmt-Console,Web-Lgcy-Scripting,Web-WMI,Web-Scripting-Tools,NET-Framework-Features,NET-Framework-Core,NET-HTTP-Activation,NET-Non-HTTP-Activ,NET-Framework-45-ASPNET,NET-WCF-HTTP-Activation45,Windows-Identity-Foundation,PowerShell-V2,WAS,WAS-Process-Model,WAS-NET-Environment,WAS-Config-APIs } foreach ($feature in $WindowsFeatures) { @@ -49,7 +49,7 @@ function Get-TargetResource $installedItems = Get-CimInstance -ClassName Win32_Product #Common prereqs - $returnValue.Add("Microsoft Identity Extensions", (Check-xSharePointInstalledProductRegistryKey -RegKeysCollection (Get-ChildItem HKLM:\Software\Microsoft\Windows\CurrentVersion\Uninstall\ -Recurse) -ProductName "Microsoft Identity Extensions").Count -gt 0) + $returnValue.Add("Microsoft Identity Extensions", (@(Get-ChildItem HKLM:\Software\Microsoft\Windows\CurrentVersion\Uninstall\ -Recurse | ? {$_.GetValue("DisplayName") -eq "Microsoft Identity Extensions" }).Count -gt 0)) $returnValue.Add("Microsoft CCR and DSS Runtime 2008 R3", (($installedItems | ? {$_.Name -eq "Microsoft CCR and DSS Runtime 2008 R3"}) -ne $null)) $returnValue.Add("Microsoft Sync Framework Runtime v1.0 SP1 (x64)", (($installedItems | ? {$_.Name -eq "Microsoft Sync Framework Runtime v1.0 SP1 (x64)"}) -ne $null)) $returnValue.Add("AppFabric 1.1 for Windows Server", (($installedItems | ? {$_.Name -eq "AppFabric 1.1 for Windows Server"}) -ne $null)) @@ -81,18 +81,6 @@ function Get-TargetResource return $results } -function Check-xSharePointInstalledProductRegistryKey() { - [CmdletBinding()] - param - ( - [parameter(Mandatory = $false)] [object] $RegKeysCollection, - [parameter(Mandatory = $true)] [string] $ProductName - ) - if ($RegKeysCollection -eq $null) { return $null } - return @($RegKeysCollection | ? {$_.GetValue("DisplayName") -eq $ProductName }) -} - - function Set-TargetResource { [CmdletBinding()] diff --git a/Tests/xSharePoint/xSharePoint.xSPInstallPrereqs.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPInstallPrereqs.Tests.ps1 index f77d29e51..32039d4cf 100644 --- a/Tests/xSharePoint/xSharePoint.xSPInstallPrereqs.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPInstallPrereqs.Tests.ps1 @@ -24,18 +24,22 @@ Describe "xSPInstallPrereqs" { Mock Invoke-xSharePointCommand { return Invoke-Command -ScriptBlock $ScriptBlock -ArgumentList $Arguments -NoNewScope } + + if ($null -eq (Get-Command Get-WindowsFeature -ErrorAction SilentlyContinue)) { + function Get-WindowsFeature() { } + } Import-Module $Global:CurrentSharePointStubModule -WarningAction SilentlyContinue $versionBeingTested = (Get-Item $Global:CurrentSharePointStubModule).Directory.BaseName $majorBuildNumber = $versionBeingTested.Substring(0, $versionBeingTested.IndexOf(".")) Mock Get-xSharePointAssemblyVersion { return $majorBuildNumber } - Mock Check-xSharePointInstalledProductRegistryKey { return $null } + Mock Get-ChildItem { return $null } - Context "Prerequisites are not installed but should be" { - Mock Invoke-Command { @( @{ Name = "ExampleFeature"; Installed = $false}) } -ParameterFilter { $ScriptBlock.ToString().Contains("Get-WindowsFeature") -eq $true } + Context "Prerequisites are not installed but should be and are to be installed in online mode" { + Mock Get-WindowsFeature { @( @{ Name = "ExampleFeature"; Installed = $false}) } Mock Get-CimInstance { return @() } - Mock Get-ChildItem { return $null } + Mock Get-ChildItem { return @() } It "returns absent from the get method" { (Get-TargetResource @testParams).Ensure | Should Be "Absent" @@ -86,7 +90,7 @@ Describe "xSPInstallPrereqs" { } Context "Prerequisites are installed and should be" { - Mock Invoke-Command { return @( @{ Name = "ExampleFeature"; Installed = $true }) } -ParameterFilter { $ScriptBlock.ToString().Contains("Get-WindowsFeature") -eq $true } + Mock Get-WindowsFeature { @( @{ Name = "ExampleFeature"; Installed = $true }) } if ($majorBuildNumber -eq 15) { Mock Get-CimInstance { return @( @{ Name = "Microsoft CCR and DSS Runtime 2008 R3"} @@ -112,7 +116,10 @@ Describe "xSPInstallPrereqs" { )} } Mock Get-ChildItem { return $null } - Mock Check-xSharePointInstalledProductRegistryKey { return @( @{Example = $true } ) } + Mock Get-ChildItem { return @( + (New-Object Object | + Add-Member ScriptMethod GetValue { return "Microsoft Identity Extensions" } -PassThru) + ) } It "returns present from the get method" { (Get-TargetResource @testParams).Ensure | Should Be "Present" @@ -126,9 +133,41 @@ Describe "xSPInstallPrereqs" { Context "Prerequisites are installed but should not be" { $testParams.Ensure = "Absent" + It "throws an exception from the set method" { + {Test-TargetResource @testParams} | Should Throw + } + It "throws an exception from the set method" { {Set-TargetResource @testParams} | Should Throw } } + + Context "Prerequisites are not installed but should be and are to be installed in offline mode" { + $testParams.OnlineMode = $false + $testParams.Ensure = "Present" + Mock Get-WindowsFeature { @( @{ Name = "ExampleFeature"; Installed = $false}) } + Mock Get-CimInstance { return @() } + Mock Get-ChildItem { return @() } + + It "throws an exception in the set method if required parameters are not set" { + {Set-TargetResource @testParams} | Should Throw + } + + if ($majorBuildNumber -eq 15) { + $requiredParams = @("SQLNCli","PowerShell","NETFX","IDFX","Sync","AppFabric","IDFX11","MSIPCClient","WCFDataServices","KB2671763","WCFDataServices56") + } + if ($majorBuildNumber -eq 16) { + $requiredParams = @("SQLNCli","Sync","AppFabric","IDFX11","MSIPCClient","WCFDataServices","KB2671763","WCFDataServices56","KB2898850","MSVCRT12") + } + $requiredParams | ForEach-Object { + $testParams.Add($_, "C:\fake\value.exe") + } + + It "does not throw an exception where the required parameters are included" { + Mock Start-Process { return @{ ExitCode = 0 } } + + {Set-TargetResource @testParams} | Should Not Throw + } + } } } \ No newline at end of file From 86bbc30defb8b2075f5efd6fc8a59ceab297696d Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 23:06:26 +1000 Subject: [PATCH 11/31] Formatting fix --- Tests/xSharePoint/xSharePoint.xSPInstallPrereqs.Tests.ps1 | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Tests/xSharePoint/xSharePoint.xSPInstallPrereqs.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPInstallPrereqs.Tests.ps1 index 32039d4cf..e66f9f35c 100644 --- a/Tests/xSharePoint/xSharePoint.xSPInstallPrereqs.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPInstallPrereqs.Tests.ps1 @@ -133,7 +133,7 @@ Describe "xSPInstallPrereqs" { Context "Prerequisites are installed but should not be" { $testParams.Ensure = "Absent" - It "throws an exception from the set method" { + It "throws an exception from the set method" { {Test-TargetResource @testParams} | Should Throw } @@ -144,7 +144,7 @@ Describe "xSPInstallPrereqs" { Context "Prerequisites are not installed but should be and are to be installed in offline mode" { $testParams.OnlineMode = $false - $testParams.Ensure = "Present" + $testParams.Ensure = "Present" Mock Get-WindowsFeature { @( @{ Name = "ExampleFeature"; Installed = $false}) } Mock Get-CimInstance { return @() } Mock Get-ChildItem { return @() } From e9f2444ca2bf1261227c8c27c9db84722ec2e241 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 23:33:42 +1000 Subject: [PATCH 12/31] Temporary local admin applied to DCache resource --- .../MSFT_xSPDistributedCacheService.psm1 | 15 +++++- .../xSharePoint.UserProfileService.psm1 | 50 ------------------- .../xSharePoint.Util/xSharePoint.Util.psm1 | 49 ++++++++++++++++++ Modules/xSharePoint/xSharePoint.psd1 | 1 - Modules/xSharePoint/xSharePoint.pssproj | 2 - ...Point.xSPDistributedCacheService.Tests.ps1 | 3 ++ 6 files changed, 66 insertions(+), 54 deletions(-) delete mode 100644 Modules/xSharePoint/Modules/xSharePoint.UserProfileService/xSharePoint.UserProfileService.psm1 diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 index b0c092b0b..f8a2dd321 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPDistributedCacheService/MSFT_xSPDistributedCacheService.psm1 @@ -13,7 +13,7 @@ function Get-TargetResource ) Write-Verbose -Message "Getting the cache host information" - + $result = Invoke-xSharePointCommand -Credential $InstallAccount -Arguments $PSBoundParameters -ScriptBlock { $params = $args[0] $nullReturnValue = @{ @@ -66,6 +66,13 @@ function Set-TargetResource $CurrentState = Get-TargetResource @PSBoundParameters + $isLocalAdmin = Test-xSharePointUserIsLocalAdmin -UserName $ServiceAccount + + if (!$isLocalAdmin) + { + Add-xSharePointUserToLocalAdmin -UserName $ServiceAccount + } + if ($Ensure -eq "Present") { Write-Verbose -Message "Adding the distributed cache to the server" if($createFirewallRules -eq $true) { @@ -123,6 +130,12 @@ function Set-TargetResource } Write-Verbose -Message "Distributed cache removed." } + + # Remove the FarmAccount from the local Administrators group, if it was added above + if (!$isLocalAdmin) + { + Remove-xSharePointUserToLocalAdmin -UserName $ServiceAccount + } } function Test-TargetResource diff --git a/Modules/xSharePoint/Modules/xSharePoint.UserProfileService/xSharePoint.UserProfileService.psm1 b/Modules/xSharePoint/Modules/xSharePoint.UserProfileService/xSharePoint.UserProfileService.psm1 deleted file mode 100644 index 2b029a1fb..000000000 --- a/Modules/xSharePoint/Modules/xSharePoint.UserProfileService/xSharePoint.UserProfileService.psm1 +++ /dev/null @@ -1,50 +0,0 @@ -function Test-xSharePointUserIsLocalAdmin() { - [CmdletBinding()] - param - ( - [parameter(Mandatory = $true,Position=1)] - [string] - $UserName - ) - - $domainName = $UserName.Split('\')[0] - $accountName = $UserName.Split('\')[1] - - return ([ADSI]"WinNT://$($env:computername)/Administrators,group").PSBase.Invoke("Members") | - ForEach-Object {$_.GetType().InvokeMember("Name", 'GetProperty', $null, $_, $null)} | - Where-Object { $_ -eq $accountName } -} - -function Add-xSharePointUserToLocalAdmin() { - [CmdletBinding()] - param - ( - [parameter(Mandatory = $true,Position=1)] - [string] - $UserName - ) - - $domainName = $UserName.Split('\')[0] - $accountName = $UserName.Split('\')[1] - - Write-Verbose -Message "Adding $domainName\$userName to local admin group" - ([ADSI]"WinNT://$($env:computername)/Administrators,group").Add("WinNT://$domainName/$accountName") | Out-Null -} - -function Remove-xSharePointUserToLocalAdmin() { - [CmdletBinding()] - param - ( - [parameter(Mandatory = $true,Position=1)] - [string] - $UserName - ) - - $domainName = $UserName.Split('\')[0] - $accountName = $UserName.Split('\')[1] - - Write-Verbose -Message "Removing $domainName\$userName from local admin group" - ([ADSI]"WinNT://$($env:computername)/Administrators,group").Remove("WinNT://$domainName/$accountName") | Out-Null -} - -Export-ModuleMember -Function * diff --git a/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 b/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 index 6f6ec46db..592288615 100644 --- a/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 +++ b/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 @@ -160,4 +160,53 @@ function Test-xSharePointSpecificParameters() { return $returnValue } +function Test-xSharePointUserIsLocalAdmin() { + [CmdletBinding()] + param + ( + [parameter(Mandatory = $true,Position=1)] + [string] + $UserName + ) + + $domainName = $UserName.Split('\')[0] + $accountName = $UserName.Split('\')[1] + + return ([ADSI]"WinNT://$($env:computername)/Administrators,group").PSBase.Invoke("Members") | + ForEach-Object {$_.GetType().InvokeMember("Name", 'GetProperty', $null, $_, $null)} | + Where-Object { $_ -eq $accountName } +} + +function Add-xSharePointUserToLocalAdmin() { + [CmdletBinding()] + param + ( + [parameter(Mandatory = $true,Position=1)] + [string] + $UserName + ) + + $domainName = $UserName.Split('\')[0] + $accountName = $UserName.Split('\')[1] + + Write-Verbose -Message "Adding $domainName\$userName to local admin group" + ([ADSI]"WinNT://$($env:computername)/Administrators,group").Add("WinNT://$domainName/$accountName") | Out-Null +} + +function Remove-xSharePointUserToLocalAdmin() { + [CmdletBinding()] + param + ( + [parameter(Mandatory = $true,Position=1)] + [string] + $UserName + ) + + $domainName = $UserName.Split('\')[0] + $accountName = $UserName.Split('\')[1] + + Write-Verbose -Message "Removing $domainName\$userName from local admin group" + ([ADSI]"WinNT://$($env:computername)/Administrators,group").Remove("WinNT://$domainName/$accountName") | Out-Null +} + Export-ModuleMember -Function * diff --git a/Modules/xSharePoint/xSharePoint.psd1 b/Modules/xSharePoint/xSharePoint.psd1 index 52963a2ea..dc07ab2d1 100644 --- a/Modules/xSharePoint/xSharePoint.psd1 +++ b/Modules/xSharePoint/xSharePoint.psd1 @@ -64,7 +64,6 @@ Description = 'This DSC module is used to deploy and configure SharePoint Server # Modules to import as nested modules of the module specified in RootModule/ModuleToProcess NestedModules = @("modules\xSharePoint.CacheAccounts\xSharePoint.CacheAccounts.psm1", - "modules\xSharePoint.UserProfileService\xSharePoint.UserProfileService.psm1", "modules\xSharePoint.Util\xSharePoint.Util.psm1") # Functions to export from this module diff --git a/Modules/xSharePoint/xSharePoint.pssproj b/Modules/xSharePoint/xSharePoint.pssproj index 26dca94f6..fc4bcb504 100644 --- a/Modules/xSharePoint/xSharePoint.pssproj +++ b/Modules/xSharePoint/xSharePoint.pssproj @@ -75,7 +75,6 @@ - @@ -126,7 +125,6 @@ - diff --git a/Tests/xSharePoint/xSharePoint.xSPDistributedCacheService.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPDistributedCacheService.Tests.ps1 index f53a68cd7..5b39ed05f 100644 --- a/Tests/xSharePoint/xSharePoint.xSPDistributedCacheService.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPDistributedCacheService.Tests.ps1 @@ -40,6 +40,9 @@ Describe "xSPDistributedCacheService" { Mock Add-SPDistributedCacheServiceInstance { } Mock Update-SPDistributedCacheSize { } Mock Get-SPManagedAccount { return @{} } + Mock Add-xSharePointUserToLocalAdmin { } + Mock Test-xSharePointUserIsLocalAdmin { return $false } + Mock Remove-xSharePointUserToLocalAdmin { } Mock Get-SPFarm { return @{ Services = @(@{ Name = "AppFabricCachingService" From 6227a69a9b3e3d5410d0ccfa53aaefac9cd6eb2e Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Mon, 28 Sep 2015 23:50:58 +1000 Subject: [PATCH 13/31] Refactor and test coverage improvement --- .../DSCResources/MSFT_xSPJoinFarm/MSFT_xSPJoinFarm.psm1 | 2 +- Tests/xSharePoint/xSharePoint.xSPJoinFarm.Tests.ps1 | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPJoinFarm/MSFT_xSPJoinFarm.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPJoinFarm/MSFT_xSPJoinFarm.psm1 index 53418eb70..15007c946 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPJoinFarm/MSFT_xSPJoinFarm.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPJoinFarm/MSFT_xSPJoinFarm.psm1 @@ -86,7 +86,7 @@ function Set-TargetResource Start-Service -Name sptimerv4 Write-Verbose -Message "Pausing for 5 minutes to allow the timer service to fully provision the server" - Invoke-Command -ScriptBlock { Start-Sleep -Seconds 300 } -NoNewScope + Start-Sleep -Seconds 300 Write-Verbose -Message "Join farm complete. Restarting computer to allow configuration to continue" $global:DSCMachineStatus = 1 diff --git a/Tests/xSharePoint/xSharePoint.xSPJoinFarm.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPJoinFarm.Tests.ps1 index c2ca83c4d..91d3d969e 100644 --- a/Tests/xSharePoint/xSharePoint.xSPJoinFarm.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPJoinFarm.Tests.ps1 @@ -34,7 +34,7 @@ Describe "xSPJoinFarm" { Mock New-SPCentralAdministration {} Mock Install-SPApplicationContent {} Mock Start-Service {} - Mock Invoke-Command {} -ParameterFilter { $ScriptBlock.ToString().Contains("Start-Sleep") -eq $true } + Mock Start-Sleep {} $versionBeingTested = (Get-Item $Global:CurrentSharePointStubModule).Directory.BaseName $majorBuildNumber = $versionBeingTested.Substring(0, $versionBeingTested.IndexOf(".")) @@ -43,7 +43,7 @@ Describe "xSPJoinFarm" { Context "no farm is configured locally and a supported version of SharePoint is installed" { - Mock Get-SPFarm { return $null } + Mock Get-SPFarm { throw "Unable to detect local farm" } It "the get method returns null when the farm is not configured" { Get-TargetResource @testParams | Should BeNullOrEmpty From aa020a0d0eb5923e32a486e09623745e10e91a59 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 00:08:52 +1000 Subject: [PATCH 14/31] Removed redundant catch block --- .../MSFT_xSPManagedAccount.psm1 | 23 ++++++++----------- 1 file changed, 9 insertions(+), 14 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPManagedAccount/MSFT_xSPManagedAccount.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPManagedAccount/MSFT_xSPManagedAccount.psm1 index 6b85880f4..c461730cb 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPManagedAccount/MSFT_xSPManagedAccount.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPManagedAccount/MSFT_xSPManagedAccount.psm1 @@ -17,20 +17,15 @@ function Get-TargetResource $result = Invoke-xSharePointCommand -Credential $InstallAccount -Arguments $PSBoundParameters -ScriptBlock { $params = $args[0] - - try { - $ma = Get-SPManagedAccount -Identity $params.Account.UserName -ErrorAction SilentlyContinue - if ($null -eq $ma) { return $null } - return @{ - AccountName = $ma.Username - EmailNotification = $ma.DaysBeforeChangeToEmail - PreExpireDays = $ma.DaysBeforeExpiryToChange - Schedule = $ma.ChangeSchedule - Account = $params.Account - InstallAccount = $params.InstallAccount - } - } catch { - return $null + $ma = Get-SPManagedAccount -Identity $params.Account.UserName -ErrorAction SilentlyContinue + if ($null -eq $ma) { return $null } + return @{ + AccountName = $ma.Username + EmailNotification = $ma.DaysBeforeChangeToEmail + PreExpireDays = $ma.DaysBeforeExpiryToChange + Schedule = $ma.ChangeSchedule + Account = $params.Account + InstallAccount = $params.InstallAccount } } return $result From 5ce8b872ba323fbc2ca7886191db1e48e609d16b Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 00:21:19 +1000 Subject: [PATCH 15/31] Refactor and increase test coverage --- .../MSFT_xSPManagedMetaDataServiceApp.psm1 | 40 ++++++++----------- ...int.xSPManagedMetadataServiceApp.Tests.ps1 | 25 +++++++++++- 2 files changed, 40 insertions(+), 25 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPManagedMetadataServiceApp/MSFT_xSPManagedMetaDataServiceApp.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPManagedMetadataServiceApp/MSFT_xSPManagedMetaDataServiceApp.psm1 index 32e85b85c..6aecc1c07 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPManagedMetadataServiceApp/MSFT_xSPManagedMetaDataServiceApp.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPManagedMetadataServiceApp/MSFT_xSPManagedMetaDataServiceApp.psm1 @@ -16,33 +16,25 @@ function Get-TargetResource $result = Invoke-xSharePointCommand -Credential $InstallAccount -Arguments $PSBoundParameters -ScriptBlock { $params = $args[0] + $serviceApps = Get-SPServiceApplication -Name $params.Name -ErrorAction SilentlyContinue + if ($null -eq $serviceApps) { + return $null + } + $serviceApp = $serviceApps | Where-Object { $_.TypeName -eq "Managed Metadata Service" } - try + If ($null -eq $serviceApp) { - $serviceApps = Get-SPServiceApplication -Name $params.Name -ErrorAction SilentlyContinue - if ($null -eq $serviceApps) { - return $null - } - $serviceApp = $serviceApps | Where-Object { $_.TypeName -eq "Managed Metadata Service" } - - If ($null -eq $serviceApp) - { - return $null - } - else - { - return @{ - Name = $serviceApp.DisplayName - ApplicationPool = $serviceApp.ApplicationPool.Name - DatabaseName = $serviceApp.Database.Name - DatabaseServer = $serviceApp.Database.Server.Name - InstallAccount = $params.InstallAccount - } - } - } - catch + return $null + } + else { - return $null + return @{ + Name = $serviceApp.DisplayName + ApplicationPool = $serviceApp.ApplicationPool.Name + DatabaseName = $serviceApp.Database.Name + DatabaseServer = $serviceApp.Database.Server.Name + InstallAccount = $params.InstallAccount + } } } return $result diff --git a/Tests/xSharePoint/xSharePoint.xSPManagedMetadataServiceApp.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPManagedMetadataServiceApp.Tests.ps1 index 26d36946c..c9a035099 100644 --- a/Tests/xSharePoint/xSharePoint.xSPManagedMetadataServiceApp.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPManagedMetadataServiceApp.Tests.ps1 @@ -28,7 +28,7 @@ Describe "xSPManagedMetaDataServiceApp" { Import-Module $Global:CurrentSharePointStubModule -WarningAction SilentlyContinue - Context "When no service application exists in the current farm" { + Context "When no service applications exist in the current farm" { Mock Get-SPServiceApplication { return $null } Mock New-SPMetadataServiceApplication { return @{} } @@ -47,6 +47,29 @@ Describe "xSPManagedMetaDataServiceApp" { Set-TargetResource @testParams Assert-MockCalled New-SPMetadataServiceApplication } + + $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) + It "creates a new service application in the set method where InstallAccount is used" { + Set-TargetResource @testParams + Assert-MockCalled New-SPMetadataServiceApplication + } + $testParams.Remove("InstallAccount") + } + + Context "When service applications exist in the current farm but the specific MMS app does not" { + + Mock Get-SPServiceApplication { return @(@{ + TypeName = "Some other service app type" + }) } + + It "returns null from the Get method" { + Get-TargetResource @testParams | Should BeNullOrEmpty + Assert-MockCalled Get-SPServiceApplication -ParameterFilter { $Name -eq $testParams.Name } + } + + It "returns false when the Test method is called" { + Test-TargetResource @testParams | Should Be $false + } } Context "When a service application exists and is configured correctly" { From 28e80e05bb0074db92a45ff6046bf375beff33a5 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 00:26:32 +1000 Subject: [PATCH 16/31] Expanded test coverage --- Tests/xSharePoint/xSharePoint.xSPManagedPath.Tests.ps1 | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/Tests/xSharePoint/xSharePoint.xSPManagedPath.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPManagedPath.Tests.ps1 index f35840ab8..9be3120e4 100644 --- a/Tests/xSharePoint/xSharePoint.xSPManagedPath.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPManagedPath.Tests.ps1 @@ -53,6 +53,14 @@ Describe "xSPManagedPath" { Assert-MockCalled New-SPManagedPath } $testParams.HostHeader = $false + + $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) + It "creates a host header path in the set method where InstallAccount is used" { + Set-TargetResource @testParams + + Assert-MockCalled New-SPManagedPath + } + $testParams.Remove("InstallAccount") } Context "The path exists but is of the wrong type" { From 7dab31472081951a9aaea592d99ccc5bb4f8fe2c Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 00:31:31 +1000 Subject: [PATCH 17/31] Expanded test coverage --- .../xSharePoint.xSPSearchServiceApp.Tests.ps1 | 35 ++++++++++++++++++- 1 file changed, 34 insertions(+), 1 deletion(-) diff --git a/Tests/xSharePoint/xSharePoint.xSPSearchServiceApp.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPSearchServiceApp.Tests.ps1 index a59826a9b..6137db92f 100644 --- a/Tests/xSharePoint/xSharePoint.xSPSearchServiceApp.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPSearchServiceApp.Tests.ps1 @@ -26,7 +26,7 @@ Describe "xSPSearchServiceApp" { Import-Module $Global:CurrentSharePointStubModule -WarningAction SilentlyContinue - Context "When no service application exists in the current farm" { + Context "When no service applications exist in the current farm" { Mock Get-SPServiceApplication { return $null } Mock Get-SPEnterpriseSearchServiceInstance { return @{} } @@ -49,6 +49,39 @@ Describe "xSPSearchServiceApp" { Set-TargetResource @testParams Assert-MockCalled New-SPEnterpriseSearchServiceApplication } + + $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) + It "creates a new service application in the set method where InstallAccount is used" { + Set-TargetResource @testParams + Assert-MockCalled New-SPEnterpriseSearchServiceApplication + } + $testParams.Remove("InstallAccount") + } + + Context "When service applications exist in the current farm but the specific search app does not" { + Mock Get-SPEnterpriseSearchServiceInstance { return @{} } + Mock New-SPBusinessDataCatalogServiceApplication { } + Mock Start-SPEnterpriseSearchServiceInstance { } + Mock New-SPEnterpriseSearchServiceApplication { return @{} } + Mock New-SPEnterpriseSearchServiceApplicationProxy { } + Mock Set-SPEnterpriseSearchServiceApplication { } + Mock Get-SPServiceApplication { return @(@{ + TypeName = "Some other service app type" + }) } + + It "returns null from the Get method" { + Get-TargetResource @testParams | Should BeNullOrEmpty + Assert-MockCalled Get-SPServiceApplication -ParameterFilter { $Name -eq $testParams.Name } + } + + It "returns false when the Test method is called" { + Test-TargetResource @testParams | Should Be $false + } + + It "creates a new service application in the set method" { + Set-TargetResource @testParams + Assert-MockCalled New-SPEnterpriseSearchServiceApplication + } } Context "When a service application exists and is configured correctly" { From 16a0c49fa9b6b75bc520bd47adb171dbc5b14bed Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 07:44:30 +1000 Subject: [PATCH 18/31] Test coverage improvements --- ...rePoint.xSPSecureStoreServiceApp.Tests.ps1 | 50 +++++++++++++++++++ 1 file changed, 50 insertions(+) diff --git a/Tests/xSharePoint/xSharePoint.xSPSecureStoreServiceApp.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPSecureStoreServiceApp.Tests.ps1 index 4172b56a4..0b4cdc8c7 100644 --- a/Tests/xSharePoint/xSharePoint.xSPSecureStoreServiceApp.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPSecureStoreServiceApp.Tests.ps1 @@ -50,6 +50,35 @@ Describe "xSPSecureStoreServiceApp" { Set-TargetResource @testParams Assert-MockCalled New-SPSecureStoreServiceApplication } + + $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) + It "creates a new service application in the set method where InstallAccount is used" { + Set-TargetResource @testParams + Assert-MockCalled New-SPSecureStoreServiceApplication + } + $testParams.Remove("InstallAccount") + + $testParams.Add("DatabaseName", "SP_SecureStore") + It "creates a new service application in the set method where parameters beyond the minimum required set" { + Set-TargetResource @testParams + Assert-MockCalled New-SPSecureStoreServiceApplication + } + $testParams.Remove("DatabaseName") + } + + Context "When service applications exist in the current farm but the specific search app does not" { + Mock Get-SPServiceApplication { return @(@{ + TypeName = "Some other service app type" + }) } + + It "returns null from the Get method" { + Get-TargetResource @testParams | Should BeNullOrEmpty + Assert-MockCalled Get-SPServiceApplication -ParameterFilter { $Name -eq $testParams.Name } + } + + It "returns false when the Test method is called" { + Test-TargetResource @testParams | Should Be $false + } } Context "When a service application exists and is configured correctly" { @@ -100,6 +129,27 @@ Describe "xSPSecureStoreServiceApp" { Assert-MockCalled Get-SPServiceApplicationPool Assert-MockCalled Set-SPSecureStoreServiceApplication } + } + + Context "When an unsupported version of SharePoint is installed" { + Mock Get-xSharePointInstalledProductVersion { return @{ FileMajorPart = 14 } } + Mock Get-SPServiceApplication { + return @(@{ + TypeName = "Secure Store Service Application" + DisplayName = $testParams.Name + ApplicationPool = @{ Name = "Wrong App Pool Name" } + Database = @{ + Name = $testParams.DatabaseName + Server = @{ Name = $testParams.DatabaseServer } + } + }) + } + Mock Get-SPServiceApplicationPool { return @{ Name = $testParams.ApplicationPool } } + Mock Set-SPSecureStoreServiceApplication { } + + It "the set method throws an exception" { + { Set-TargetResource @testParams } | Should Throw + } } } } \ No newline at end of file From f8da3047e43b50367d40e79ba850988988be1471 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 11:06:09 +1000 Subject: [PATCH 19/31] --- .../xSharePoint.xSPSecureStoreServiceApp.Tests.ps1 | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Tests/xSharePoint/xSharePoint.xSPSecureStoreServiceApp.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPSecureStoreServiceApp.Tests.ps1 index 0b4cdc8c7..4dd73048c 100644 --- a/Tests/xSharePoint/xSharePoint.xSPSecureStoreServiceApp.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPSecureStoreServiceApp.Tests.ps1 @@ -58,7 +58,7 @@ Describe "xSPSecureStoreServiceApp" { } $testParams.Remove("InstallAccount") - $testParams.Add("DatabaseName", "SP_SecureStore") + $testParams.Add("DatabaseName", "SP_SecureStore") It "creates a new service application in the set method where parameters beyond the minimum required set" { Set-TargetResource @testParams Assert-MockCalled New-SPSecureStoreServiceApplication @@ -131,8 +131,8 @@ Describe "xSPSecureStoreServiceApp" { } } - Context "When an unsupported version of SharePoint is installed" { - Mock Get-xSharePointInstalledProductVersion { return @{ FileMajorPart = 14 } } + Context "When an unsupported version of SharePoint is installed" { + Mock Get-xSharePointInstalledProductVersion { return @{ FileMajorPart = 14 } } Mock Get-SPServiceApplication { return @(@{ TypeName = "Secure Store Service Application" From 7c0319a44d161a2f8891ee292a0a67f298c3e119 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 20:59:15 +1000 Subject: [PATCH 20/31] Expanded test coverage --- .../xSharePoint.xSPServiceInstance.Tests.ps1 | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/Tests/xSharePoint/xSharePoint.xSPServiceInstance.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPServiceInstance.Tests.ps1 index 5e69f07a1..d2016c7a9 100644 --- a/Tests/xSharePoint/xSharePoint.xSPServiceInstance.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPServiceInstance.Tests.ps1 @@ -28,6 +28,18 @@ Describe "xSPServiceInstance" { Mock Start-SPServiceInstance { } Mock Stop-SPServiceInstance { } + Context "The service instance is not running but should be" { + Mock Get-SPServiceInstance { return $null } + + It "returns absent from the get method" { + (Get-TargetResource @testParams).Ensure | Should Be "Absent" + } + + It "returns false from the set method" { + Test-TargetResource @testParams | Should Be $false + } + } + Context "The service instance is not running but should be" { Mock Get-SPServiceInstance { return @( @{ From 96be03f32eabd684c9595358669b39be3023de4f Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 21:37:39 +1000 Subject: [PATCH 21/31] Expanded code coverage --- .../xSharePoint/xSharePoint.xSPSite.Tests.ps1 | 44 +++++++++++++++++++ 1 file changed, 44 insertions(+) diff --git a/Tests/xSharePoint/xSharePoint.xSPSite.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPSite.Tests.ps1 index 7f6af8826..c5ad1e72d 100644 --- a/Tests/xSharePoint/xSharePoint.xSPSite.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPSite.Tests.ps1 @@ -84,6 +84,35 @@ Describe "xSPSite" { It "returns true from the test method" { Test-TargetResource @testParams | Should Be $true + } + + Mock Get-SPSite { return @{ + HostHeaderIsSiteName = $false + WebApplication = @{ + Url = $testParams.Url + UseClaimsAuthentication = $true + } + Url = $testParams.Url + Owner = $null + }} + + It "returns the site data from the get method where a valid site collection admin does not exist" { + Get-TargetResource @testParams | Should Not BeNullOrEmpty + } + + Mock Get-SPSite { return @{ + HostHeaderIsSiteName = $false + WebApplication = @{ + Url = $testParams.Url + UseClaimsAuthentication = $true + } + Url = $testParams.Url + Owner = @{ UserLogin = "DEMO\owner" } + SecondaryContact = @{ UserLogin = "DEMO\secondary" } + }} + + It "returns the site data from the get method where a secondary site contact exists" { + Get-TargetResource @testParams | Should Not BeNullOrEmpty } } @@ -104,6 +133,21 @@ Describe "xSPSite" { It "returns true from the test method" { Test-TargetResource @testParams | Should Be $true + } + + Mock Get-SPSite { return @{ + HostHeaderIsSiteName = $false + WebApplication = @{ + Url = $testParams.Url + UseClaimsAuthentication = $false + } + Url = $testParams.Url + Owner = @{ UserLogin = "DEMO\owner" } + SecondaryContact = @{ UserLogin = "DEMO\secondary" } + }} + + It "returns the site data from the get method where a secondary site contact exists" { + Get-TargetResource @testParams | Should Not BeNullOrEmpty } } } From 52d185deed4724d6454a0e802bb38f88c6cb1d5d Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 21:41:57 +1000 Subject: [PATCH 22/31] Expanded test coverage --- Tests/xSharePoint/xSharePoint.xSPStateServiceApp.Tests.ps1 | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Tests/xSharePoint/xSharePoint.xSPStateServiceApp.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPStateServiceApp.Tests.ps1 index 1454092cd..24d1146fd 100644 --- a/Tests/xSharePoint/xSharePoint.xSPStateServiceApp.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPStateServiceApp.Tests.ps1 @@ -17,6 +17,8 @@ Describe "xSPStateServiceApp" { $testParams = @{ Name = "State Service App" DatabaseName = "SP_StateService" + DatabaseServer = "SQL.test.domain" + DatabaseCredentials = New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)) } Import-Module (Join-Path ((Resolve-Path $PSScriptRoot\..\..).Path) "Modules\xSharePoint") From 6959dd589b62be78e66143510f47ed7a58b96335 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 22:17:36 +1000 Subject: [PATCH 23/31] Expanded test coverage, fixed minor issues --- .../MSFT_xSPUsageApplication.psm1 | 3 +-- .../xSharePoint/xSharePoint.xSPSite.Tests.ps1 | 18 +++++++-------- .../xSharePoint.xSPStateServiceApp.Tests.ps1 | 4 ++-- .../xSharePoint.xSPusageApplication.Tests.ps1 | 23 ++++++++++++++++++- 4 files changed, 34 insertions(+), 14 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPUsageApplication/MSFT_xSPUsageApplication.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPUsageApplication/MSFT_xSPUsageApplication.psm1 index 088d93e97..4fd51fefe 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPUsageApplication/MSFT_xSPUsageApplication.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPUsageApplication/MSFT_xSPUsageApplication.psm1 @@ -80,12 +80,11 @@ function Set-TargetResource if ($null -eq $CurrentState) { Invoke-xSharePointCommand -Credential $InstallAccount -Arguments $PSBoundParameters -ScriptBlock { $params = $args[0] - $newParams = @{} $newParams.Add("Name", $params.Name) if ($params.ContainsKey("DatabaseName")) { $newParams.Add("DatabaseName", $params.DatabaseName) } - if ($params.ContainsKey("DatabasePassword")) { $newParams.Add("DatabasePassword", $params.DatabasePassword) } + if ($params.ContainsKey("DatabasePassword")) { $newParams.Add("DatabasePassword", (ConvertTo-SecureString -String $params.DatabasePassword -AsPlainText -force)) } if ($params.ContainsKey("DatabaseServer")) { $newParams.Add("DatabaseServer", $params.DatabaseServer) } if ($params.ContainsKey("DatabaseUsername")) { $newParams.Add("DatabaseUsername", $params.DatabaseUsername) } if ($params.ContainsKey("FailoverDatabaseServer")) { $newParams.Add("FailoverDatabaseServer", $params.FailoverDatabaseServer) } diff --git a/Tests/xSharePoint/xSharePoint.xSPSite.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPSite.Tests.ps1 index c5ad1e72d..b0ecec56b 100644 --- a/Tests/xSharePoint/xSharePoint.xSPSite.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPSite.Tests.ps1 @@ -86,7 +86,7 @@ Describe "xSPSite" { Test-TargetResource @testParams | Should Be $true } - Mock Get-SPSite { return @{ + Mock Get-SPSite { return @{ HostHeaderIsSiteName = $false WebApplication = @{ Url = $testParams.Url @@ -96,11 +96,11 @@ Describe "xSPSite" { Owner = $null }} - It "returns the site data from the get method where a valid site collection admin does not exist" { + It "returns the site data from the get method where a valid site collection admin does not exist" { Get-TargetResource @testParams | Should Not BeNullOrEmpty } - - Mock Get-SPSite { return @{ + + Mock Get-SPSite { return @{ HostHeaderIsSiteName = $false WebApplication = @{ Url = $testParams.Url @@ -108,10 +108,10 @@ Describe "xSPSite" { } Url = $testParams.Url Owner = @{ UserLogin = "DEMO\owner" } - SecondaryContact = @{ UserLogin = "DEMO\secondary" } + SecondaryContact = @{ UserLogin = "DEMO\secondary" } }} - It "returns the site data from the get method where a secondary site contact exists" { + It "returns the site data from the get method where a secondary site contact exists" { Get-TargetResource @testParams | Should Not BeNullOrEmpty } } @@ -135,7 +135,7 @@ Describe "xSPSite" { Test-TargetResource @testParams | Should Be $true } - Mock Get-SPSite { return @{ + Mock Get-SPSite { return @{ HostHeaderIsSiteName = $false WebApplication = @{ Url = $testParams.Url @@ -143,10 +143,10 @@ Describe "xSPSite" { } Url = $testParams.Url Owner = @{ UserLogin = "DEMO\owner" } - SecondaryContact = @{ UserLogin = "DEMO\secondary" } + SecondaryContact = @{ UserLogin = "DEMO\secondary" } }} - It "returns the site data from the get method where a secondary site contact exists" { + It "returns the site data from the get method where a secondary site contact exists" { Get-TargetResource @testParams | Should Not BeNullOrEmpty } } diff --git a/Tests/xSharePoint/xSharePoint.xSPStateServiceApp.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPStateServiceApp.Tests.ps1 index 24d1146fd..8175ebaca 100644 --- a/Tests/xSharePoint/xSharePoint.xSPStateServiceApp.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPStateServiceApp.Tests.ps1 @@ -17,8 +17,8 @@ Describe "xSPStateServiceApp" { $testParams = @{ Name = "State Service App" DatabaseName = "SP_StateService" - DatabaseServer = "SQL.test.domain" - DatabaseCredentials = New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)) + DatabaseServer = "SQL.test.domain" + DatabaseCredentials = New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)) } Import-Module (Join-Path ((Resolve-Path $PSScriptRoot\..\..).Path) "Modules\xSharePoint") diff --git a/Tests/xSharePoint/xSharePoint.xSPusageApplication.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPusageApplication.Tests.ps1 index 5d8e07ea4..b95d44197 100644 --- a/Tests/xSharePoint/xSharePoint.xSPusageApplication.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPusageApplication.Tests.ps1 @@ -20,6 +20,11 @@ Describe "xSPUsageApplication" { UsageLogLocation = "L:\UsageLogs" UsageLogMaxFileSizeKB = 1024 UsageLogMaxSpaceGB = 10 + DatabaseName = "SP_Usage" + DatabaseServer = "sql.test.domain" + DatabaseUsername = "user" + DatabasePassword = "password" + FailoverDatabaseServer = "anothersql.test.domain" } Import-Module (Join-Path ((Resolve-Path $PSScriptRoot\..\..).Path) "Modules\xSharePoint") @@ -38,7 +43,7 @@ Describe "xSPUsageApplication" { UsageLogMaxSpaceGB = $testParams.UsageLogMaxSpaceGB }} - Context "When no service application exists in the current farm" { + Context "When no service applications exist in the current farm" { Mock Get-SPServiceApplication { return $null } @@ -57,6 +62,22 @@ Describe "xSPUsageApplication" { } } + Context "When service applications exist in the current farm but not the specific usage service app" { + + Mock Get-SPServiceApplication { return @(@{ + TypeName = "Some other service app type" + }) } + + It "returns null from the Get method" { + Get-TargetResource @testParams | Should BeNullOrEmpty + Assert-MockCalled Get-SPServiceApplication -ParameterFilter { $Name -eq $testParams.Name } + } + + It "returns false when the Test method is called" { + Test-TargetResource @testParams | Should Be $false + } + } + Context "When a service application exists and is configured correctly" { Mock Get-SPServiceApplication { return @(@{ From 24dbba847d561ccc2216b776b76dc00b1711dc9f Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 22:34:25 +1000 Subject: [PATCH 24/31] Code coverage improvements --- ...rePoint.xSPUserProfileServiceApp.Tests.ps1 | 36 +++++++++++++++++-- 1 file changed, 34 insertions(+), 2 deletions(-) diff --git a/Tests/xSharePoint/xSharePoint.xSPUserProfileServiceApp.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPUserProfileServiceApp.Tests.ps1 index 8d1b09f64..01b96af4f 100644 --- a/Tests/xSharePoint/xSharePoint.xSPUserProfileServiceApp.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPUserProfileServiceApp.Tests.ps1 @@ -30,14 +30,14 @@ Describe "xSPUserProfileServiceApp" { Mock Get-SPFarm { return @{ DefaultServiceAccount = @{ Name = $testParams.FarmAccount.Username } }} - Mock New-SPProfileServiceApplication { } + Mock New-SPProfileServiceApplication { return @{} } Mock New-SPProfileServiceApplicationProxy { } Mock Add-xSharePointUserToLocalAdmin { } Mock Test-xSharePointUserIsLocalAdmin { return $false } Mock Remove-xSharePointUserToLocalAdmin { } Mock New-PSSession { return $null } -ModuleName "xSharePoint.Util" - Context "When no service application exists in the current farm" { + Context "When no service applications exist in the current farm" { Mock Get-SPServiceApplication { return $null } @@ -53,6 +53,29 @@ Describe "xSPUserProfileServiceApp" { It "creates a new service application in the set method" { Set-TargetResource @testParams Assert-MockCalled New-SPProfileServiceApplication + } + + $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("domain\username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) + It "creates a new service application in the set method when InstallAccount is used" { + Set-TargetResource @testParams + Assert-MockCalled New-SPProfileServiceApplication + } + $testParams.Remove("InstallAccount") + } + + Context "When service applications exist in the current farm but not the specific user profile service app" { + + Mock Get-SPServiceApplication { return @(@{ + TypeName = "Some other service app type" + }) } + + It "returns null from the Get method" { + Get-TargetResource @testParams | Should BeNullOrEmpty + Assert-MockCalled Get-SPServiceApplication -ParameterFilter { $Name -eq $testParams.Name } + } + + It "returns false when the Test method is called" { + Test-TargetResource @testParams | Should Be $false } } @@ -110,6 +133,15 @@ Describe "xSPUserProfileServiceApp" { It "returns true when the Test method is called" { Test-TargetResource @testParams | Should Be $true } + + Mock Get-SPFarm { return @{ + DefaultServiceAccount = @{ Name = "WRONG\account" } + }} + + It "returns values from the get method where the farm account doesn't match" { + Get-TargetResource @testParams | Should Not BeNullOrEmpty + Assert-MockCalled Get-SPServiceApplication -ParameterFilter { $Name -eq $testParams.Name } + } } } } \ No newline at end of file From f19aa1097b819d08429e9dc6720257b24cbbb03e Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 23:28:33 +1000 Subject: [PATCH 25/31] Expanded code coverage --- .../MSFT_xSPUserProfileSyncService.psm1 | 5 +- ...ePoint.xSPUserProfileSyncService.Tests.ps1 | 256 ++++++++++-------- 2 files changed, 142 insertions(+), 119 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPUserProfileSyncService/MSFT_xSPUserProfileSyncService.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPUserProfileSyncService/MSFT_xSPUserProfileSyncService.psm1 index bfa80d63d..0baebd176 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPUserProfileSyncService/MSFT_xSPUserProfileSyncService.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPUserProfileSyncService/MSFT_xSPUserProfileSyncService.psm1 @@ -111,10 +111,9 @@ function Set-TargetResource $maxCount = 10 while (($count -lt $maxCount) -and ($syncService.Status -ne $desiredState)) { - # Get the current status of the Sync service - $syncService = Get-SPServiceInstance -Server $env:COMPUTERNAME | Where-Object { $_.TypeName -eq "User Profile Synchronization Service" } - if ($syncService.Status -ne $desiredState) { Start-Sleep -Seconds 60 } + # Get the current status of the Sync service + $syncService = Get-SPServiceInstance -Server $env:COMPUTERNAME | Where-Object { $_.TypeName -eq "User Profile Synchronization Service" } $count++ } } diff --git a/Tests/xSharePoint/xSharePoint.xSPUserProfileSyncService.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPUserProfileSyncService.Tests.ps1 index 088953a3b..a5698e344 100644 --- a/Tests/xSharePoint/xSharePoint.xSPUserProfileSyncService.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPUserProfileSyncService.Tests.ps1 @@ -42,128 +42,152 @@ Describe "xSPUserProfileSyncService" { Mock Test-xSharePointUserIsLocalAdmin { return $false } Mock Remove-xSharePointUserToLocalAdmin { } Mock New-PSSession { return $null } -ModuleName "xSharePoint.Util" + Mock Start-Sleep { } switch ($majorBuildNumber) { 15 { - Context "User profile sync service is not running and should be" { - Mock Get-SPServiceInstance { if ($Global:xSharePointUPACheck -eq $false) { - $Global:xSharePointUPACheck = $true - return @( @{ - Status = "Disabled" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::Empty - TypeName = "User Profile Synchronization Service" - }) - } else { - return @( @{ - Status = "Online" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::NewGuid() - TypeName = "User Profile Synchronization Service" - }) - } - } - Mock Get-SPServiceApplication { return @( - New-Object Object | - Add-Member NoteProperty ID ([Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f")) -PassThru | - Add-Member NoteProperty TypeName "User Profile Service Application" -PassThru | - Add-Member ScriptMethod SetSynchronizationMachine { - param($computerName, $syncServiceID, $FarmUserName, $FarmPassword) - } -PassThru - )} - - It "returns absent from the get method" { - $Global:xSharePointUPACheck = $false - (Get-TargetResource @testParams).Ensure | Should Be "Absent" - } + Context "User profile sync service is not found locally" { + Mock Get-SPServiceInstance { return $null } - It "returns false from the test method" { - $Global:xSharePointUPACheck = $false - Test-TargetResource @testParams | Should Be $false - } - - It "calls the start service cmdlet from the set method" { - $Global:xSharePointUPACheck = $false - Set-TargetResource @testParams + It "returns absent from the get method" { + $Global:xSharePointUPACheck = $false + (Get-TargetResource @testParams).Ensure | Should Be "Absent" + } + } - Assert-MockCalled Start-SPServiceInstance - } - } - - Context "User profile sync service is running and should be" { - Mock Get-SPServiceInstance { return @( @{ - Status = "Online" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::NewGuid() - TypeName = "User Profile Synchronization Service" - }) - } + Context "User profile sync service is not running and should be" { + Mock Get-SPServiceInstance { if ($Global:xSharePointUPACheck -eq $false) { + $Global:xSharePointUPACheck = $true + return @( @{ + Status = "Disabled" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::Empty + TypeName = "User Profile Synchronization Service" + }) + } else { + return @( @{ + Status = "Online" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::NewGuid() + TypeName = "User Profile Synchronization Service" + }) + } + } + Mock Get-SPServiceApplication { return @( + New-Object Object | + Add-Member NoteProperty ID ([Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f")) -PassThru | + Add-Member NoteProperty TypeName "User Profile Service Application" -PassThru | + Add-Member ScriptMethod SetSynchronizationMachine { + param($computerName, $syncServiceID, $FarmUserName, $FarmPassword) + } -PassThru + )} + + It "returns absent from the get method" { + $Global:xSharePointUPACheck = $false + (Get-TargetResource @testParams).Ensure | Should Be "Absent" + } + + It "returns false from the test method" { + $Global:xSharePointUPACheck = $false + Test-TargetResource @testParams | Should Be $false + } + + It "calls the start service cmdlet from the set method" { + $Global:xSharePointUPACheck = $false + Set-TargetResource @testParams + + Assert-MockCalled Start-SPServiceInstance + } + + Mock Get-SPFarm { return @{ + DefaultServiceAccount = @{ Name = "WRONG\account" } + }} + + It "returns values from the get method where the farm account doesn't match" { + Get-TargetResource @testParams | Should Not BeNullOrEmpty + } + + $Global:xSharePointUPACheck = $false + Mock Get-SPServiceApplication { return $null } + It "throws in the set method if the user profile service app can't be found" { + { Set-TargetResource @testParams } | Should Throw + } + } + + Context "User profile sync service is running and should be" { + Mock Get-SPServiceInstance { return @( @{ + Status = "Online" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::NewGuid() + TypeName = "User Profile Synchronization Service" + }) + } - It "returns present from the get method" { - (Get-TargetResource @testParams).Ensure | Should Be "Present" - } - - It "returns true from the test method" { - Test-TargetResource @testParams | Should Be $true - } - } - - $testParams.Ensure = "Absent" - - Context "User profile sync service is running and shouldn't be" { - Mock Get-SPServiceInstance { if ($Global:xSharePointUPACheck -eq $false) { - $Global:xSharePointUPACheck = $true - return @( @{ - Status = "Online" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::NewGuid() - TypeName = "User Profile Synchronization Service" - }) - } else { - return @( @{ - Status = "Disabled" - ID = [Guid]::Empty - UserProfileApplicationGuid = [Guid]::Empty - TypeName = "User Profile Synchronization Service" - }) - } - } - - It "returns present from the get method" { - $Global:xSharePointUPACheck = $false - (Get-TargetResource @testParams).Ensure | Should Be "Present" - } - - It "returns false from the test method" { - $Global:xSharePointUPACheck = $false - Test-TargetResource @testParams | Should Be $false - } - - It "calls the start service cmdlet from the set method" { - $Global:xSharePointUPACheck = $false - Set-TargetResource @testParams - - Assert-MockCalled Stop-SPServiceInstance - } - } - - Context "User profile sync service is not running and shouldn't be" { - Mock Get-SPServiceInstance { return @( @{ - Status = "Disabled" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::Empty - TypeName = "User Profile Synchronization Service" - }) - } - - It "returns absent from the get method" { - (Get-TargetResource @testParams).Ensure | Should Be "Absent" - } - - It "returns true from the test method" { - Test-TargetResource @testParams | Should Be $true - } - } + It "returns present from the get method" { + (Get-TargetResource @testParams).Ensure | Should Be "Present" + } + + It "returns true from the test method" { + Test-TargetResource @testParams | Should Be $true + } + } + + $testParams.Ensure = "Absent" + + Context "User profile sync service is running and shouldn't be" { + Mock Get-SPServiceInstance { if ($Global:xSharePointUPACheck -eq $false) { + $Global:xSharePointUPACheck = $true + return @( @{ + Status = "Online" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::NewGuid() + TypeName = "User Profile Synchronization Service" + }) + } else { + return @( @{ + Status = "Disabled" + ID = [Guid]::Empty + UserProfileApplicationGuid = [Guid]::Empty + TypeName = "User Profile Synchronization Service" + }) + } + } + + It "returns present from the get method" { + $Global:xSharePointUPACheck = $false + (Get-TargetResource @testParams).Ensure | Should Be "Present" + } + + It "returns false from the test method" { + $Global:xSharePointUPACheck = $false + Test-TargetResource @testParams | Should Be $false + } + + It "calls the start service cmdlet from the set method" { + $Global:xSharePointUPACheck = $false + Set-TargetResource @testParams + + Assert-MockCalled Stop-SPServiceInstance + } + } + + Context "User profile sync service is not running and shouldn't be" { + Mock Get-SPServiceInstance { return @( @{ + Status = "Disabled" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::Empty + TypeName = "User Profile Synchronization Service" + }) + } + + It "returns absent from the get method" { + (Get-TargetResource @testParams).Ensure | Should Be "Absent" + } + + It "returns true from the test method" { + Test-TargetResource @testParams | Should Be $true + } + } } 16 { Context "All methods throw exceptions as user profile sync doesn't exist in 2016" { From 2f7ac55f428f3bbea8dba9b747aea750d1ceeb7b Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 23:40:15 +1000 Subject: [PATCH 26/31] Added scenarios to expand test coverage --- .../xSharePoint.xSPWebApplication.Tests.ps1 | 53 ++++++++++++++++++- 1 file changed, 52 insertions(+), 1 deletion(-) diff --git a/Tests/xSharePoint/xSharePoint.xSPWebApplication.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPWebApplication.Tests.ps1 index b2a6a83fe..36f5c0548 100644 --- a/Tests/xSharePoint/xSharePoint.xSPWebApplication.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPWebApplication.Tests.ps1 @@ -49,6 +49,24 @@ Describe "xSPWebApplication" { Assert-MockCalled New-SPWebApplication Assert-MockCalled New-SPAuthenticationProvider -ParameterFilter { $DisableKerberos -eq $true } } + + $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) + It "calls the new cmdlet from the set method where InstallAccount is used" { + Set-TargetResource @testParams + + Assert-MockCalled New-SPWebApplication + Assert-MockCalled New-SPAuthenticationProvider -ParameterFilter { $DisableKerberos -eq $true } + } + $testParams.Remove("InstallAccount") + + $testParams.Add("AllowAnonymous", $true) + It "calls the new cmdlet from the set where anonymous authentication is requested" { + Set-TargetResource @testParams + + Assert-MockCalled New-SPWebApplication + Assert-MockCalled New-SPAuthenticationProvider -ParameterFilter { $DisableKerberos -eq $true } + } + $testParams.Remove("AllowAnonymous") } $testParams.AuthenticationMethod = "Kerberos" @@ -71,7 +89,9 @@ Describe "xSPWebApplication" { } } - Context "The web appliation does exist and should" { + $testParams.AuthenticationMethod = "NTLM" + + Context "The web appliation does exist and should that uses NTLM" { Mock Get-SPAuthenticationProvider { return @{ DisableKerberos = $true; AllowAnonymous = $false } } Mock Get-SPWebApplication { return @(@{ DisplayName = $testParams.Name @@ -95,6 +115,37 @@ Describe "xSPWebApplication" { Get-TargetResource @testParams | Should Not BeNullOrEmpty } + It "returns true from the test method" { + Test-TargetResource @testParams | Should Be $true + } + } + + $testParams.AuthenticationMethod = "Kerberos" + + Context "The web appliation does exist and should that uses Kerberos" { + Mock Get-SPAuthenticationProvider { return @{ DisableKerberos = $false; AllowAnonymous = $false } } + Mock Get-SPWebApplication { return @(@{ + DisplayName = $testParams.Name + ApplicationPool = @{ + Name = $testParams.ApplicationPool + Username = $testParams.ApplicationPoolAccount + } + ContentDatabases = @( + @{ + Name = "SP_Content_01" + Server = "sql.domain.local" + } + ) + IisSettings = @( + @{ Path = "C:\inetpub\wwwroot\something" } + ) + Url = $testParams.Url + })} + + It "returns the current data from the get method" { + Get-TargetResource @testParams | Should Not BeNullOrEmpty + } + It "returns true from the test method" { Test-TargetResource @testParams | Should Be $true } From 01e66eb6a6427fa1de41f9c63f75d85db2a9cbc1 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Tue, 29 Sep 2015 23:40:54 +1000 Subject: [PATCH 27/31] Formatting fixes --- .../MSFT_xSPUserProfileSyncService.psm1 | 2 +- ...rePoint.xSPUserProfileServiceApp.Tests.ps1 | 6 +- ...ePoint.xSPUserProfileSyncService.Tests.ps1 | 278 +++++++++--------- .../xSharePoint.xSPWebApplication.Tests.ps1 | 18 +- 4 files changed, 152 insertions(+), 152 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPUserProfileSyncService/MSFT_xSPUserProfileSyncService.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPUserProfileSyncService/MSFT_xSPUserProfileSyncService.psm1 index 0baebd176..eac5b8704 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPUserProfileSyncService/MSFT_xSPUserProfileSyncService.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPUserProfileSyncService/MSFT_xSPUserProfileSyncService.psm1 @@ -112,7 +112,7 @@ function Set-TargetResource while (($count -lt $maxCount) -and ($syncService.Status -ne $desiredState)) { if ($syncService.Status -ne $desiredState) { Start-Sleep -Seconds 60 } - # Get the current status of the Sync service + # Get the current status of the Sync service $syncService = Get-SPServiceInstance -Server $env:COMPUTERNAME | Where-Object { $_.TypeName -eq "User Profile Synchronization Service" } $count++ } diff --git a/Tests/xSharePoint/xSharePoint.xSPUserProfileServiceApp.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPUserProfileServiceApp.Tests.ps1 index 01b96af4f..97081f11b 100644 --- a/Tests/xSharePoint/xSharePoint.xSPUserProfileServiceApp.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPUserProfileServiceApp.Tests.ps1 @@ -55,12 +55,12 @@ Describe "xSPUserProfileServiceApp" { Assert-MockCalled New-SPProfileServiceApplication } - $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("domain\username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) - It "creates a new service application in the set method when InstallAccount is used" { + $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("domain\username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) + It "creates a new service application in the set method when InstallAccount is used" { Set-TargetResource @testParams Assert-MockCalled New-SPProfileServiceApplication } - $testParams.Remove("InstallAccount") + $testParams.Remove("InstallAccount") } Context "When service applications exist in the current farm but not the specific user profile service app" { diff --git a/Tests/xSharePoint/xSharePoint.xSPUserProfileSyncService.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPUserProfileSyncService.Tests.ps1 index a5698e344..e06fbe133 100644 --- a/Tests/xSharePoint/xSharePoint.xSPUserProfileSyncService.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPUserProfileSyncService.Tests.ps1 @@ -42,152 +42,152 @@ Describe "xSPUserProfileSyncService" { Mock Test-xSharePointUserIsLocalAdmin { return $false } Mock Remove-xSharePointUserToLocalAdmin { } Mock New-PSSession { return $null } -ModuleName "xSharePoint.Util" - Mock Start-Sleep { } + Mock Start-Sleep { } switch ($majorBuildNumber) { 15 { - Context "User profile sync service is not found locally" { - Mock Get-SPServiceInstance { return $null } + Context "User profile sync service is not found locally" { + Mock Get-SPServiceInstance { return $null } - It "returns absent from the get method" { - $Global:xSharePointUPACheck = $false - (Get-TargetResource @testParams).Ensure | Should Be "Absent" - } - } + It "returns absent from the get method" { + $Global:xSharePointUPACheck = $false + (Get-TargetResource @testParams).Ensure | Should Be "Absent" + } + } Context "User profile sync service is not running and should be" { - Mock Get-SPServiceInstance { if ($Global:xSharePointUPACheck -eq $false) { - $Global:xSharePointUPACheck = $true - return @( @{ - Status = "Disabled" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::Empty - TypeName = "User Profile Synchronization Service" - }) - } else { - return @( @{ - Status = "Online" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::NewGuid() - TypeName = "User Profile Synchronization Service" - }) - } - } - Mock Get-SPServiceApplication { return @( - New-Object Object | - Add-Member NoteProperty ID ([Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f")) -PassThru | - Add-Member NoteProperty TypeName "User Profile Service Application" -PassThru | - Add-Member ScriptMethod SetSynchronizationMachine { - param($computerName, $syncServiceID, $FarmUserName, $FarmPassword) - } -PassThru - )} - - It "returns absent from the get method" { - $Global:xSharePointUPACheck = $false - (Get-TargetResource @testParams).Ensure | Should Be "Absent" - } - - It "returns false from the test method" { - $Global:xSharePointUPACheck = $false - Test-TargetResource @testParams | Should Be $false - } - - It "calls the start service cmdlet from the set method" { - $Global:xSharePointUPACheck = $false - Set-TargetResource @testParams - - Assert-MockCalled Start-SPServiceInstance - } - - Mock Get-SPFarm { return @{ - DefaultServiceAccount = @{ Name = "WRONG\account" } - }} - - It "returns values from the get method where the farm account doesn't match" { - Get-TargetResource @testParams | Should Not BeNullOrEmpty - } - - $Global:xSharePointUPACheck = $false - Mock Get-SPServiceApplication { return $null } - It "throws in the set method if the user profile service app can't be found" { - { Set-TargetResource @testParams } | Should Throw - } - } - - Context "User profile sync service is running and should be" { - Mock Get-SPServiceInstance { return @( @{ - Status = "Online" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::NewGuid() - TypeName = "User Profile Synchronization Service" - }) - } + Mock Get-SPServiceInstance { if ($Global:xSharePointUPACheck -eq $false) { + $Global:xSharePointUPACheck = $true + return @( @{ + Status = "Disabled" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::Empty + TypeName = "User Profile Synchronization Service" + }) + } else { + return @( @{ + Status = "Online" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::NewGuid() + TypeName = "User Profile Synchronization Service" + }) + } + } + Mock Get-SPServiceApplication { return @( + New-Object Object | + Add-Member NoteProperty ID ([Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f")) -PassThru | + Add-Member NoteProperty TypeName "User Profile Service Application" -PassThru | + Add-Member ScriptMethod SetSynchronizationMachine { + param($computerName, $syncServiceID, $FarmUserName, $FarmPassword) + } -PassThru + )} + + It "returns absent from the get method" { + $Global:xSharePointUPACheck = $false + (Get-TargetResource @testParams).Ensure | Should Be "Absent" + } + + It "returns false from the test method" { + $Global:xSharePointUPACheck = $false + Test-TargetResource @testParams | Should Be $false + } + + It "calls the start service cmdlet from the set method" { + $Global:xSharePointUPACheck = $false + Set-TargetResource @testParams + + Assert-MockCalled Start-SPServiceInstance + } + + Mock Get-SPFarm { return @{ + DefaultServiceAccount = @{ Name = "WRONG\account" } + }} + + It "returns values from the get method where the farm account doesn't match" { + Get-TargetResource @testParams | Should Not BeNullOrEmpty + } + + $Global:xSharePointUPACheck = $false + Mock Get-SPServiceApplication { return $null } + It "throws in the set method if the user profile service app can't be found" { + { Set-TargetResource @testParams } | Should Throw + } + } + + Context "User profile sync service is running and should be" { + Mock Get-SPServiceInstance { return @( @{ + Status = "Online" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::NewGuid() + TypeName = "User Profile Synchronization Service" + }) + } - It "returns present from the get method" { - (Get-TargetResource @testParams).Ensure | Should Be "Present" - } - - It "returns true from the test method" { - Test-TargetResource @testParams | Should Be $true - } - } - - $testParams.Ensure = "Absent" - - Context "User profile sync service is running and shouldn't be" { - Mock Get-SPServiceInstance { if ($Global:xSharePointUPACheck -eq $false) { - $Global:xSharePointUPACheck = $true - return @( @{ - Status = "Online" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::NewGuid() - TypeName = "User Profile Synchronization Service" - }) - } else { - return @( @{ - Status = "Disabled" - ID = [Guid]::Empty - UserProfileApplicationGuid = [Guid]::Empty - TypeName = "User Profile Synchronization Service" - }) - } - } - - It "returns present from the get method" { - $Global:xSharePointUPACheck = $false - (Get-TargetResource @testParams).Ensure | Should Be "Present" - } - - It "returns false from the test method" { - $Global:xSharePointUPACheck = $false - Test-TargetResource @testParams | Should Be $false - } - - It "calls the start service cmdlet from the set method" { - $Global:xSharePointUPACheck = $false - Set-TargetResource @testParams - - Assert-MockCalled Stop-SPServiceInstance - } - } - - Context "User profile sync service is not running and shouldn't be" { - Mock Get-SPServiceInstance { return @( @{ - Status = "Disabled" - ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") - UserProfileApplicationGuid = [Guid]::Empty - TypeName = "User Profile Synchronization Service" - }) - } - - It "returns absent from the get method" { - (Get-TargetResource @testParams).Ensure | Should Be "Absent" - } - - It "returns true from the test method" { - Test-TargetResource @testParams | Should Be $true - } - } + It "returns present from the get method" { + (Get-TargetResource @testParams).Ensure | Should Be "Present" + } + + It "returns true from the test method" { + Test-TargetResource @testParams | Should Be $true + } + } + + $testParams.Ensure = "Absent" + + Context "User profile sync service is running and shouldn't be" { + Mock Get-SPServiceInstance { if ($Global:xSharePointUPACheck -eq $false) { + $Global:xSharePointUPACheck = $true + return @( @{ + Status = "Online" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::NewGuid() + TypeName = "User Profile Synchronization Service" + }) + } else { + return @( @{ + Status = "Disabled" + ID = [Guid]::Empty + UserProfileApplicationGuid = [Guid]::Empty + TypeName = "User Profile Synchronization Service" + }) + } + } + + It "returns present from the get method" { + $Global:xSharePointUPACheck = $false + (Get-TargetResource @testParams).Ensure | Should Be "Present" + } + + It "returns false from the test method" { + $Global:xSharePointUPACheck = $false + Test-TargetResource @testParams | Should Be $false + } + + It "calls the start service cmdlet from the set method" { + $Global:xSharePointUPACheck = $false + Set-TargetResource @testParams + + Assert-MockCalled Stop-SPServiceInstance + } + } + + Context "User profile sync service is not running and shouldn't be" { + Mock Get-SPServiceInstance { return @( @{ + Status = "Disabled" + ID = [Guid]::Parse("21946987-5163-418f-b781-2beb83aa191f") + UserProfileApplicationGuid = [Guid]::Empty + TypeName = "User Profile Synchronization Service" + }) + } + + It "returns absent from the get method" { + (Get-TargetResource @testParams).Ensure | Should Be "Absent" + } + + It "returns true from the test method" { + Test-TargetResource @testParams | Should Be $true + } + } } 16 { Context "All methods throw exceptions as user profile sync doesn't exist in 2016" { diff --git a/Tests/xSharePoint/xSharePoint.xSPWebApplication.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPWebApplication.Tests.ps1 index 36f5c0548..9bcb0d0bf 100644 --- a/Tests/xSharePoint/xSharePoint.xSPWebApplication.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPWebApplication.Tests.ps1 @@ -50,23 +50,23 @@ Describe "xSPWebApplication" { Assert-MockCalled New-SPAuthenticationProvider -ParameterFilter { $DisableKerberos -eq $true } } - $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) - It "calls the new cmdlet from the set method where InstallAccount is used" { + $testParams.Add("InstallAccount", (New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force)))) + It "calls the new cmdlet from the set method where InstallAccount is used" { Set-TargetResource @testParams Assert-MockCalled New-SPWebApplication Assert-MockCalled New-SPAuthenticationProvider -ParameterFilter { $DisableKerberos -eq $true } } - $testParams.Remove("InstallAccount") + $testParams.Remove("InstallAccount") - $testParams.Add("AllowAnonymous", $true) - It "calls the new cmdlet from the set where anonymous authentication is requested" { + $testParams.Add("AllowAnonymous", $true) + It "calls the new cmdlet from the set where anonymous authentication is requested" { Set-TargetResource @testParams Assert-MockCalled New-SPWebApplication Assert-MockCalled New-SPAuthenticationProvider -ParameterFilter { $DisableKerberos -eq $true } } - $testParams.Remove("AllowAnonymous") + $testParams.Remove("AllowAnonymous") } $testParams.AuthenticationMethod = "Kerberos" @@ -89,7 +89,7 @@ Describe "xSPWebApplication" { } } - $testParams.AuthenticationMethod = "NTLM" + $testParams.AuthenticationMethod = "NTLM" Context "The web appliation does exist and should that uses NTLM" { Mock Get-SPAuthenticationProvider { return @{ DisableKerberos = $true; AllowAnonymous = $false } } @@ -120,9 +120,9 @@ Describe "xSPWebApplication" { } } - $testParams.AuthenticationMethod = "Kerberos" + $testParams.AuthenticationMethod = "Kerberos" - Context "The web appliation does exist and should that uses Kerberos" { + Context "The web appliation does exist and should that uses Kerberos" { Mock Get-SPAuthenticationProvider { return @{ DisableKerberos = $false; AllowAnonymous = $false } } Mock Get-SPWebApplication { return @(@{ DisplayName = $testParams.Name From a17ff915a5621a75d165ceca2c443312a85a0f7e Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Thu, 1 Oct 2015 10:15:52 +1000 Subject: [PATCH 28/31] Refactored tests for cache accounts and util --- .../MSFT_xSPCacheAccounts.psm1 | 12 +- .../xSharePoint.CacheAccounts.psm1 | 35 ----- .../xSharePoint.Util/xSharePoint.Util.psm1 | 131 ++++++------------ Modules/xSharePoint/xSharePoint.psd1 | 6 +- Modules/xSharePoint/xSharePoint.pssproj | 2 - Tests/xSharePoint/xSharePoint.Util.Tests.ps1 | 29 ++++ .../xSharePoint.xSPCacheAccounts.Tests.ps1 | 106 ++++++++++---- 7 files changed, 165 insertions(+), 156 deletions(-) delete mode 100644 Modules/xSharePoint/Modules/xSharePoint.CacheAccounts/xSharePoint.CacheAccounts.psm1 diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPCacheAccounts/MSFT_xSPCacheAccounts.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPCacheAccounts/MSFT_xSPCacheAccounts.psm1 index 364ef1cc6..b96cd2072 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPCacheAccounts/MSFT_xSPCacheAccounts.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPCacheAccounts/MSFT_xSPCacheAccounts.psm1 @@ -54,7 +54,6 @@ function Set-TargetResource $result = Invoke-xSharePointCommand -Credential $InstallAccount -Arguments $PSBoundParameters -ScriptBlock { $params = $args[0] - $wa = Get-SPWebApplication -Identity $params.WebAppUrl -ErrorAction SilentlyContinue if ($null -eq $wa) { @@ -72,10 +71,15 @@ function Set-TargetResource $wa.Properties.Add("portalsuperreaderaccount", $params.SuperReaderAlias) } - Set-xSharePointCacheReaderPolicy -WebApplication $wa -UserName $params.SuperReaderAlias - Set-xSharePointCacheOwnerPolicy -WebApplication $wa -UserName $params.SuperUserAlias + $readPolicy = $wa.Policies.Add($params.SuperReaderAlias, $params.SuperReaderAlias) + $readPolicyRole = $wa.PolicyRoles.GetSpecialRole([Microsoft.SharePoint.Administration.SPPolicyRoleType]::FullRead) + $readPolicy.PolicyRoleBindings.Add($readPolicyRole) - Update-xSharePointObject -InputObject $wa + $policy = $wa.Policies.Add($params.SuperUserAlias, $params.SuperUserAlias) + $policyRole = $wa.PolicyRoles.GetSpecialRole([Microsoft.SharePoint.Administration.SPPolicyRoleType]::FullControl) + $policy.PolicyRoleBindings.Add($policyRole) + + $wa.Update() } } diff --git a/Modules/xSharePoint/Modules/xSharePoint.CacheAccounts/xSharePoint.CacheAccounts.psm1 b/Modules/xSharePoint/Modules/xSharePoint.CacheAccounts/xSharePoint.CacheAccounts.psm1 deleted file mode 100644 index a97057976..000000000 --- a/Modules/xSharePoint/Modules/xSharePoint.CacheAccounts/xSharePoint.CacheAccounts.psm1 +++ /dev/null @@ -1,35 +0,0 @@ -function Set-xSharePointCacheReaderPolicy() { - [CmdletBinding()] - param - ( - [parameter(Mandatory = $true,Position=1)] - $WebApplication, - - [parameter(Mandatory = $true,Position=2)] - [string] - $UserName - ) - $VerbosePreference = "Continue" - - $policy = $WebApplication.Policies.Add($UserName, $UserName) - $policyRole = $WebApplication.PolicyRoles.GetSpecialRole([Microsoft.SharePoint.Administration.SPPolicyRoleType]::FullRead) - $policy.PolicyRoleBindings.Add($policyRole) -} - -function Set-xSharePointCacheOwnerPolicy() { - [CmdletBinding()] - param - ( - [parameter(Mandatory = $true,Position=1)] - $WebApplication, - - [parameter(Mandatory = $true,Position=2)] - [string] - $UserName - ) - $policy = $WebApplication.Policies.Add($UserName, $UserName) - $policyRole = $WebApplication.PolicyRoles.GetSpecialRole([Microsoft.SharePoint.Administration.SPPolicyRoleType]::FullControl) - $policy.PolicyRoleBindings.Add($policyRole) -} - -Export-ModuleMember -Function * \ No newline at end of file diff --git a/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 b/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 index 592288615..3bcd9be0b 100644 --- a/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 +++ b/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 @@ -1,19 +1,41 @@ -function Invoke-xSharePointCommand() { +function Add-xSharePointUserToLocalAdmin() { [CmdletBinding()] param ( - [parameter(Mandatory = $false)] - [System.Management.Automation.PSCredential] - $Credential, + [parameter(Mandatory = $true,Position=1)] [string] $UserName + ) - [parameter(Mandatory = $false)] - [HashTable] - $Arguments, + $domainName = $UserName.Split('\')[0] + $accountName = $UserName.Split('\')[1] + Write-Verbose -Message "Adding $domainName\$userName to local admin group" + ([ADSI]"WinNT://$($env:computername)/Administrators,group").Add("WinNT://$domainName/$accountName") | Out-Null +} - [parameter(Mandatory = $true)] - [ScriptBlock] - $ScriptBlock +function Get-xSharePointAssemblyVersion() { + [CmdletBinding()] + param + ( + [parameter(Mandatory = $true,Position=1)] + [string] + $PathToAssembly + ) + return (Get-Command $PathToAssembly).FileVersionInfo.FileMajorPart +} + +function Get-xSharePointInstalledProductVersion() { + $pathToSearch = "C:\Program Files\Common Files\microsoft shared\Web Server Extensions\*\ISAPI\Microsoft.SharePoint.dll" + $fullPath = Get-Item $pathToSearch | Sort-Object { $_.Directory } -Descending | Select-Object -First 1 + return (Get-Command $fullPath).FileVersionInfo +} + +function Invoke-xSharePointCommand() { + [CmdletBinding()] + param + ( + [parameter(Mandatory = $false)] [System.Management.Automation.PSCredential] $Credential, + [parameter(Mandatory = $false)] [HashTable] $Arguments, + [parameter(Mandatory = $true)] [ScriptBlock] $ScriptBlock ) $VerbosePreference = 'Continue' @@ -61,14 +83,9 @@ function Rename-xSharePointParamValue() { [CmdletBinding()] param ( - [parameter(Mandatory = $true,Position=1,ValueFromPipeline=$true)] - $params, - - [parameter(Mandatory = $true,Position=2)] - $oldName, - - [parameter(Mandatory = $true,Position=3)] - $newName + [parameter(Mandatory = $true,Position=1,ValueFromPipeline=$true)] $params, + [parameter(Mandatory = $true,Position=2)] $oldName, + [parameter(Mandatory = $true,Position=3)] $newName ) if ($params.ContainsKey($oldName)) { @@ -78,49 +95,27 @@ function Rename-xSharePointParamValue() { return $params } -function Get-xSharePointInstalledProductVersion() { - $pathToSearch = "C:\Program Files\Common Files\microsoft shared\Web Server Extensions\*\ISAPI\Microsoft.SharePoint.dll" - $fullPath = Get-Item $pathToSearch | Sort-Object { $_.Directory } -Descending | Select-Object -First 1 - return (Get-Command $fullPath).FileVersionInfo -} - -function Get-xSharePointAssemblyVersion() { +function Remove-xSharePointUserToLocalAdmin() { [CmdletBinding()] param ( - [parameter(Mandatory = $true,Position=1)] - [string] - $PathToAssembly + [parameter(Mandatory = $true,Position=1)] [string] $UserName ) - return (Get-Command $PathToAssembly).FileVersionInfo.FileMajorPart -} -function Update-xSharePointObject() { - [CmdletBinding()] - param - ( - [parameter(Mandatory = $true,Position=1)] - [object] - $InputObject - ) - $InputObject.Update() + $domainName = $UserName.Split('\')[0] + $accountName = $UserName.Split('\')[1] + + Write-Verbose -Message "Removing $domainName\$userName from local admin group" + ([ADSI]"WinNT://$($env:computername)/Administrators,group").Remove("WinNT://$domainName/$accountName") | Out-Null } function Test-xSharePointSpecificParameters() { [CmdletBinding()] param ( - [parameter(Mandatory = $true,Position=1)] - [HashTable] - $CurrentValues, - - [parameter(Mandatory = $true,Position=2)] - [HashTable] - $DesiredValues, - - [parameter(Mandatory = $false,Position=3)] - [Array] - $ValuesToCheck + [parameter(Mandatory = $true,Position=1)] [HashTable] $CurrentValues, + [parameter(Mandatory = $true,Position=2)] [HashTable] $DesiredValues, + [parameter(Mandatory = $false,Position=3)] [Array] $ValuesToCheck ) $returnValue = $true @@ -164,9 +159,7 @@ function Test-xSharePointUserIsLocalAdmin() { [CmdletBinding()] param ( - [parameter(Mandatory = $true,Position=1)] - [string] - $UserName + [parameter(Mandatory = $true,Position=1)] [string] $UserName ) $domainName = $UserName.Split('\')[0] @@ -177,36 +170,4 @@ function Test-xSharePointUserIsLocalAdmin() { Where-Object { $_ -eq $accountName } } -function Add-xSharePointUserToLocalAdmin() { - [CmdletBinding()] - param - ( - [parameter(Mandatory = $true,Position=1)] - [string] - $UserName - ) - - $domainName = $UserName.Split('\')[0] - $accountName = $UserName.Split('\')[1] - - Write-Verbose -Message "Adding $domainName\$userName to local admin group" - ([ADSI]"WinNT://$($env:computername)/Administrators,group").Add("WinNT://$domainName/$accountName") | Out-Null -} - -function Remove-xSharePointUserToLocalAdmin() { - [CmdletBinding()] - param - ( - [parameter(Mandatory = $true,Position=1)] - [string] - $UserName - ) - - $domainName = $UserName.Split('\')[0] - $accountName = $UserName.Split('\')[1] - - Write-Verbose -Message "Removing $domainName\$userName from local admin group" - ([ADSI]"WinNT://$($env:computername)/Administrators,group").Remove("WinNT://$domainName/$accountName") | Out-Null -} - Export-ModuleMember -Function * diff --git a/Modules/xSharePoint/xSharePoint.psd1 b/Modules/xSharePoint/xSharePoint.psd1 index dc07ab2d1..7d7cf4054 100644 --- a/Modules/xSharePoint/xSharePoint.psd1 +++ b/Modules/xSharePoint/xSharePoint.psd1 @@ -63,8 +63,7 @@ Description = 'This DSC module is used to deploy and configure SharePoint Server # FormatsToProcess = @() # Modules to import as nested modules of the module specified in RootModule/ModuleToProcess -NestedModules = @("modules\xSharePoint.CacheAccounts\xSharePoint.CacheAccounts.psm1", - "modules\xSharePoint.Util\xSharePoint.Util.psm1") +NestedModules = @("modules\xSharePoint.Util\xSharePoint.Util.psm1") # Functions to export from this module FunctionsToExport = '*' @@ -73,9 +72,6 @@ FunctionsToExport = '*' CmdletsToExport = @("Invoke-xSharePointCommand", "Get-xSharePointInstalledProductVersion", "Rename-xSharePointParamValue", - "Update-xSharePointObject", - "Set-xSharePointCacheReaderPolicy", - "Set-xSharePointCacheOwnerPolicy", "Add-xSharePointUserToLocalAdmin", "Remove-xSharePointUserToLocalAdmin", "Test-xSharePointUserIsLocalAdmin", diff --git a/Modules/xSharePoint/xSharePoint.pssproj b/Modules/xSharePoint/xSharePoint.pssproj index fc4bcb504..dd7740cee 100644 --- a/Modules/xSharePoint/xSharePoint.pssproj +++ b/Modules/xSharePoint/xSharePoint.pssproj @@ -75,7 +75,6 @@ - @@ -124,7 +123,6 @@ - diff --git a/Tests/xSharePoint/xSharePoint.Util.Tests.ps1 b/Tests/xSharePoint/xSharePoint.Util.Tests.ps1 index ac91c7392..0dcfc8c62 100644 --- a/Tests/xSharePoint/xSharePoint.Util.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.Util.Tests.ps1 @@ -12,6 +12,35 @@ $ModuleName = "xSharePoint.Util" Import-Module (Join-Path $RepoRoot "Modules\xSharePoint") Describe "xSharePoint.Util" { + Context "Validate Get-xSharePointAssemblyVersion" { + It "returns the version number of a given executable" { + Get-xSharePointAssemblyVersion -PathToAssembly "C:\windows\System32\WindowsPowerShell\v1.0\powershell.exe" | Should Not Be 0 + } + } + + Context "Validate Invoke-xSharePointCommand" { + Mock Invoke-Command { return $null } -ModuleName "xSharePoint.Util" + Mock New-PSSession { return $null } -ModuleName "xSharePoint.Util" + Mock Get-PSSnapin { return $null } -ModuleName "xSharePoint.Util" + Mock Add-PSSnapin { return $null } -ModuleName "xSharePoint.Util" + + It "executes a command as the local run as user" { + Invoke-xSharePointCommand -ScriptBlock { return "value" } + } + + It "executes a command as the local run as user with additional arguments" { + Invoke-xSharePointCommand -ScriptBlock { return "value" } -Arguments @{ Something = "42" } + } + + It "executes a command as the specified InstallAccount user where it is different to the current user" { + Invoke-xSharePointCommand -ScriptBlock { return "value" } -Credential (New-Object System.Management.Automation.PSCredential ("username", (ConvertTo-SecureString "password" -AsPlainText -Force))) + } + + It "throws an exception when the run as user is the same as the InstallAccount user" { + { Invoke-xSharePointCommand -ScriptBlock { return "value" } -Credential (New-Object System.Management.Automation.PSCredential ("$($Env:USERDOMAIN)\$($Env:USERNAME)", (ConvertTo-SecureString "password" -AsPlainText -Force)))} | Should Throw + } + } + Context "Validate Test-xSharePointSpecificParameters" { It "Returns true for two identical tables" { $desired = @{ Example = "test" } diff --git a/Tests/xSharePoint/xSharePoint.xSPCacheAccounts.Tests.ps1 b/Tests/xSharePoint/xSharePoint.xSPCacheAccounts.Tests.ps1 index 7dff5d9a1..2acd07423 100644 --- a/Tests/xSharePoint/xSharePoint.xSPCacheAccounts.Tests.ps1 +++ b/Tests/xSharePoint/xSharePoint.xSPCacheAccounts.Tests.ps1 @@ -24,12 +24,18 @@ Describe "xSPCacheAccounts" { Mock Invoke-xSharePointCommand { return Invoke-Command -ScriptBlock $ScriptBlock -ArgumentList $Arguments -NoNewScope } + + try { [Microsoft.SharePoint.Administration.SPThingType] } + catch { + Add-Type @" +namespace Microsoft.SharePoint.Administration { + public enum SPPolicyRoleType { FullRead, FullControl }; +} +"@ + } Import-Module $Global:CurrentSharePointStubModule -WarningAction SilentlyContinue - Mock Set-xSharePointCacheReaderPolicy {} - Mock Set-xSharePointCacheOwnerPolicy {} - Mock Update-xSharePointObject {} - + Context "The web application specified does not exist" { Mock Get-SPWebApplication { return $null } @@ -47,9 +53,23 @@ Describe "xSPCacheAccounts" { } Context "The specified cache accounts have not been configured" { - Mock Get-SPWebApplication { return @{ - Properties = @{ } - }} + Mock Get-SPWebApplication { return New-Object Object | + Add-Member NoteProperty Properties @{} -PassThru | + Add-Member NoteProperty Policies ( + New-Object Object | + Add-Member ScriptMethod Add { return New-Object Object | + Add-Member NoteProperty PolicyRoleBindings ( + New-Object Object | + Add-Member ScriptMethod Add {} -PassThru + ) -PassThru + } -PassThru + ) -PassThru | + Add-Member NoteProperty PolicyRoles ( + New-Object Object | + Add-Member ScriptMethod GetSpecialRole { return @{} } -PassThru + ) -PassThru | + Add-Member ScriptMethod Update {} -PassThru + } It "returns empty strings from the Get method" { $results = Get-TargetResource @testParams @@ -63,20 +83,30 @@ Describe "xSPCacheAccounts" { It "Updates the accounts when set is called" { Set-TargetResource @testParams - - Assert-MockCalled Set-xSharePointCacheReaderPolicy - Assert-MockCalled Set-xSharePointCacheOwnerPolicy - Assert-MockCalled Update-xSharePointObject } } Context "The cache accounts have been configured correctly" { - Mock Get-SPWebApplication { return @{ - Properties = @{ + Mock Get-SPWebApplication { return New-Object Object | + Add-Member NoteProperty Properties @{ portalsuperuseraccount = $testParams.SuperUserAlias portalsuperreaderaccount = $testParams.SuperReaderAlias - } - }} + } -PassThru | + Add-Member NoteProperty Policies ( + New-Object Object | + Add-Member ScriptMethod Add { return New-Object Object | + Add-Member NoteProperty PolicyRoleBindings ( + New-Object Object | + Add-Member ScriptMethod Add {} -PassThru + ) -PassThru + } -PassThru + ) -PassThru | + Add-Member NoteProperty PolicyRoles ( + New-Object Object | + Add-Member ScriptMethod GetSpecialRole { return @{} } -PassThru + ) -PassThru | + Add-Member ScriptMethod Update {} -PassThru + } It "returns the values from the get method" { $results = Get-TargetResource @testParams @@ -90,12 +120,26 @@ Describe "xSPCacheAccounts" { } Context "Cache accounts have been configured, but the reader account is wrong" { - Mock Get-SPWebApplication { return @{ - Properties = @{ + Mock Get-SPWebApplication { return New-Object Object | + Add-Member NoteProperty Properties @{ portalsuperuseraccount = $testParams.SuperUserAlias portalsuperreaderaccount = "WRONG\AccountName" - } - }} + } -PassThru | + Add-Member NoteProperty Policies ( + New-Object Object | + Add-Member ScriptMethod Add { return New-Object Object | + Add-Member NoteProperty PolicyRoleBindings ( + New-Object Object | + Add-Member ScriptMethod Add {} -PassThru + ) -PassThru + } -PassThru + ) -PassThru | + Add-Member NoteProperty PolicyRoles ( + New-Object Object | + Add-Member ScriptMethod GetSpecialRole { return @{} } -PassThru + ) -PassThru | + Add-Member ScriptMethod Update {} -PassThru + } It "returns false from the test method" { Test-TargetResource @testParams | Should Be $false @@ -103,17 +147,30 @@ Describe "xSPCacheAccounts" { It "sets the correct accounts to the web app again" { Set-TargetResource @testParams - Assert-MockCalled Update-xSharePointObject } } Context "Cache accounts have been configured, but the super account is wrong" { - Mock Get-SPWebApplication { return @{ - Properties = @{ + Mock Get-SPWebApplication { return New-Object Object | + Add-Member NoteProperty Properties @{ portalsuperuseraccount = "WRONG\AccountName" portalsuperreaderaccount = $testParams.SuperReaderAlias - } - }} + } -PassThru | + Add-Member NoteProperty Policies ( + New-Object Object | + Add-Member ScriptMethod Add { return New-Object Object | + Add-Member NoteProperty PolicyRoleBindings ( + New-Object Object | + Add-Member ScriptMethod Add {} -PassThru + ) -PassThru + } -PassThru + ) -PassThru | + Add-Member NoteProperty PolicyRoles ( + New-Object Object | + Add-Member ScriptMethod GetSpecialRole { return @{} } -PassThru + ) -PassThru | + Add-Member ScriptMethod Update {} -PassThru + } It "returns false from the test method" { Test-TargetResource @testParams | Should Be $false @@ -121,7 +178,6 @@ Describe "xSPCacheAccounts" { It "sets the correct accounts to the web app again" { Set-TargetResource @testParams - Assert-MockCalled Update-xSharePointObject } } } From f2b460ad718e53831ae54ea583aff4f3517533c7 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Thu, 1 Oct 2015 10:18:59 +1000 Subject: [PATCH 29/31] Updated for 0.7 --- README.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 815c14934..8ba0bfcb2 100644 --- a/README.md +++ b/README.md @@ -68,10 +68,13 @@ Additional detailed documentation is included on the wiki on GitHub. ## Version History +### 0.7.0.0 + + * Bug fixes and stability improvements + ### 0.6.0.0 * Added support for PsDscRunAsCredential in PowerShell 5 resource use - * Expanded automated unit testing * Removed timeout loop in xSPJoinFarm in favour of WaitForAll resource in PowerShell 5 ### 0.5.0.0 From 2b417f6f7b206c941dbb138e9fa9e8353ec23518 Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Fri, 2 Oct 2015 09:47:50 +1000 Subject: [PATCH 30/31] Fix to placement of get call in set method --- .../MSFT_xSPManagedPath/MSFT_xSPManagedPath.psm1 | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) diff --git a/Modules/xSharePoint/DSCResources/MSFT_xSPManagedPath/MSFT_xSPManagedPath.psm1 b/Modules/xSharePoint/DSCResources/MSFT_xSPManagedPath/MSFT_xSPManagedPath.psm1 index 30da5d478..68df6b5b6 100644 --- a/Modules/xSharePoint/DSCResources/MSFT_xSPManagedPath/MSFT_xSPManagedPath.psm1 +++ b/Modules/xSharePoint/DSCResources/MSFT_xSPManagedPath/MSFT_xSPManagedPath.psm1 @@ -54,16 +54,12 @@ function Set-TargetResource Write-Verbose -Message "Creating the managed path $RelativeUrl in $WebAppUrl" - Invoke-xSharePointCommand -Credential $InstallAccount -Arguments $PSBoundParameters -ScriptBlock { - $params = $args[0] - - - $path = Get-TargetResource @params -ErrorAction SilentlyContinue + $path = Get-TargetResource @PSBoundParameters - if ($params.ContainsKey("InstallAccount")) { $params.Remove("InstallAccount") | Out-Null } + if ($null -eq $path) { + Invoke-xSharePointCommand -Credential $InstallAccount -Arguments $PSBoundParameters -ScriptBlock { + $params = $args[0] - if ($null -eq $path) { - $newParams = @{} if ($params.HostHeader) { $newParams.Add("HostHeader", $params.HostHeader) From ece7a801a6b43401974bddbc13a012f4b824ebbf Mon Sep 17 00:00:00 2001 From: Brian Farnhill Date: Fri, 2 Oct 2015 10:23:22 +1000 Subject: [PATCH 31/31] Added formatting test to username parameters --- .../Modules/xSharePoint.Util/xSharePoint.Util.psm1 | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 b/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 index 3bcd9be0b..7b5b5c388 100644 --- a/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 +++ b/Modules/xSharePoint/Modules/xSharePoint.Util/xSharePoint.Util.psm1 @@ -5,6 +5,10 @@ function Add-xSharePointUserToLocalAdmin() { [parameter(Mandatory = $true,Position=1)] [string] $UserName ) + if ($UserName.Contains("\") -eq $false) { + throw [Exception] "Usernames should be formatted as domain\username" + } + $domainName = $UserName.Split('\')[0] $accountName = $UserName.Split('\')[1] @@ -102,6 +106,10 @@ function Remove-xSharePointUserToLocalAdmin() { [parameter(Mandatory = $true,Position=1)] [string] $UserName ) + if ($UserName.Contains("\") -eq $false) { + throw [Exception] "Usernames should be formatted as domain\username" + } + $domainName = $UserName.Split('\')[0] $accountName = $UserName.Split('\')[1] @@ -162,6 +170,10 @@ function Test-xSharePointUserIsLocalAdmin() { [parameter(Mandatory = $true,Position=1)] [string] $UserName ) + if ($UserName.Contains("\") -eq $false) { + throw [Exception] "Usernames should be formatted as domain\username" + } + $domainName = $UserName.Split('\')[0] $accountName = $UserName.Split('\')[1]