Today I was building a script to create system resources in SCCM 2012 and part of the task was to add these resources to a set of collections.

The script will use from the SCCM server when finally implemented but for now I was using my laptop for editing and debugging.

When I came to the point where I had to create the actual membership rules for the collections I ran into a hurdle that puzzled me.

The WMI object I had to create was the SMS_CollectionRuleDirect, which often is done using this simple PowerShell snippet:

$ruleClass = [WMICLASS]"\\$($server)\root\sms\site_$($sitecode):SMS_CollectionRuleDirect".CreateInstance()

And don’t get me wrong, it works and it is fairly short … BUT there is no way to assign any credentials to this call, which I needed when calling the server from remote.

So I looked around for a way to create this instance using some other method.

First I tried Set-WMIInstance but that resulted in an error from SCCM as Set-WMIInstance apparently contains and implicit call to Put(), and this particular object is not supposed to be Put().

After quite a lot of reading and searching I came across a blog called “Schnitzelspechts Blog” where the author was struggling with a very similar issue related to the WMI registry provider, stdregprov.

It turns out that Get-WMIObject has a switch called -List that allows you to list all classes in a namespace, so using this snippet you can list all classes in the SMS\Site_XXX namespace.

Get-WMIObject –List -Namespace Root\SMS\Site_XXX

A pretty long list by the way …

Using this I was then able to get my class object remotely using credentials as Get-WMIObject works very well with credentials.

$ruleClass = Get-WmiObject -List -ComputerName "$server" -Namespace Root\SMS\Site_"$sitecode" -Credential $cred | where-object { $ -eq "SMS_CollectionRuleDirect" }

yippee ki … well almost … yay … the list was pretty long so the call does take a while to finish, and I was going to create a few memberships so I tried to see if there was a way to query the class in the call to Get-WMIObject and not by using a where-object, as that would get the whole list and query into that.

My first attempt was to see if the -class argument would help me out.

$ruleClass = Get-WmiObject -List -ComputerName "$server" -Namespace Root\SMS\Site_"$sitecode" -Credential $cred –class SMS_CollectionRuleDirect

I was expecting a polite error message saying that my life was not THAT easy but no, it worked like a charm and was quite a lot faster than the previous call.

I now had my class and could continue on to call the CreateInstance method.

So for future use I might stick to using this approach as I find the [WMIClass]”\\ syntax very crude and not very readable but maybe that’s just me.

You can read Schnitzelspecht’s very helpful post here