Hey PowerShell Guy!,How Can I Map Drives Based on Membership in an Active Directory Group and a CSV file.
In this translation of a Hey Scripting guy article to PowerShell based on : How Can I Map Drives Based on Membership in an Active Directory Group When the User Belongs to Multiple Groups? I tuned the example a bit as I did not like the configuration of groups and drives in the script I moved them to a CSV file also I decided to make a general Invoke-MapNetworkdrive function first.
Let's start with the Invoke-MapNetworkdrive function :
Function Invoke-MapNetworkDrive ($DriveLetter,$UncPath) {
$nw = New-Object -ComObject Wscript.Network
$nw.MapNetworkDrive($DriveLetter, $UncPath)
}
You can see that this is wrapping the same COM object used in the Vbscript example but it is handy to have this function around in general.
Next as I wanted to use a CSV file we must make one first, you can make this in excel but from PowerShell I often use a here string to generate a test file like this :
$Mappings = @'
Group,Mapping
Administrators,\\localhost\c$
mowGroup,\\localhost\PoSH$
'@
Set-Content c:\scripts\mappings.csv $mappings
Now we have the helper function and CSV file we are ready to go (V2 CTP only ):
$groups = @(([AdsiSearcher]"CN=$($env:USERNAME)").Findone().properties.memberof |% {([adsi]"LDAP://$_").cn})
trap{continue};Import-Csv c:\scripts\mappings.csv |? {$groups -contains $_.group} |% {Invoke-MapNetworkDrive x: $_.mapping}
2 simple lines and we are done :)
Ok, Ok maybe some more explaination might be handy ;)
Let's go step by step over the last 2 lines and rebuild then in the console interactively :
First as in the Vbscript example we get the username not using the COM object but an environment variable:
[PoSH]>$env:USERNAME
Administrator
we make a string in "CN format"
[PoSH]>"CN=$($env:USERNAME)"
CN=Administrator
and Cast it into a AdsiSearcher this is new forthe PowerShell V2 CTP for Version 1.0 you need new-object directoryservices.directorysearcher("CN=$($env:USERNAME)")
[PoSH]>[AdsiSearcher]"CN=$($env:USERNAME)"
CacheResults : True
ClientTimeout : -00:00:01
PropertyNamesOnly : False
Filter : CN=Administrator
PageSize : 0
...
we start a search for a single object (use FindAll() when more objects can be returned) :
[PoSH]>([AdsiSearcher]"CN=$($env:USERNAME)").Findone()
Path Properties
---- ----------
LDAP://CN=Administrator,CN=Users,DC=PoshWorks,DC=com {samaccounttype, lastlogon, dscorepropagationdata, objec...
Select the Properties
[PoSH]>([AdsiSearcher]"CN=$($env:USERNAME)").Findone().properties.memberof
CN=Group Policy Creator Owners,CN=Users,DC=PoshWorks,DC=com
CN=Domain Admins,CN=Users,DC=PoshWorks,DC=com
CN=Enterprise Admins,CN=Users,DC=PoshWorks,DC=com
CN=Schema Admins,CN=Users,DC=PoshWorks,DC=com
CN=Administrators,CN=Builtin,DC=PoshWorks,DC=com
Cast the strings returned by the MemberOf property into ADSI Objects and select only the CN property
[PoSH]>@(([AdsiSearcher]"CN=$($env:USERNAME)").Findone().properties.memberof |% {([adsi]"LDAP://$_")})
distinguishedName : {CN=Group Policy Creator Owners,CN=Users,DC=PoshWorks,DC=com}
Path : LDAP://CN=Group Policy Creator Owners,CN=Users,DC=PoshWorks,DC=com
distinguishedName : {CN=Domain Admins,CN=Users,DC=PoshWorks,DC=com}
Path : LDAP://CN=Domain Admins,CN=Users,DC=PoshWorks,DC=com
distinguishedName : {CN=Enterprise Admins,CN=Users,DC=PoshWorks,DC=com}
Path : LDAP://CN=Enterprise Admins,CN=Users,DC=PoshWorks,DC=com
distinguishedName : {CN=Schema Admins,CN=Users,DC=PoshWorks,DC=com}
Path : LDAP://CN=Schema Admins,CN=Users,DC=PoshWorks,DC=com
distinguishedName : {CN=Administrators,CN=Builtin,DC=PoshWorks,DC=com}
Path : LDAP://CN=Administrators,CN=Builtin,DC=PoshWorks,DC=com
[PoSH]>@(([AdsiSearcher]"CN=$($env:USERNAME)").Findone().properties.memberof |% {([adsi]"LDAP://$_").cn})
Group Policy Creator Owners
Domain Admins
Enterprise Admins
Schema Admins
Administrators
[PoSH]>
we put this result into the $Groups variable and are ready for the next line :
get the contents of the CSV file
[PoSH]>Import-Csv c:\scripts\mappings.csv
Group Mapping
----- -------
Administrators \\localhost\c$
mowGroup \\localhost\PoSH$
Filter the groups from the user
[PoSH]>Import-Csv c:\scripts\mappings.csv |? {$groups -contains $_.group}
Group Mapping
----- -------
Administrators \\localhost\c$
We feed this to the Invoke-MapNetworkdrive function and the Trap will break the Loop when the Driveletter is allready mapped and will break the loop so the first mapping "Wins" as in the VbScript example
trap{continue};Import-Csv c:\scripts\mappings.csv |? {$groups -contains $_.group} |% {Invoke-MapNetworkDrive x: $_.mapping}
Enjoy,
Greetings /\/\o\/\/