How should custom DSC resources behave when the actual resource object cannot be created or removed by DSC?
In my specific example, I'm writing a resource for managing COM+ Applications, Components and Interfaces. Creating resources for Applications and Components is fine; they can be created and removed from the Catalog programmatically. However Interfaces are created automatically when a Component is created from a DLL.
I need to be able to update the Interface properties (namely the QueuingEnabled
property). I therefore intended to describe the configuration of a COM+ Interface as below:
COMplusInterface MyInterface
{
Ensure = 'Present'
ApplicationID = 'BB5B8A1F-D70C-44BD-8ADD-E548DF39AACF'
ComponentDLLPath = 'C:\Program Files\MyApplication\bin\MyComponent.dll'
InterfaceName = 'MyInterface'
Description = 'This is my interface'
QueuingEnabled = $true
}
But if the Application or Component doesn't yet exist, should this resource throw an error? Similarly if the DLL just doesn't have that interface. There's no point in Test-TargetResource
returning $false
because that will initiate Set-TargetResource
that then won't be able to create the Interface.
Following on from that, what should the DSC resource do if Ensure
is set to Absent
? The Interface can't be removed if it does exist, only by removing the Component can I do that. Should I just return all Interface properties to their default values?
Starting with your question about Ensure
, I'll just say that there is no requirement whatsoever to have an Ensure
property. Although most resources do, you'll find ones (even from Microsoft) where it doesn't quite make sense. If it doesn't make sense for your resource, don't include it.
As for what to do if the component doesn't exist, yes, you should throw an error. Use DependsOn
in your COMplusInterface
resource to ensure it's applied after your COMplusComponent
resource.
Test-TargetResource
should return $false
whenever the state doesn't match, whether the reason is that the component doesn't exist, or the properties don't match. If the component doesn't exist then Set-TargetResource
will run, and it will fail, as it should. You're trying to describe state with your Configuration so you should have set pre-requisite states in the configuration before this part runs (that's where DependsOn
comes in).
I would say that ApplicationID
should be your Key
property, and the others should be optional; you would only want to specify them if you are forcing their state, so I think you should be able to specify your configuration this way:
COMplusComponent MyComponent
{
<# your component resource #>
}
COMplusInterface MyInterface
{
ApplicationID = 'BB5B8A1F-D70C-44BD-8ADD-E548DF39AACF'
QueuingEnabled = $true
DependsOn = '[COMplusComponent]MyComponent'
}