Share This Post

Prepare for ConfigMgr 2012 with these handy PowerShell scripts!

So the time is coming – you need to prepare to ConfigMgr 2012. Sure, the migration tool built into 2012 is an awesome product, but don’t you think you should clean up your ConfigMgr 2007 infrastructure before you run down the migration path?

Yes…yes you should.

Here are some scripts we have thrown together for a MMS 2011 presentation, but we thought it would be nice to share them out a bit early.

Word of advice: Change servername and site_123 in the following examples to the appropriate ConfigMgr Primary server and Site code.

Packages missing version or manufacturer fields:

Let’s talk about package source. You have hundreds of packages in 2007 – some of which have been there before your packaging standards went in. Perhaps you have packages that don’t have a version number assigned to them, or don’t have a manufacturer assigned to them….you need a quick way to see those packages.

gwmi -computer servername -namespace root\sms\site_123 -class sms_package | % {if ($_.version -eq “”) {$_.packageid}}

This simple one-line command (watch word wrap!!) shows you a list of packages that don’t have a version. Need to check manufacturer? Just change the script a slight bit:

gwmi -computer servername -namespace root\sms\site_123 -class sms_package | % {if ($_.manufacturer-eq “”) {$_.packageid}}

Simple, huh? Now go hunt down the techs that created those packages and beat them around the head and neck.

Unused Packages:

Wait – why would you want to move packages that aren’t even being used? Who would want to do that? This script is a bit longer, but gives you a nice output of packages that aren’t used in advertisements, depenedent (run another program first) programs, or Task Sequences:

$adverts = gwmi -computer servername -namespace root\sms\site_123 -class sms_advertisement | select-object packageid
$packages = gwmi -computer
servername -namespace root\sms\site_123 -class sms_package |select-object packageid
$references = gwmi -computer
servername -namespace root\sms\site_123 -class sms_tasksequencereferencesinfo |select-object referencepackageid
$dependent = gwmi -computer
servername -namespace root\sms\site_123 -query “select dependentprogram from sms_program where dependentprogram != ”” | select-object dependentprogram
$packagelist = @()
Foreach ($package in $packages)
$pkgid = $package.packageid
if (!($packagelist -contains $pkgid))
{gwmi -computer servername -namespace root\sms\site_123 -query “select * from sms_package where packageid = ‘$pkgid'”| select-object packageid,manufacturer, name, version}

Great – now you can clean those up or just refuse to migrate them.

Validate Package Source:

So now you have a list of packages that are being used, they should have the right version numbers and other fields filled out – better validate your package source before you do any migrating, or this whole thing will come to a crashing halt!

$packages = gwmi -computer servername -namespace root\sms\site_123 -class sms_package
$packages | %{
if ($_.pkgsourcepath -ne “”)
if (!(test-path $_.pkgsourcepath)) {$_|select-object manufacturer, name, version, packageid, pkgsourcepath}

There is one caveot with this script – if you aren’t on the site server when you run this command, and if the package source is local (d:\packagesource) then the packages will show up in the invalid list. Either run it from the primary server, or just understand that anything that shows a local path will need to be checked outside of this script.

Move package source:

Right – you have valid sources, packages with all of the appropriate fields…now what? Well, if you are like us, you will probably be moving that package source to a new server when you stand up your new hierarchy. Here is a simple script that will take your package list, move the source files from your old site, and place them in a new source location that is built around the information in the packages. I.e. \\server\packagesource\manufacturer\packagename\version\<actual source files>.

gwmi -computer servername -namespace root\sms\site_123 -class sms_package | % {$pkgman = $_.manufacturer; $pkgname = $; $pkgversion = $_.version; if (!(test-path c:\pub\temp\$pkgman\$pkgname\$pkgversion)) {mkdir c:\pub\temp\$pkgman\$pkgname\$pkgversion}; robocopy $_.pkgsourcepath d:\newpackagesource\$pkgman\$pkgname\$pkgversion /E /R:100 /NP /NFL /NDL}

Find App Model Candidates:

Ok – So now you have your new source – let’s talk about finding App Model candidates for CM2012. Obviously MSI packages are the easiest to place in app model – let’s find those real quick:

gwmi -computer servername -namespace root\sms\site_123 -class sms_program | % {$prgname = $_.programname; $pkgid = $_.packageid; $commandline = $_.commandline; if ($commandline.contains(“msi”)) {gwmi -computer servername -namespace root\sms\site_123 -query “select manufacturer, name,version from sms_package where packageid = ‘$pkgid'”| select-object manufacturer, name, version}}

Great! A list of packages that will make excellent App Models in CM2012. That will make Microsoft very happy.

List Program Requirements:

One last script around packages – let’s find out what the program requirements are on your existing packages. It will be nice to have those documented then moving apps over. Warning! This can take a while to run!

#Modify SiteServer value, and Namespace value for your environment.
$SiteServer = “Servername”
$NameSpace = “root\sms\site_123”
#Get all Advertisements
$adv = gwmi sms_advertisement -computer $SiteServer -namespace $NameSpace
#Create an Array for all objects created…
$allObjs = @()
$adv | foreach {
$myPackageID = $_.PackageID
$myProgramName = $_.ProgramName
$myAdvertName = $_.AdvertisementName
#grab the program for this advertisement
$prg = gwmi sms_program -computer $SiteServer -namespace $NameSpace -filter “PackageID=’$myPackageID’ and Programname=’$myProgramName'”
#see if it’s configured to run on “Any Platform”
if ($prg.ProgramFlags -band 0x08000000) {
#it is configured to run on “Any Platform” – create a new object, and add it to the array.
$Obj = New-Object PSObject -Property @{
AdvertisementName = $myAdvertName
PackageID = $myPackageID
ProgramName = $myProgramName
AnyPlatform = $True
Platform = $null
MaxVersion = $null
MinVersion = $null
Name = $null
$allObjs += $obj
else {
#have to use a wmi accelerator, because SupportedOperatingSystems is a lazy property
$prg = [wmi] (gwmi sms_program -computer $SiteServer -namespace $NameSpace -filter “PackageID=’$myPackageID’ and Programname=’$myProgramName'”).__Path
$prg.SupportedOperatingSystems | foreach {
#create a new object for each supported OS
$Obj = New-Object PSObject -Property @{
AdvertisementName = $myAdvertName
PackageID = $myPackageID
ProgramName = $myProgramName
AnyPlatform = $False
Platform = $_.Platform
MaxVersion = $_.MaxVersion
MinVersion = $_.MinVersion
Name = $_.Name
$allObjs += $obj
#select column order, sort, and display in gridview
$allObjs | select AdvertisementName, PackageID, ProgramName, AnyPlatform, Platform, Name, MinVersion, MaxVersion | Sort-Object AnyPlatform, advertisementname | out-gridview
#export to csv
$allObjs | select AdvertisementName, PackageID, ProgramName, AnyPlatform, Platform, Name, MinVersion, MaxVersion | Sort-Object AnyPlatform, advertisementname | export-csv c:\temp\Platforminfo.csv -notypeinformation

This one is a bit longer – mostly because program requirements flag is a lazy WMI property (YUCK!).

List Disabled Software Metering Rules:

Ok, let’s swtich gears. How about we look at something else we don’t want to migrate….Disabled Software Metering Rules. I mean, really – they were disabled for a reason, right?

gwmi -computer servername -namespace root\sms\site_123 -class sms_meteredproductrule | % { if ($_.enabled -eq $FALSE) {$_.ProductName}}

Quick, simple, and to the point. You could even through some parentheses around that command and appeand a delete to automatically get rid of them.

Share This Post

Leave a Reply