5 ConvertFrom-StringData @'
6 SetScriptWhatIfMessage=Executing the SetScript with the user supplied credential
7 InValidResultFromGetScriptError=Failure to get the results from the script in a hash table format.
8 InValidResultFromTestScriptError=Failure to get a valid result from the execution of TestScript. The Test script should return True or False.
9 ScriptBlockProviderScriptExecutionFailureError=Failure to successfully execute the script.
10 GetTargetResourceStartVerboseMessage=Begin executing Get Script.
11 GetTargetResourceEndVerboseMessage=End executing Get Script.
12 SetTargetResourceStartVerboseMessage=Begin executing Set Script.
13 SetTargetResourceEndVerboseMessage=End executing Set Script.
14 TestTargetResourceStartVerboseMessage=Begin executing Test Script.
15 TestTargetResourceEndVerboseMessage=End executing Test Script.
16 ExecutingScriptMessage=Executing Script: {0}
17 ResourceNotAllowedWhenDeviceGuardIsEnabled='Script' resource from 'PSDesiredStateConfiguration' module is not supported when Device Guard is enabled. Please use 'Script' resource published by PSDscResources module from PowerShell Gallery.
18 WarningRunningScriptResourceInFullLanguageMode=Running 'Script' resource in FullLanguage mode as Device Guard is enabled in 'Audit' mode.
22 $GenericMessageEventID=0x1005;
23 $ClassName="MSFT_ScriptResource"
26 Import-LocalizedData LocalizedData -filename MSFT_ScriptResourceStrings
29 # The Get-TargetResource cmdlet is used to fetch the desired state of the DSC managed node through a powershell script.
30 # This cmdlet executes the user supplied script (i.e., the script is responsible for validating the desired state of the
31 # DSC managed node). The result of the script execution is in the form of a hashtable containing all the inormation
32 # gathered from the GetScript execution.
33 function Get-TargetResource
38 [parameter(Mandatory = $true)]
39 [ValidateNotNullOrEmpty()]
43 [parameter(Mandatory = $true)]
44 [ValidateNotNullOrEmpty()]
47 [parameter(Mandatory = $true)]
48 [ValidateNotNullOrEmpty()]
52 [Parameter(Mandatory=$false)]
53 [System.Management.Automation.PSCredential]
57 # Inbox 'Script' resource is not allowed to execute if Device Guard is enabled.
58 # Check and throw terminating error if Device Guard is enabled.
59 CheckDeviceGuardStatus
61 $getTargetResourceResult = $null;
63 $getTargetResourceStartVerboseMessage = $($LocalizedData.GetTargetResourceStartVerboseMessage);
64 Write-Debug -Message $getTargetResourceStartVerboseMessage;
66 $script = [ScriptBlock]::Create($GetScript);
67 $parameters = $psboundparameters.Remove("GetScript");
68 $psboundparameters.Add("ScriptBlock", $script);
70 $parameters = $psboundparameters.Remove("SetScript");
71 $parameters = $psboundparameters.Remove("TestScript");
73 $scriptResult = ScriptExecutionHelper @psboundparameters;
75 $scriptResultAsErrorRescord = $scriptResult -as [System.Management.Automation.ErrorRecord]
76 if($null -ne $scriptResultAsErrorRescord)
78 $PSCmdlet.ThrowTerminatingError($scriptResultAsErrorRescord);
81 $scriptResultAsHasTable = $scriptResult -as [hashtable]
83 if($null -ne $scriptResultAsHasTable)
85 $getTargetResourceResult = $scriptResultAsHasTable ;
89 # Error message indicating failure to get valid hashtable as the result of the Get script execution.
90 $errorId = "InValidResultFromGetScript";
91 $errorCategory = [System.Management.Automation.ErrorCategory]::InvalidResult;
92 $exception = New-Object System.InvalidOperationException $($LocalizedData.InValidResultFromGetScriptError);
93 $errorRecord = New-Object System.Management.Automation.ErrorRecord $exception, $errorId, $errorCategory, $null
95 $PSCmdlet.ThrowTerminatingError($errorRecord);
98 $getTargetResourceEndVerboseMessage = $($LocalizedData.GetTargetResourceEndVerboseMessage);
99 Write-Debug -Message $getTargetResourceEndVerboseMessage;
101 $getTargetResourceResult;
105 # The Set-TargetResource cmdlet is used to Set the desired state of the DSC managed node through a powershell script.
106 # The method executes the user supplied script (i.e., the script is responsible for validating the desired state of the
107 # DSC managed node). If the DSC managed node requires a restart either during or after the execution of the SetScript,
108 # the SetScript notifies the PS Infrasturcure by setting the variable $DSCMachineStatus.IsRestartRequired to $true.
109 function Set-TargetResource
111 [CmdletBinding(SupportsShouldProcess=$true)]
114 [parameter(Mandatory = $true)]
115 [ValidateNotNullOrEmpty()]
119 [parameter(Mandatory = $true)]
120 [ValidateNotNullOrEmpty()]
124 [Parameter(Mandatory=$false)]
125 [System.Management.Automation.PSCredential]
128 [parameter(Mandatory = $true)]
129 [ValidateNotNullOrEmpty()]
135 # Inbox 'Script' resource is not allowed to execute if Device Guard is enabled.
136 # Check and throw terminating error if Device Guard is enabled.
137 CheckDeviceGuardStatus
139 $setscriptmessage = '$SetScript:' + $SetScript
140 $testscriptmessage = '$TestScript:' + $TestScript
141 if ($pscmdlet.ShouldProcess($($LocalizedData.SetScriptWhatIfMessage)))
143 $setTargetResourceStartVerboseMessage = $($LocalizedData.SetTargetResourceStartVerboseMessage);
144 Write-Debug -Message $setTargetResourceStartVerboseMessage;
146 $script = [ScriptBlock]::Create($SetScript);
147 $parameters = $psboundparameters.Remove("SetScript");
148 $psboundparameters.Add("ScriptBlock", $script);
150 $parameters = $psboundparameters.Remove("GetScript");
151 $parameters = $psboundparameters.Remove("TestScript");
153 $scriptResult = ScriptExecutionHelper @psboundparameters ;
155 $scriptResultAsErrorRescord = $scriptResult -as [System.Management.Automation.ErrorRecord]
156 if($null -ne $scriptResultAsErrorRescord)
158 $PSCmdlet.ThrowTerminatingError($scriptResultAsErrorRescord);
161 $setTargetResourceEndVerboseMessage = $($LocalizedData.SetTargetResourceEndVerboseMessage);
162 Write-Debug -Message $setTargetResourceEndVerboseMessage;
167 # The Test-TargetResource cmdlet is used to validate the desired state of the DSC managed node through a powershell script.
168 # The method executes the user supplied script (i.e., the script is responsible for validating the desired state of the
169 # DSC managed node). The result of the script execution should be true if the DSC managed machine is in the desired state
170 # or else false should be returned.
171 function Test-TargetResource
175 [parameter(Mandatory = $true)]
176 [ValidateNotNullOrEmpty()]
180 [parameter(Mandatory = $true)]
181 [ValidateNotNullOrEmpty()]
184 [parameter(Mandatory = $true)]
185 [ValidateNotNullOrEmpty()]
188 [Parameter(Mandatory=$false)]
189 [System.Management.Automation.PSCredential]
193 # Inbox 'Script' resource is not allowed to execute if Device Guard is enabled.
194 # Check and throw terminating error if Device Guard is enabled.
195 CheckDeviceGuardStatus
197 $testTargetResourceResult = $false;
199 $testTargetResourceStartVerboseMessage = $($LocalizedData.TestTargetResourceStartVerboseMessage);
200 Write-Debug -Message $testTargetResourceStartVerboseMessage;
202 $script = [ScriptBlock]::Create($TestScript);
203 $parameters = $psboundparameters.Remove("TestScript");
204 $psboundparameters.Add("ScriptBlock", $script);
206 $parameters = $psboundparameters.Remove("GetScript");
207 $parameters = $psboundparameters.Remove("SetScript");
209 $scriptResult = ScriptExecutionHelper @psboundparameters ;
211 $scriptResultAsErrorRescord = $scriptResult -as [System.Management.Automation.ErrorRecord]
212 if($null -ne $scriptResultAsErrorRescord)
214 $PSCmdlet.ThrowTerminatingError($scriptResultAsErrorRescord);
217 if($null -eq $scriptResult)
219 $errorId = "InValidResultFromTestScript";
220 $errorCategory = [System.Management.Automation.ErrorCategory]::InvalidResult;
221 $exception = New-Object System.InvalidOperationException $($LocalizedData.InValidResultFromTestScriptError) ;
222 $errorRecord = New-Object System.Management.Automation.ErrorRecord $exception, $errorId, $errorCategory, $null
224 $PSCmdlet.ThrowTerminatingError($errorRecord);
227 # If the script is returing multiple objects, then we consider the last object to be the result of script execution.
228 if($scriptResult.GetType().ToString() -eq 'System.Object[]')
230 $reultObject = $scriptResult[$scriptResult.Length -1];
234 $reultObject = $scriptResult;
237 if(($null -ne $reultObject) -and
238 (($reultObject -eq $true) -or ($reultObject -eq $false)))
240 $testTargetResourceResult = $reultObject;
244 $errorId = "InValidResultFromTestScript";
245 $errorCategory = [System.Management.Automation.ErrorCategory]::InvalidResult;
246 $exception = New-Object System.InvalidOperationException $($LocalizedData.InValidResultFromTestScriptError) ;
247 $errorRecord = New-Object System.Management.Automation.ErrorRecord $exception, $errorId, $errorCategory, $null
249 $PSCmdlet.ThrowTerminatingError($errorRecord);
252 $testTargetResourceEndVerboseMessage = $($LocalizedData.TestTargetResourceEndVerboseMessage);
253 Write-Debug -Message $testTargetResourceEndVerboseMessage;
255 $testTargetResourceResult;
258 function CheckDeviceGuardStatus
262 # Check if Device Guard is enabled.
263 $systemLockdownPolicy = [System.Management.Automation.Security.SystemPolicy]::GetSystemLockdownPolicy()
264 if($systemLockdownPolicy -eq [System.Management.Automation.Security.SystemEnforcementMode]::Enforce)
266 $errorId = "ResourceNotAllowedWhenDeviceGuardIsEnabled";
267 $errorCategory = [System.Management.Automation.ErrorCategory]::InvalidOperation;
268 $exception = New-Object System.InvalidOperationException $($LocalizedData.ResourceNotAllowedWhenDeviceGuardIsEnabled);
269 $errorRecord = New-Object System.Management.Automation.ErrorRecord $exception, $errorId, $errorCategory, $null
270 $PSCmdlet.ThrowTerminatingError($errorRecord);
272 elseif ($systemLockdownPolicy -eq [System.Management.Automation.Security.SystemEnforcementMode]::Audit)
274 Write-Warning ($LocalizedData.WarningRunningScriptResourceInFullLanguageMode)
279 if($_.FullyQualifiedErrorId -eq 'TypeNotFound')
281 # [System.Management.Automation.Security.SystemPolicy] Type not found.
282 # It may happen with old PowerShell version.
287 # Failed to get Device Guard status.
292 function ScriptExecutionHelper
299 [System.Management.Automation.PSCredential]
303 $scriptExecutionResult = $null;
308 $executingScriptMessage = $($LocalizedData.ExecutingScriptMessage) -f ${ScriptBlock} ;
309 Write-Debug -Message $executingScriptMessage;
311 if($null -ne $Credential)
313 $scriptExecutionResult = Invoke-Command -ScriptBlock $ScriptBlock -ComputerName . -Credential $Credential
317 $scriptExecutionResult = &$ScriptBlock;
319 $scriptExecutionResult;
323 # Surfacing the error thrown by the execution of Get/Set/Test script.