fork download
  1. cls
  2.  
  3. #####################################
  4. ### Domain Administration with .NET ###
  5. ### 2012 ###
  6. #####################################
  7.  
  8. # These scripts must run with domain administrator credentials.
  9.  
  10. # Although the DirectoryEntry constructor can take a username
  11. # and password, ADSI uses the current "logged on" credentials.
  12.  
  13. #region DirectoryEntry objects
  14.  
  15. # The .NET framework provides a DirectoryEntry class that is used to
  16. # access directory objects including users, groups, OUs, the domain root, etc.
  17. $directoryEntry = New-Object System.DirectoryServices.DirectoryEntry("LDAP://CN=Jared Deckard,OU=GroupName,OU=Users and Groups,DC=domain,DC=com")
  18.  
  19. # The following line is functionally identical, but casts the path string to a DirectoryEntry
  20. # instead of explicitly creating a new object with the class constructor.
  21. $directoryEntry = [adsi] "LDAP://CN=Jared Deckard,OU=GroupName,OU=Users and Groups,DC=domain,DC=com"
  22.  
  23. # Note: Creating a DirectoryEntry requires downloading all the objects properties from the
  24. # server and should only be used when the object needs to be modified. The collection returned
  25. # by a search will contain a read-only copy of these properties, but is much faster than
  26. # creating a new DirectoryEntry.
  27.  
  28. # Any changes made to a DirectoryEntry must be committed to the server with CommitChanges()
  29. $directoryEntry.CommitChanges()
  30.  
  31. #endregion
  32.  
  33. #region Setup a directory search
  34.  
  35. # Create a .NET DirectoryEntry that connects to the domain root using the current credentials
  36. $domainRoot = [adsi] "LDAP://dc=domain,dc=com"
  37.  
  38. # Create a .NET DirectorySearcher
  39. $objSearcher = New-Object System.DirectoryServices.DirectorySearcher
  40.  
  41. $objSearcher.PageSize = 1000 # Limit PageSize to process results 1000 at a time
  42. $objSearcher.SearchScope = "Subtree" # Allows search to traverse child nodes
  43.  
  44. # Limit the properties to only those needed to speed up the search
  45. $objSearcher.PropertiesToLoad.Clear()
  46. $objSearcher.PropertiesToLoad.Add("cn") | Out-Null
  47. $objSearcher.PropertiesToLoad.Add("member") | Out-Null
  48.  
  49. # Start searching at the domain root
  50. $objSearcher.SearchRoot = $domainRoot
  51.  
  52. #endregion
  53.  
  54. #region Search for users
  55.  
  56. # Sample user info
  57. $filterBy = "name"
  58. $first = ""
  59. $last = "deck"
  60.  
  61. # Create a user filter with wild cards for partial matches
  62. $objSearcher.Filter = "(&(objectCategory=User)($filterBy=$first* $last*))"
  63.  
  64. # Get a collection of matching results
  65. $userResults = $objSearcher.FindAll()
  66.  
  67. #endregion
  68.  
  69. #region Process user search results
  70.  
  71. if($userResults.Count -lt 1) # Process no results
  72. {
  73. Write-Host "No matches found in $($domainRoot.name)" -ForegroundColor Red
  74. }
  75.  
  76. if($userResults.Count -eq 1) # Process one result
  77. {
  78. # Resolve user path to a full DirectoryEntry object
  79. $FullUserEntry = [adsi] $userResults[0].Path
  80. Write-Host "$($FullUserEntry.name)" -BackgroundColor Green
  81. }
  82.  
  83. if($userResults.Count -gt 1) # Process many results
  84. {
  85. Write-Host "User matches: "
  86. foreach($UserEntry in $userResults){ Write-Host "$($UserEntry.Properties.cn)" -ForegroundColor Blue }
  87. }
  88.  
  89. Write-Host ""
  90.  
  91. #endregion
  92.  
  93. #region Search for groups
  94.  
  95. # Sample group name from company name
  96. $Company = "*"
  97. $GroupName = "sec-glb-$Company Users"
  98.  
  99. # Get group from AD
  100. $objSearcher.Filter = "(&(objectCategory=group)(name=$GroupName))"
  101.  
  102. $groupResults = $objSearcher.FindAll()
  103.  
  104. #endregion
  105.  
  106. #region Process group search results
  107.  
  108. # Process no results
  109. if($groupResults.Count -lt 1)
  110. {
  111. Write-Host "No matches found in $($domainRoot.name)" -ForegroundColor Red
  112. }
  113.  
  114. # Process one result
  115. if($groupResults.Count -eq 1)
  116. {
  117. $groupEntry = $groupResults[0]
  118.  
  119. Write-Host "$($groupEntry.Properties.cn)" -BackgroundColor Green
  120.  
  121. # Loop over each group member
  122. foreach($UserDN in $groupEntry.Properties.member)
  123. {
  124. # Resolve user DN to a full DirectoryEntry object
  125. $fullUser = [adsi] "LDAP://$UserDN"
  126. Write-Host "+ $($fullUser.name)" -ForegroundColor Blue
  127. }
  128. }
  129.  
  130. # Process many results
  131. if($groupResults.Count -gt 1)
  132. {
  133. Write-Host "Group matches: "
  134.  
  135. # Loop over each group
  136. foreach($groupEntry in $groupResults)
  137. {
  138. Write-Host "$($groupEntry.Properties.cn)" -ForegroundColor Blue
  139.  
  140. # Loop over each group member
  141. foreach($User in $groupEntry.Properties.member){ Write-Host "- $User" -ForegroundColor DarkGray }
  142. }
  143. }
  144.  
  145. Write-Host ""
  146.  
  147. #endregion
  148.  
  149. #region Adding users to a group
  150.  
  151. # Only the user path (DN) is required to add a user to a group, avoid resolving to DirectoryEntry if possible
  152. $UserPath = "LDAP://CN=Jared Deckard,OU=GroupName,OU=Users and Groups,DC=domain,DC=com"
  153.  
  154. # The group path must be resolved to a DirectoryEntry to expose the object methods
  155. $GroupPath = "LDAP://CN=sec-glb-ComapanyName,OU=Users and Groups,DC=domain,DC=com"
  156. $FullGroup = [adsi] $GroupPath
  157.  
  158. try # Exceptions can be thrown for many reasons
  159. {
  160. # Add the user path to the group object's member list
  161. $FullGroup.add($UserPath) | Out-Null
  162.  
  163. # Commit any changes made to the group object to the domain
  164. $FullGroup.CommitChanges()
  165.  
  166. # User added successfully
  167. Write-Host "$UserPath added to $GroupPath" -BackgroundColor Green
  168. }
  169.  
  170. catch # Catch errors to gracefully continue execution
  171. {
  172. # The add should throw an exception because I am already a member of the group
  173. Write-Host $Error[0] -ForegroundColor Red
  174. }
  175.  
  176. #endregion
  177.  
  178. #region Creating objects
  179.  
  180. # Sample object
  181. $ObjectType = "group"
  182. $ObjectName = "tst-PS-ADSI-Example"
  183.  
  184. try # Always catch exceptions when trying to make changes to the directory
  185. {
  186. # Objects must be created in an existing OU
  187. $ParentOU = [adsi] "LDAP://OU=Users and Groups,dc=domain,dc=com"
  188.  
  189. # Create a new object in a parent OU
  190. $NewObject = $ParentOU.Create("$ObjectType", "CN=$ObjectName")
  191.  
  192. # Required attributes may need to be set before the object can be created
  193. # Default values will be used if they are specified by the domain
  194. $NewObject.Put("sAMAccountName", "$ObjectName");
  195. $NewObject.Put("groupType", "-2147483646");
  196.  
  197. # Commit the changes to the new object
  198. $NewObject.CommitChanges()
  199.  
  200. # Object created successfully
  201. Write-Host "$ObjectName created successfully" -BackgroundColor Green
  202. }
  203. catch{ Write-Host $Error[0] -ForegroundColor Red }
  204.  
  205. #endregion
  206.  
  207. #region Deleting objects
  208.  
  209. try
  210. {
  211. # The Delete method removes an object from the parent OU
  212. # The change is automatically committed to the domain
  213. $ParentOU.Delete("$ObjectType", "CN=$ObjectName")
  214.  
  215. # Object deleted successfully
  216. Write-Host "$ObjectName deleted successfully" -BackgroundColor Green
  217. }
  218. catch{ Write-Host $Error[0] -ForegroundColor Red }
  219.  
  220. #endregion
  221.  
  222. #region Resources
  223.  
  224. # http://social.technet.microsoft.com/wiki/contents/articles/4231.working-with-active-directory-using-powershell-adsi-adapter-en-us.aspx
  225. # http://msdn.microsoft.com/en-us/library/system.directoryservices.directoryentry.aspx
  226.  
  227. #endregion
  228.  
  229. #region Notes
  230.  
  231. #####################################
  232. # Created 07/31/12 by Jared Deckard #
  233. #####################################
  234.  
  235. #region Change Log
  236.  
  237. # Added "DirectoryEntry objects" - 07/31/12 JD
  238. # Added "Setup a directory search" - 07/31/12 JD
  239. # Added "Search for users" - 07/31/12 JD
  240. # Added "Process user search results" - 07/31/12 JD
  241. # Added "Search for groups" - 07/31/12 JD
  242. # Added "Process group search results" - 07/31/12 JD
  243. # Added "Adding users to a group" - 07/31/12 JD
  244. # Added "Creating objects" - 07/31/12 JD
  245. # Added "Deleting objects" - 07/31/12 JD
  246.  
  247. # Added "Resources" - 08/02/12 JD
  248. # Changed SetInfo() to CommitChanges() - 08/02/12 JD
  249.  
  250. #endregion
  251.  
  252. #endregion
Not running #stdin #stdout 0s 0KB
stdin
Standard input is empty
stdout
Standard output is empty