diff --git a/DSCResources/MSFT_xVirtualMemory/MSFT_xVirtualMemory.psm1 b/DSCResources/MSFT_xVirtualMemory/MSFT_xVirtualMemory.psm1 new file mode 100644 index 00000000..e00a1b69 --- /dev/null +++ b/DSCResources/MSFT_xVirtualMemory/MSFT_xVirtualMemory.psm1 @@ -0,0 +1,385 @@ +<# +.SYNOPSIS + Returns the current state of the virtual memory configuration +.PARAMETER Drive + The drive for which the virtual memory configuration needs to be returned +.PARAMETER Type + The type of the virtual memory configuration +#> +function Get-TargetResource +{ + [CmdletBinding()] + [OutputType([System.Collections.Hashtable])] + param + ( + [parameter(Mandatory = $true)] + [System.String] + $Drive, + + [ValidateSet("AutoManagePagingFile", "CustomSize", "SystemManagedSize", "NoPagingFile")] + [parameter(Mandatory = $true)] + [System.String] + $Type + ) + + Write-Verbose -Message 'Getting current page file settings' + + $returnValue = @{ + Drive = [string]::Empty + Type = [string]::Empty + InitialSize = 0 + MaximumSize = 0 + } + + [bool] $isSystemManaged = (Get-CimInstance -ClassName Win32_ComputerSystem).AutomaticManagedPagefile + + if ($isSystemManaged) + { + $returnValue.Type = 'AutoManagePagingFile' + return $returnValue + } + + $driveItem = [System.IO.DriveInfo] $Drive + + Write-Verbose -Message "Pagefile was not automatically managed. Retrieving detailed page file settings with query Select * from Win32_PageFileSetting where SettingID='pagefile.sys @ $($driveItem.Name.Substring(0,2))'" + + # Find existing page file settings by drive letter + $virtualMemoryInstance = Get-CimInstance -Namespace root\cimv2 -Query "Select * from Win32_PageFileSetting where SettingID='pagefile.sys @ $($driveItem.Name.Substring(0,2))'" + + if (-not $virtualMemoryInstance) + { + $returnValue.Type = 'NoPagingFile' + return $returnValue + } + + if ($virtualMemoryInstance.InitialSize -eq 0 -and $virtualMemoryInstance.MaximumSize -eq 0) + { + $returnValue.Type = 'SystemManagedSize' + } + else + { + $returnValue.Type = "CustomSize" + } + + $returnValue.Drive = $virtualMemoryInstance.Name.Substring(0, 3) + $returnValue.InitialSize = $virtualMemoryInstance.InitialSize + $returnValue.MaximumSize = $virtualMemoryInstance.MaximumSize + + $returnValue +} + +<# +.SYNOPSIS + Sets the virtual memory settings based on the parameters supplied +.PARAMETER Drive + The drive for which the virtual memory configuration should be set. +.PARAMETER Type + The paging type. When set to AutoManagePagingFile, drive letters are ignored +.PARAMETER InitialSize + The initial page file size in megabyte +.PARAMETER MaximumSize + The maximum page file size in megabyte. May not be smaller than InitialSize +#> +function Set-TargetResource +{ + [CmdletBinding()] + param + ( + [parameter(Mandatory = $true)] + [System.String] + $Drive, + + [ValidateSet("AutoManagePagingFile", "CustomSize", "SystemManagedSize", "NoPagingFile")] + [parameter(Mandatory = $true)] + [System.String] + $Type, + + [System.Int64] + $InitialSize, + + [System.Int64] + $MaximumSize + ) + + Write-Verbose -Message 'Setting page file' + + $SystemInfo = Get-CimInstance -Class Win32_ComputerSystem + + switch ($Type) + { + "AutoManagePagingFile" + { + $setParams = @{ + Namespace = 'root\cimv2' + Query = 'Select * from Win32_ComputerSystem' + Property = @{AutomaticManagedPageFile = $true} + } + + Write-Verbose -Message 'Enabling AutoManagePagingFile' + + Set-CimInstance @setParams + $global:DSCMachineStatus = 1 + break + } + "CustomSize" + { + if ($SystemInfo.AutomaticManagedPageFile) + { + # First set AutomaticManagedPageFile to $false to be able to set a custom one later + + $setParams = @{ + Namespace = 'root\cimv2' + Query = 'Select * from Win32_ComputerSystem' + Property = @{AutomaticManagedPageFile = $false} + } + + Write-Verbose -Message 'Disabling AutoManagePagingFile' + + Set-CimInstance @setParams + } + + $driveInfo = [System.IO.DriveInfo] $Drive + if (-not $driveInfo.IsReady) + { + throw "Drive $($driveInfo.Name) is not ready. Please ensure that the drive exists and is available" + } + + $pageFileName = Join-Path -Path $driveInfo.Name -ChildPath 'pagefile.sys' + + Write-Verbose -Message ('Checking if a paging file already exists at {0}' -f $pageFileName) + $existingPageFileSetting = Get-CimInstance -Namespace root\cimv2 -Query "Select * from Win32_PageFileSetting where SettingID='pagefile.sys @ $($driveInfo.Name.Substring(0,2))'" + if (-not $existingPageFileSetting) + { + [void] (New-CimInstance -Namespace 'root\cimv2' -ClassName 'Win32_PageFileSetting' -Property @{Name = $pageFileName}) + } + + <# + New-CimInstance does not support properties InitialSize and MaximumSize. Therefore, create + a New-CimInstance with the page file name only if it does not exist and Set-CimInstance on the instance + #> + $setParams = @{ + Namespace = 'root\cimv2' + Query = "Select * from Win32_PageFileSetting where SettingID='pagefile.sys @ $($driveInfo.Name.Substring(0,2))'" + Property = @{ + InitialSize = $InitialSize + MaximumSize = $MaximumSize + } + } + + Write-Verbose -Message ("Setting page file to {0}. Initial size {1}MB, maximum size {2}MB" -f $pageFileName, $InitialSize, $MaximumSize) + + Set-CimInstance @setParams + $global:DSCMachineStatus = 1 + break + } + "SystemManagedSize" + { + if ($SystemInfo.AutomaticManagedPageFile) + { + $setParams = @{ + Namespace = 'root\cimv2' + Query = 'Select * from Win32_ComputerSystem' + Property = @{AutomaticManagedPageFile = $false} + } + + Write-Verbose -Message 'Disabling AutoManagePagingFile' + + Set-CimInstance @setParams + } + + $driveInfo = [System.IO.DriveInfo] $Drive + if (-not $driveInfo.IsReady) + { + throw "Drive $($driveInfo.Name) is not ready. Please ensure that the drive exists and is available" + } + + $pageFileName = Join-Path -Path $driveInfo.Name -ChildPath 'pagefile.sys' + + Write-Verbose -Message ('Checking if a paging file already exists at {0}' -f $pageFileName) + + $existingPageFileSetting = Get-CimInstance -Namespace root\cimv2 -Query "Select * from Win32_PageFileSetting where SettingID='pagefile.sys @ $($driveInfo.Name.Substring(0,2))'" + if (-not $existingPageFileSetting) + { + [void] (New-CimInstance -Namespace 'root\cimv2' -ClassName 'Win32_PageFileSetting' -Property @{Name = $pageFileName}) + } + + + $setParams = @{ + Namespace = 'root\cimv2' + Query = "Select * from Win32_PageFileSetting where SettingID='pagefile.sys @ $($driveInfo.Name.Substring(0,2))'" + Property = @{ + InitialSize = 0 + MaximumSize = 0 + } + } + + Write-Verbose -Message "Enabling system-managed page file on $pageFileName" + + Set-CimInstance @setParams + $global:DSCMachineStatus = 1 + break + } + "NoPagingFile" + { + if ($SystemInfo.AutomaticManagedPageFile) + { + $setParams = @{ + Namespace = 'root\cimv2' + Query = 'Select * from Win32_ComputerSystem' + Property = @{AutomaticManagedPageFile = $false} + } + + Set-CimInstance @setParams + } + + $driveInfo = [System.IO.DriveInfo] $Drive + if (-not $driveInfo.IsReady) + { + throw "Drive $($driveInfo.Name) is not ready. Please ensure that the drive exists and is available" + } + + $PageFile = Get-CimInstance -Class Win32_PageFileSetting -Filter "SettingID='pagefile.sys @ $($driveInfo.Name.Substring(0,2))'" + + $existingPageFileSetting = Get-CimInstance -Namespace root\cimv2 -Query "Select * from Win32_PageFileSetting where SettingID='pagefile.sys @ $($driveInfo.Name.Substring(0,2))'" + if ($existingPageFileSetting) + { + Write-Verbose -Message "Removing existing page file $($existingPageFileSetting.Name)" + Remove-CimInstance -InputObject $existingPageFileSetting + $global:DSCMachineStatus = 1 + } + + Write-Verbose -Message "Disabled page file for drive $Drive" + + break + } + default + { + throw "A wrong type '$Type' has been selected." + } + } +} + +<# +.SYNOPSIS + Tests if virtual memory settings need to be applied based on the parameters supplied +.PARAMETER Drive + The drive letter that should be tested +.PARAMETER Type + The type of the virtual memory configuration +.PARAMETER InitialSize + The initial page file size in megabyte +.PARAMETER MaximumSize + The maximum page file size in megabyte +#> +function Test-TargetResource +{ + [CmdletBinding()] + [OutputType([System.Boolean])] + param + ( + [parameter(Mandatory = $true)] + [System.String] + $Drive, + + [ValidateSet("AutoManagePagingFile", "CustomSize", "SystemManagedSize", "NoPagingFile")] + [parameter(Mandatory = $true)] + [System.String] + $Type, + + [System.Int64] + $InitialSize, + + [System.Int64] + $MaximumSize + ) + + $SystemInfo = Get-CimInstance -Class Win32_ComputerSystem + $result = $false + + switch ($Type) + { + "AutoManagePagingFile" + { + $result = $SystemInfo.AutomaticManagedPagefile + break + } + "CustomSize" + { + if ($SystemInfo.AutomaticManagedPageFile) + { + $result = $false + break + } + + $driveInfo = [System.IO.DriveInfo] $Drive + $PageFile = Get-CimInstance -Class Win32_PageFileSetting -Filter "SettingID='pagefile.sys @ $($driveInfo.Name.Substring(0,2))'" + if (-not $PageFile) + { + $result = $false + break + } + + if (-not ($PageFile.InitialSize -eq $InitialSize -and $PageFile.MaximumSize -eq $MaximumSize)) + { + $result = $false + break + } + + $result = $true + break + } + "SystemManagedSize" + { + if ($SystemInfo.AutomaticManagedPageFile) + { + $result = $false + break + } + + $driveInfo = [System.IO.DriveInfo] $Drive + $PageFile = Get-CimInstance -Class Win32_PageFileSetting -Filter "SettingID='pagefile.sys @ $($driveInfo.Name.Substring(0,2))'" + if (-not $PageFile) + { + $result = $false + break + } + + if (-not ($PageFile.InitialSize -eq 0 -and $PageFile.MaximumSize -eq 0)) + { + $result = $false + break + } + + $result = $true + break + } + "NoPagingFile" + { + if ($SystemInfo.AutomaticManagedPageFile) + { + $result = $false + break + } + + $driveInfo = [System.IO.DriveInfo] $Drive + $PageFile = Get-CimInstance -Class Win32_PageFileSetting -Filter "SettingID='pagefile.sys @ $($driveInfo.Name.Substring(0,2))'" + + if ($PageFile) + { + $result = $false + break + } + + $result = $true + break + } + default + { + break + } + } + + $result +} + +Export-ModuleMember -Function *-TargetResource diff --git a/DSCResources/MSFT_xVirtualMemory/MSFT_xVirtualMemory.schema.mof b/DSCResources/MSFT_xVirtualMemory/MSFT_xVirtualMemory.schema.mof new file mode 100644 index 00000000..38651f9d --- /dev/null +++ b/DSCResources/MSFT_xVirtualMemory/MSFT_xVirtualMemory.schema.mof @@ -0,0 +1,10 @@ + +[ClassVersion("1.0.0.0"), FriendlyName("xVirtualMemory")] +class MSFT_xVirtualMemory : OMI_BaseResource +{ + [Key, Description("The drive letter for which paging settings should be set. Can be letter only, letter and colon or letter with colon and trailing slash.")] String Drive; + [Key, Description("The type of the paging setting to use. If set to AutoManagePagingFile, the drive letter will be ignored. If set to SystemManagedSize, the values for InitialSize and MaximumSize will be ignored"), ValueMap{"AutoManagePagingFile","CustomSize","SystemManagedSize","NoPagingFile"}, Values{"AutoManagePagingFile","CustomSize","SystemManagedSize","NoPagingFile"}] String Type; + [Write, Description("The initial size of the page file in Megabyte")] Sint64 InitialSize; + [Write, Description("The maximum size of the page file in Megabyte")] Sint64 MaximumSize; +}; + diff --git a/Examples/Sample_xVirtualMemory.ps1 b/Examples/Sample_xVirtualMemory.ps1 new file mode 100644 index 00000000..33d14451 --- /dev/null +++ b/Examples/Sample_xVirtualMemory.ps1 @@ -0,0 +1,31 @@ +<# +.SYNOPSIS + Example to set the paging file +.DESCRIPTION + Example script that sets the paging file to reside on drive C with the custom size 2048MB +#> +configuration Sample_xVirtualMemory +{ + param + ( + [Parameter()] + [String[]] + $NodeName = 'localhost' + ) + + Import-DSCResource -ModuleName xComputerManagement + + node $NodeName + { + xVirtualMemory pagingSettings + { + Type = "CustomSize" + Drive = "C" + InitialSize = "2048" + MaximumSize = "2048" + } + } +} + +Sample_xVirtualMemory +Start-DscConfiguration -Path Sample_xVirtualMemory -Wait -verbose -Force diff --git a/README.md b/README.md index e0028faa..5bb07b08 100644 --- a/README.md +++ b/README.md @@ -76,11 +76,25 @@ xPowerPlan resource has following properties: * IsSingleInstance: Specifies the resource is a single instance, the value must be 'Yes'. * Name: The name of the power plan to activate. + +## xVirtualMemory + +xVirtualMemory resource is used to set the properties of the paging file on the local computer. +xVirtualMemory has the following properties: + +* Type: The type of the paging settings, mandatory, out of "AutoManagePagingFile","CustomSize","SystemManagedSize","NoPagingFile" +* Drive: The drive to enable paging on, mandatory. Ignored for "AutoManagePagingFile" +* InitialSize: The initial size in MB of the paging file. Ignored for Type "AutoManagePagingFile" and "SystemManagedSize" +* MaximumSize: The maximum size in MB of the paging file. Ignored for Type "AutoManagePagingFile" and "SystemManagedSize" ## Versions ### Unreleased +### 1.10.0.0 +* Added resources + - xVirtualMemory + ### 1.9.0.0 * Added resources - xPowerPlan diff --git a/Tests/Integration/MSFT_xVirtualMemory.Config.ps1 b/Tests/Integration/MSFT_xVirtualMemory.Config.ps1 new file mode 100644 index 00000000..8edd95d8 --- /dev/null +++ b/Tests/Integration/MSFT_xVirtualMemory.Config.ps1 @@ -0,0 +1,49 @@ +Configuration setToAuto +{ + Import-DscResource -ModuleName xComputerManagement + node "localhost" { + xVirtualMemory vMem + { + Type = 'AutoManagePagingFile' + Drive = 'C' + } + } +} + +Configuration setToCustom +{ + Import-DscResource -ModuleName xComputerManagement + node "localhost" { + xVirtualMemory vMem + { + Type = 'CustomSize' + Drive = 'C' + InitialSize = 128 + MaximumSize = 1024 + } + } +} + +Configuration setToSystemManaged +{ + Import-DscResource -ModuleName xComputerManagement + node "localhost" { + xVirtualMemory vMem + { + Type = 'SystemManagedSize' + Drive = 'C' + } + } +} + +Configuration setToNone +{ + Import-DscResource -ModuleName xComputerManagement + node "localhost" { + xVirtualMemory vMem + { + Type = 'NoPagingFile' + Drive = 'C' + } + } +} diff --git a/Tests/Integration/MSFT_xVirtualMemory.Integration.Tests.ps1 b/Tests/Integration/MSFT_xVirtualMemory.Integration.Tests.ps1 new file mode 100644 index 00000000..b03eaa5c --- /dev/null +++ b/Tests/Integration/MSFT_xVirtualMemory.Integration.Tests.ps1 @@ -0,0 +1,127 @@ +$script:DSCModuleName = 'xComputerManagement' +$script:DSCResourceName = 'MSFT_xVirtualMemory' + +#region HEADER +# Integration Test Template Version: 1.1.1 +[String] $script:moduleRoot = Split-Path -Parent (Split-Path -Parent $PSScriptRoot) +if ( (-not (Test-Path -Path (Join-Path -Path $script:moduleRoot -ChildPath 'DSCResource.Tests'))) -or ` + (-not (Test-Path -Path (Join-Path -Path $script:moduleRoot -ChildPath 'DSCResource.Tests\TestHelper.psm1'))) ) +{ + & git @('clone','https://github.com/PowerShell/DscResource.Tests.git',(Join-Path -Path $script:moduleRoot -ChildPath '\DSCResource.Tests\')) +} + +Import-Module -Name (Join-Path -Path $script:moduleRoot -ChildPath (Join-Path -Path 'DSCResource.Tests' -ChildPath 'TestHelper.psm1')) -Force +$TestEnvironment = Initialize-TestEnvironment ` + -DSCModuleName $script:DSCModuleName ` + -DSCResourceName $script:DSCResourceName ` + -TestType Integration + +#endregion + +# Using try/finally to always cleanup. +try +{ + #region Integration Tests + $configFile = Join-Path -Path $PSScriptRoot -ChildPath "$($script:DSCResourceName).config.ps1" + . $configFile + + Describe "$($script:DSCResourceName)_Integration" { + + Context "Set page file to automatically managed" { + $CurrentConfig = "setToAuto" + $ConfigDir = (Join-Path -Path $TestDrive -ChildPath $CurrentConfig) + $ConfigMof = (Join-Path -Path $ConfigDir -ChildPath "localhost.mof") + + It "should compile a MOF file without error" { + { + . $CurrentConfig -OutputPath $ConfigDir + } | Should Not Throw + } + + It "should apply the MOF correctly" { + { + Start-DscConfiguration -Path $ConfigDir -Wait -Verbose -Force + } | Should Not Throw + } + + It "should return a compliant state after being applied" { + (Test-DscConfiguration -ReferenceConfiguration $ConfigMof -Verbose).InDesiredState | Should be $true + } + } + + Context "Set page file to custom size" { + $CurrentConfig = "setToCustom" + $ConfigDir = (Join-Path -Path $TestDrive -ChildPath $CurrentConfig) + $ConfigMof = (Join-Path -Path $ConfigDir -ChildPath "localhost.mof") + + It "should compile a MOF file without error" { + { + . $CurrentConfig -OutputPath $ConfigDir + } | Should Not Throw + } + + It "should apply the MOF correctly" { + { + Start-DscConfiguration -Path $ConfigDir -Wait -Verbose -Force + } | Should Not Throw + } + + It "should return a compliant state after being applied" { + (Test-DscConfiguration -ReferenceConfiguration $ConfigMof -Verbose).InDesiredState | Should be $true + } + } + + Context "Set page file to system managed" { + $CurrentConfig = "setToSystemManaged" + $ConfigDir = (Join-Path -Path $TestDrive -ChildPath $CurrentConfig) + $ConfigMof = (Join-Path -Path $ConfigDir -ChildPath "localhost.mof") + + It "should compile a MOF file without error" { + { + . $CurrentConfig -OutputPath $ConfigDir + } | Should Not Throw + } + + It "should apply the MOF correctly" { + { + Start-DscConfiguration -Path $ConfigDir -Wait -Verbose -Force + } | Should Not Throw + } + + It "should return a compliant state after being applied" { + (Test-DscConfiguration -ReferenceConfiguration $ConfigMof -Verbose).InDesiredState | Should be $true + } + } + + Context "Set page file to none" { + $CurrentConfig = "setToNone" + $ConfigDir = (Join-Path -Path $TestDrive -ChildPath $CurrentConfig) + $ConfigMof = (Join-Path -Path $ConfigDir -ChildPath "localhost.mof") + + It "should compile a MOF file without error" { + { + . $CurrentConfig -OutputPath $ConfigDir + } | Should Not Throw + } + + It "should apply the MOF correctly" { + { + Start-DscConfiguration -Path $ConfigDir -Wait -Verbose -Force + } | Should Not Throw + } + + It "should return a compliant state after being applied" { + (Test-DscConfiguration -ReferenceConfiguration $ConfigMof -Verbose).InDesiredState | Should be $true + } + } + } +} +finally +{ + #region FOOTER + + Restore-TestEnvironment -TestEnvironment $TestEnvironment + + #endregion +} + diff --git a/Tests/Unit/MSFT_xComputer.Tests.ps1 b/Tests/Unit/MSFT_xComputer.Tests.ps1 index b3258249..89b7904e 100644 --- a/Tests/Unit/MSFT_xComputer.Tests.ps1 +++ b/Tests/Unit/MSFT_xComputer.Tests.ps1 @@ -130,7 +130,7 @@ try It 'Should return a hashtable containing Name, DomainName, JoinOU, CurrentOU, Credential, UnjoinCredential and WorkGroupName' { $Result = Get-TargetResource -Name $env:COMPUTERNAME $Result.GetType().Fullname | Should Be 'System.Collections.Hashtable' - $Result.Keys | Should Be @('Name', 'DomainName', 'JoinOU', 'CurrentOU', 'Credential', 'UnjoinCredential', 'WorkGroupName') + $Result.Keys | Sort-Object | Should Be @('Credential', 'CurrentOU', 'DomainName', 'JoinOU', 'Name', 'UnjoinCredential', 'WorkGroupName') } It 'Throws if name is to long' { {Get-TargetResource -Name "ThisNameIsTooLong"} | Should Throw diff --git a/Tests/Unit/MSFT_xVirtualMemory.Tests.ps1 b/Tests/Unit/MSFT_xVirtualMemory.Tests.ps1 new file mode 100644 index 00000000..d4e55081 --- /dev/null +++ b/Tests/Unit/MSFT_xVirtualMemory.Tests.ps1 @@ -0,0 +1,200 @@ +#region HEADER +$script:DSCModuleName = 'xComputerManagement' +$script:DSCResourceName = 'MSFT_xVirtualMemory' + +# Unit Test Template Version: 1.2.0 +$script:moduleRoot = Split-Path -Parent (Split-Path -Parent $PSScriptRoot) +if ( (-not (Test-Path -Path (Join-Path -Path $script:moduleRoot -ChildPath 'DSCResource.Tests'))) -or ` + (-not (Test-Path -Path (Join-Path -Path $script:moduleRoot -ChildPath 'DSCResource.Tests\TestHelper.psm1'))) ) { + & git @('clone','https://github.com/PowerShell/DscResource.Tests.git',(Join-Path -Path $script:moduleRoot -ChildPath '\DSCResource.Tests\')) +} + +Import-Module -Name (Join-Path -Path $script:moduleRoot -ChildPath (Join-Path -Path 'DSCResource.Tests' -ChildPath 'TestHelper.psm1')) -Force + +$TestEnvironment = Initialize-TestEnvironment ` + -DSCModuleName $script:DSCModuleName ` + -DSCResourceName $script:DSCResourceName ` + -TestType Unit + +#endregion HEADER + +function Invoke-TestSetup { +} + +function Invoke-TestCleanup { + Restore-TestEnvironment -TestEnvironment $TestEnvironment +} + +# Begin Testing +try { + Invoke-TestSetup + + InModuleScope 'MSFT_xVirtualMemory' { + + Describe "$($script:DSCResourceName)\Get-TargetResource" { + + BeforeEach { + $testParameters = @{ + Drive = 'D:' + Type = 'CustomSize' + } + } + + Context 'When the system is in the desired present state' { + BeforeEach { + Mock -CommandName Get-CimInstance -MockWith { + [PSObject] @{ AutomaticManagedPageFile = $false; Name = 'D:\pagefile.sys' } + } -ModuleName $script:DSCResourceName -Verifiable + } + + It 'It should return the same values as passed as parameters' { + $result = Get-TargetResource @testParameters + $result.Type | Should Be $testParameters.Type + $result.Drive | Should Be ([System.IO.DriveInfo]$testParameters.Drive).Name + } + } + + Context 'When the system is not in the desired present state' { + BeforeEach { + Mock -CommandName Get-CimInstance -MockWith { + [PSObject] @{ + InitialSize = 0 + MaximumSize = 0 + Name = "C:\pagefile.sys" + } + } -ModuleName $script:DSCResourceName -Verifiable + } + + It 'It should not return a valid type' { + $result = Get-TargetResource @testParameters + $result.Type | Should Not Be $testParameters.Type + } + + It 'It should not return a valid drive letter' { + $result = Get-TargetResource @testParameters + $result.Drive | Should Not Be ([System.IO.DriveInfo]$testParameters.Drive).Name + } + } + + Assert-VerifiableMocks + } + + Describe "$($script:DSCResourceName)\Set-TargetResource" { + + Context 'When the system is not in the desired state' { + BeforeEach { + $testParameters = @{ + Drive = 'C:' + Type = 'CustomSize' + InitialSize = 0 + MaximumSize = 1337 + } + } + Mock -CommandName Set-CimInstance -MockWith {} -ModuleName $script:DSCResourceName -Verifiable + Mock -CommandName New-CimInstance -MockWith {} -ModuleName $script:DSCResourceName -Verifiable + Mock -CommandName Remove-CimInstance -MockWith {} -ModuleName $script:DSCResourceName -Verifiable + Mock -CommandName Get-CimInstance -MockWith {} -ModuleName $script:DSCResourceName -Verifiable + + It 'Should call the mocked function Set-CimInstance exactly once' { + Set-TargetResource @testParameters + + Assert-MockCalled -CommandName Set-CimInstance -Exactly -Times 1 -Scope It + } + } + + + context 'When an exception is expected' { + Mock -CommandName Set-CimInstance -MockWith {} -ModuleName $script:DSCResourceName -Verifiable + Mock -CommandName New-CimInstance -MockWith {} -ModuleName $script:DSCResourceName -Verifiable + Mock -CommandName Remove-CimInstance -MockWith {} -ModuleName $script:DSCResourceName -Verifiable + Mock -CommandName Get-CimInstance -MockWith { + [PSObject] @{ + InitialSize = 0 + MaximumSize = 1338 + Name = "D:\pagefile.sys" + AutomaticManagedPageFile = $false + } + } + + $testParameters = @{ + Drive = 'abc' + Type = 'CustomSize' + InitialSize = 0 + MaximumSize = 1337 + } + It 'Should throw if no valid drive letter has been used' { + { Set-TargetResource @testParameters } | Should Throw + } + + $testParameters = @{ + Drive = 'N:' + Type = 'CustomSize' + InitialSize = 0 + MaximumSize = 1337 + } + It 'Should throw if the drive is not ready' { + { Set-TargetResource @testParameters } | Should Throw + } + } + + Assert-VerifiableMocks + } + + Describe "$($script:DSCResourceName)\Test-TargetResource" { + Context 'When a True or False is expected' { + BeforeEach { + $testParameters = @{ + Drive = 'D:' + Type = 'CustomSize' + InitialSize = 0 + MaximumSize = 1337 + } + } + + $pageFileObject = [PSObject] @{ + InitialSize = 0 + MaximumSize = 1338 + Name = "D:\pagefile.sys" + AutomaticManagedPageFile = $false + } + + Mock -CommandName Get-CimInstance -MockWith { + $pageFileObject.MaximumSize = 1337 + $pageFileObject + } + It 'Should return True if the input matches the actual values' { + Test-TargetResource @testParameters | Should Be $true + } + + Mock -CommandName Get-CimInstance -MockWith { + $pageFileObject.MaximumSize = 1337 + $pageFileObject.AutomaticManagedPageFile = $true + $pageFileObject + } + It 'Should return False if the type is wrong' { + Test-TargetResource @testParameters | Should Be $false + } + + Mock -CommandName Get-CimInstance -MockWith { + $pageFileObject.MaximumSize = 1338 + $pageFileObject + } + It 'Should return False if InitialSize and/or MaximumSize do not match' { + Test-TargetResource @testParameters | Should Be $false + } + + Mock -CommandName Get-CimInstance -MockWith { + # In this case Get-CimInstance returns an empty object + } + It 'Should return False if Name does not match' { + Test-TargetResource @testParameters | Should Be $false + } + + } + } + } +} +finally { + Invoke-TestCleanup +} + diff --git a/xComputerManagement.psd1 b/xComputerManagement.psd1 index ea995901..5b4d796a 100644 --- a/xComputerManagement.psd1 +++ b/xComputerManagement.psd1 @@ -1,6 +1,6 @@ @{ # Version number of this module. -ModuleVersion = '1.9.0.0' +ModuleVersion = '1.10.0.0' # ID used to uniquely identify this module GUID = 'B5004952-489E-43EA-999C-F16A25355B89' @@ -50,7 +50,7 @@ PrivateData = @{ # ReleaseNotes of this module ReleaseNotes = '* Added resources - - xPowerPlan + - xVirtualMemory ' @@ -61,3 +61,4 @@ PrivateData = @{ +