Contents

SCCM : Refresh Device Collection Memberships


Contents

I’m in the finishing stages of a new SCCM deployment, but also in the process of an Active Directory consolidation at the moment, and ran in to the following issue:

A machine from Domain A has been re-imaged using SCCM to run in Domain B. SCCM has a Device Collection X for Domain A and Device Collection Y for Domain B. Device Collection Y has a Deployment for a specific VPN Application that’s required, otherwise it won’t run.

The Problem

The engineer that re-images the machine forgot to remove the machine from Domain A and therefor doesn’t get the VPN Application, as the Client is still recognized as being an active machine on Domain A, taking precedent over the fact that it ALSO exists in Domain B now [same MAC address etc].

The Solution

By manually removing [yes, this needs to be automated at a later time as well] the old AD machine from Domain A and refreshing the Device Collection’s memberships, the issue can be resolved.

Normally this is something that gets done on a regular interval [in this case, every 24h], but we need to force it, sometimes for multiple Device Collections.

Instead of using the clunky GUI, PowerShell’s to the rescue 🙂

There is a WMI Method in the SMS_Collection which does exactly what we require: Refresh the Membership of a Collection 🙂

The Code

Here’s the code that does the trick for me

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
[CmdletBinding()]

param (
$SiteCode = 'AMS',
$SiteServer = 'CM01.contoso.com'
)


begin {
Write-Verbose "Starting '$MyInvocation.MyCommand'"
Write-Verbose "Sitecode is '$SiteCode'"
Write-Verbose "Siteserver is '$SiteServer'"
Set-location -Path "$SiteCode`:"

Write-Verbose 'Selecting Device Collections to refresh'
$DCollections = Get-CMDeviceCollection | Select-Object Name,CollectionID,MemberCount,LastChangeTime,LastMemberChangeTime,LastRefreshTime | Sort-Object Name | Out-GridView -PassThru -Title 'Select the Device Collections to force refresh'

}
process {

if ($DCollections) {
    foreach ($DCollection in $DCollections) {
        Write-Verbose "Refreshing Device Collection '$($DCollection.Name)'"

        $WmiParams = @{
            Path = "ROOT\SMS\Site_$($SiteCode):SMS_Collection.CollectionId='$($DCollection.CollectionID)'"
            Name = 'RequestRefresh'
            ComputerName = $SiteServer
            }
        Invoke-WmiMethod @WmiParams
        Write-Verbose "Device Collection '$($DCollection.Name)' refreshed"
        }
    }
}

Happy Scripting! 🙂