Skip navigation

Bulk create NPS policies

Q. How can I bulk create NPS policies?

A. I recently had to create a fairly complicated set of policies on NPS that enabled access to specific vlans based on a users membership of different different groups, one for the VLAN they could to connect to and one their location. Therefore a user had to be in a specific location group, the request had to come from that RADIUS client in that location and they needed to be in specific VLAN group which was the VLAN returned. Consider if I had 20 possible VLANs and 10 locations that would result in 200 separate policies (you have to multiply them). Manually creating that would be terrible so I looked for an automated solution.

There are no command line interfaces to create NPS rules which leaves one option. It is possible to export out the configuration to XML and also to import the configuration from XML. Therefore the solution is:

  1. Export out the NPS configuration to XML
    Export-NpsConfiguration -Path NPSConfig.xml
  2. Modify the XML with the rules required
  3. Import in the updated XML
    Import-NpsConfiguration -Path NPSConfig.xml

There are two key elements for each policy. The first defines the policy itself, the second defines the conditions and it uses the GUIDs of users/groups and not the names which means you will require the GUIDs (use Get-ADUser and look at the SID property).

<Wireless_Authentication_VLAN291___LondonLab name="Wireless Authentication VLAN291 - LondonLab">
<Properties>
<IP_Filter_Template_Guid dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes">{00000000-0000-0000-0000-000000000000}</IP_Filter_Template_Guid>
<Opaque_Data dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes"/>
<Template_Guid dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes">{00000000-0000-0000-0000-000000000000}</Template_Guid>
<msNPAllowDialin dt:dt="boolean" xmlns:dt="urn:schemas-microsoft-com:datatypes">1</msNPAllowDialin>
<msNPAllowedEapType dt:dt="bin.hex" xmlns:dt="urn:schemas-microsoft-com:datatypes">19000000000000000000000000000000</msNPAllowedEapType>
<msNPAllowedEapType dt:dt="bin.hex" xmlns:dt="urn:schemas-microsoft-com:datatypes">1a000000000000000000000000000000</msNPAllowedEapType>
<msNPAuthenticationType2 dt:dt="int" xmlns:dt="urn:schemas-microsoft-com:datatypes">5</msNPAuthenticationType2>
<msQuarantineState dt:dt="int" xmlns:dt="urn:schemas-microsoft-com:datatypes">0</msQuarantineState>
<msQuarantineUpdateNonCompliant dt:dt="boolean" xmlns:dt="urn:schemas-microsoft-com:datatypes">1</msQuarantineUpdateNonCompliant>
<msRADIUSTunnelMediumType dt:dt="int" xmlns:dt="urn:schemas-microsoft-com:datatypes">6</msRADIUSTunnelMediumType>
<msRADIUSTunnelPrivateGroupId dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes">291</msRADIUSTunnelPrivateGroupId>
<msRADIUSTunnelType dt:dt="int" xmlns:dt="urn:schemas-microsoft-com:datatypes">13</msRADIUSTunnelType>
<msSavedMachineHealthCheckOnly dt:dt="int" xmlns:dt="urn:schemas-microsoft-com:datatypes">0</msSavedMachineHealthCheckOnly>
</Properties>
</Wireless_Authentication_VLAN291___LondonLab>

<Wireless_Authentication_VLAN291___LondonLab name="Wireless Authentication VLAN291 - LondonLab">
<Properties>
<Opaque_Data dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes"/>
<Policy_Enabled dt:dt="boolean" xmlns:dt="urn:schemas-microsoft-com:datatypes">1</Policy_Enabled>
<Policy_SourceTag dt:dt="int" xmlns:dt="urn:schemas-microsoft-com:datatypes">0</Policy_SourceTag>
<Template_Guid dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes">{00000000-0000-0000-0000-000000000000}</Template_Guid>
<msNPAction dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes">Wireless Authentication VLAN291 - LondonLab</msNPAction>
<msNPConstraint dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes">USERNTGROUPS("S-1-5-21-3834142513-3770161285-3225119399-3113")</msNPConstraint>
<msNPConstraint dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes">USERNTGROUPS("S-1-5-21-3834142513-3770161285-3225119399-3110")</msNPConstraint>
<msNPConstraint dt:dt="string" xmlns:dt="urn:schemas-microsoft-com:datatypes">MATCH("NAS-Identifier=LondonLab")</msNPConstraint>
<msNPSequence dt:dt="int" xmlns:dt="urn:schemas-microsoft-com:datatypes">2</msNPSequence>
</Properties>
</Wireless_Authentication_VLAN291___LondonLab>

The easiest way to work out the XML you need is to manually create a policy in the Network Policy Server MMC snap-in before exporting then duplicate that XML in the file with you changes. What is the best way to duplicate that XML? With PowerShell which I cover in the next FAQ. To help in my script when I create the various groups for each location and VLAN I actually saved them to a hash table with the SID which I could then read back into my script to update the XML to get the required SIDs. Below is my script to create the VLAN and location groups if it helps in your environment.

$LABs = @(("LABATL","Atlanta"),("LABBOS","Boston"),("LABCHI","Chicago"),("LABDAL","Dallas"),("LABDET","Detroit"),("LABIRV","Irvine"),("LABLA","Los Angeles"),("LABMPLS","Minneapolis"),("LABNY","New York"),("LABPHL","Philadelphia"),("LABDC","Washington DC"),("LABSIVY","Silicon Valley"),("LABSTL","St. Louis"),("LABTOR","Toronto"))
$ParentVLANGRPOU = "OU=VLANGroups,OU=VLANAccess,DC=oneLAB,DC=net"
$ParentLABGRPOU = "OU=LABGroups,OU=VLANAccess,DC=oneLAB,DC=net"

#hash table for the VLANs and SIDs
$vlangrouphash = @{}

#for each VALN from 2 to 255
foreach($vlannum in 2..255)
{
    $VLANName = 'VLAN' + $vlannum + 'GRP'
    Write-Output $VLANName

    $VLANGroup = New-ADGroup -Name $VLANName -GroupCategory Security -GroupScope Global `
            -DisplayName $VLANName -Path $ParentVLANGRPOU `
            -Description "Group for users of VLAN $vlannum"  -PassThru

    $vlangrouphash.Add($VLANName,$VLANGroup.SID)
}

#Save to file
$vlangrouphash |Export-Clixml -Path vlans.xml

#to read in
$vlangrouphash = Import-Clixml -Path vlans.xml


#hash table for the LABs and SIDs
$LABgrouphash = @{}

#for each LAB
foreach($LAB in $LABs)
{
    $LABName = $LAB[0] + 'VLGRP'
    Write-Output $LABName

    $LABGroup = New-ADGroup -Name $LABName -GroupCategory Security -GroupScope Global `
            -DisplayName $LABName -Path $ParentLABGRPOU `
            -Description "Group for users of LAB $($LAB[0])"  -PassThru

    $LABgrouphash.Add($LABName,$LABGroup.SID)
}

#Save to file
$LABgrouphash |Export-Clixml -Path LABs.xml

#to read in
$LABgrouphash = Import-Clixml -Path LABs.xml

 

Hide comments

Comments

  • Allowed HTML tags: <em> <strong> <blockquote> <br> <p>

Plain text

  • No HTML tags allowed.
  • Web page addresses and e-mail addresses turn into links automatically.
  • Lines and paragraphs break automatically.
Publish