uruloke Posted July 8, 2008 Share Posted July 8, 2008 (edited) Hello, i'm a new user of AutoIt, but i decided to use it because it seems really great to get awesome GUI for my vbscripts Anyway, I want to make an Active Directory Treeview (look like ADUC console) to run customs scripts to performs creations, search, etc..Reading the help file of AutoIt, I found a way to create a treeview, and i'm pretty sure i can use my brain to find a way to dynamicaly create nodes from my AD. But there something i have not found (I promise I made a search on the forum before posting) : I need a way to get the full path (to have the Distinguished Name in AD) of the selected node. The only thing I found is how to get the name of the node with GUICtrlRead($menu1, 1)So, my questions are: - how can i have the name of the parent node ? With this info, i could recursively build the full path- Is it possible to set a hidden value on a node? In this case I could set the Distinguished Name in the value, and the treeview will only show the name (i'm not sure to be clear muttley )Anyway, if someone as already made an AD treeview / browser, I would be happy to get it Thank you very much----------------------------------- EDIT : SCRIPT SOLUTION-----------------------------------Hi!Here I give you my GenerateADTreeview v1It makes queries in Active Directory to build the treeviewFor now, you have to specify a root Organizationnal Unit (in the MAIN part, modify $strRootContainer) to make it work! You won't see User or Computers container for exempleexpandcollapse popup#include <GUIConstantsEx.au3> #include <WindowsConstants.au3> #include <TreeViewConstants.au3> #include <StaticConstants.au3> #Include <GuiTreeView.au3> Opt('MustDeclareVars', 1) #region ; Define AD Constants Global Const $ADS_GROUP_TYPE_GLOBAL_GROUP = 0x2 Global Const $ADS_GROUP_TYPE_DOMAIN_LOCAL_GROUP = 0x4 Global Const $ADS_GROUP_TYPE_UNIVERSAL_GROUP = 0x8 Global Const $ADS_GROUP_TYPE_SECURITY_ENABLED = 0x80000000 Global Const $ADS_GROUP_TYPE_GLOBAL_SECURITY = BitOR($ADS_GROUP_TYPE_GLOBAL_GROUP, $ADS_GROUP_TYPE_SECURITY_ENABLED) Global Const $ADS_GROUP_TYPE_UNIVERSAL_SECURITY = BitOR($ADS_GROUP_TYPE_UNIVERSAL_GROUP, $ADS_GROUP_TYPE_SECURITY_ENABLED) Global Const $ADS_GROUP_TYPE_DOMAIN_LOCAL_SECURITY = BitOR($ADS_GROUP_TYPE_DOMAIN_LOCAL_GROUP, $ADS_GROUP_TYPE_SECURITY_ENABLED) Global Const $ADS_UF_PASSWD_NOTREQD = 0x0020 Global Const $ADS_UF_WORKSTATION_TRUST_ACCOUNT = 0x1000 Global Const $ADS_ACETYPE_ACCESS_ALLOWED = 0x0 Global Const $ADS_ACETYPE_ACCESS_ALLOWED_OBJECT = 0x5 Global Const $ADS_FLAG_OBJECT_TYPE_PRESENT = 0x1 Global Const $ADS_RIGHT_GENERIC_READ = 0x80000000 Global Const $ADS_RIGHT_DS_SELF = 0x8 Global Const $ADS_RIGHT_DS_WRITE_PROP = 0x20 Global Const $ADS_RIGHT_DS_CONTROL_ACCESS = 0x100 Global Const $ADS_UF_ACCOUNTDISABLE = 2 Global Const $ADS_OPTION_SECURITY_MASK = 3 Global Const $ADS_SECURITY_INFO_DACL = 4 Global Const $ADS_PROPERTY_CLEAR = 1 Global Const $ADS_PROPERTY_APPEND = 3 Global Const $ADS_SCOPE_ONELEVEL = 1 Global Const $ADS_SCOPE_SUBTREE = 2 Global Const $ALLOWED_TO_AUTHENTICATE = "{68B1D179-0D15-4d4f-AB71-46152E79A7BC}" Global Const $RECEIVE_AS = "{AB721A56-1E2f-11D0-9819-00AA0040529B}" Global Const $SEND_AS = "{AB721A54-1E2f-11D0-9819-00AA0040529B}" Global Const $USER_CHANGE_PASSWORD = "{AB721A53-1E2f-11D0-9819-00AA0040529b}" Global Const $USER_FORCE_CHANGE_PASSWORD = "{00299570-246D-11D0-A768-00AA006E0529}" Global Const $USER_ACCOUNT_RESTRICTIONS = "{4C164200-20C0-11D0-A768-00AA006E0529}" Global Const $VALIDATED_DNS_HOST_NAME = "{72E39547-7B18-11D1-ADEF-00C04FD8D5CD}" Global Const $VALIDATED_SPN = "{F3A64788-5306-11D1-A9C5-0000F80367C1}" Const $Member_SchemaIDGuid = "{BF9679C0-0DE6-11D0-A285-00AA003049E2}" Global $objConnection = ObjCreate("ADODB.Connection") ; Create COM object to AD $objConnection.ConnectionString = "Provider=ADsDSOObject" $objConnection.Open ("Active Directory Provider") ; Open connection to AD Global $objRootDSE = ObjGet("LDAP://RootDSE") Global $strAdsDomainPath = $objRootDSE.Get ("defaultNamingContext") ; Retrieve the current AD domain name Global $strHostServer = $objRootDSE.Get ("dnsHostName"); Retrieve the name of the connected DC Global $strConfiguration = $objRootDSE.Get ("ConfigurationNamingContext"); Retrieve the Configuration naming context #endregion #region ; Define Script Constants Global Const $ADS_SCOPE_DEPTH = 1 #endregion ;********************************************************************** ; MAIN ;********************************************************************** Global $hTreeView Global $strRootContainer = "OU=TESTS" &","& $strAdsDomainPath Local $infobutton, $cancelbutton, $msg, $Text GUICreate("AD TreeView", 400, 400) $hTreeView = CreateADTree ($strRootContainer, 25, 25, 300, 300, BitOr($TVS_HASBUTTONS, $TVS_HASLINES, $TVS_LINESATROOT, $TVS_DISABLEDRAGDROP, $TVS_SHOWSELALWAYS), $WS_EX_CLIENTEDGE) $infobutton = GUICtrlCreateButton("Info", 25, 350, 70, 20, 0) $cancelbutton = GUICtrlCreateButton("Cancel", 125, 350, 70, 20, 0) GUISetState () GUIRegisterMsg($WM_NOTIFY, "WM_NOTIFY") While 1 $msg = GUIGetMsg() Select Case $msg = $cancelbutton Or $msg = $GUI_EVENT_CLOSE ExitLoop Case $msg = $infobutton $Text = GetItemAdsPath ($hTreeView) MsgBox(64, "Information", $Text) EndSelect WEnd GUIDelete() Exit #region ;********************************************************************** ; FONCTIONS ;********************************************************************** #region ; TreeView Functions ; --------------------------------------------------------------------- ; Create Treeview of OrganizationalUnits by queries in Active Directory ; --------------------------------------------------------------------- Func CreateADTree ($strRootAdsPath, $intLeft, $intTop, $intWidth, $intHeight, $intStyle, $intExStyle ) Local $LocalTreeview, $RootNode, $strRootName Global $hImage, $hFolderImage $LocalTreeview = GUICtrlCreateTreeView($intLeft, $intTop, $intWidth, $intHeight, $intStyle, $intExStyle) $hImage = _GUIImageList_Create(16, 16, 5, 3) $hFolderImage = _GUIImageList_AddIcon($hImage, "shell32.dll", 4);Folder Image _GUICtrlTreeView_SetNormalImageList($LocalTreeview, $hImage) _GUICtrlTreeView_BeginUpdate($LocalTreeview) $strRootName = GetObjectInfo ($strRootAdsPath, "Name") $RootNode = _GUICtrlTreeView_Add($LocalTreeview, 0, $strRootName, $hFolderImage, $hFolderImage) BuildADtreeView ($LocalTreeview, $RootNode, $strRootAdsPath,$ADS_SCOPE_DEPTH) _GUICtrlTreeView_EndUpdate($LocalTreeview) Return $LocalTreeview EndFunc ; --------------------------------------------------------------------- ; Fonction récursive à N niveaux créant des noeuds à partir de requetes AD ; $intDepth = number of recursive calls ; --------------------------------------------------------------------- Func BuildADtreeView ($hTreeView, $hItem, $strAdsContainer,$intDepth) Local $strOrganizationalUnitsDN, $arrOUsList, $intSizeArray Local $strObjectDN, $strObjectName Local $ThisItem, $i If $intDepth < 1 Then Return EndIf $strOrganizationalUnitsDN = QueryAD ($strAdsContainer, $ADS_SCOPE_ONELEVEL,"OrganizationalUnit", "DistinguishedName", "name", "=", "*", "name") $arrOUsList = StringSplit($strOrganizationalUnitsDN,";") $intSizeArray = $arrOUsList[0] If $strOrganizationalUnitsDN = "" Then ;ConsoleWrite("LISTOU > EXIT FUNC "&@LF) Else For $i = 1 To $intSizeArray $strObjectDN = $arrOUsList[$i] $strObjectName = GetObjectInfo($strObjectDN, "name") ; Add Item on Treeview $ThisItem = _GUICtrlTreeView_AddChild($hTreeView, $hItem, $strObjectName, $hFolderImage, $hFolderImage) ; Build Sub Containers If ($intDepth-1) > 0 Then BuildADtreeView ($hTreeView, $ThisItem, $strObjectDN,$intDepth-1) EndIf Next EndIf EndFunc ; --------------------------------------------------------------------- ; Control clicks on Treeview ; --------------------------------------------------------------------- Func WM_NOTIFY($hWnd, $iMsg, $iwParam, $ilParam) #forceref $hWnd, $iMsg, $iwParam Local $hWndFrom, $iIDFrom, $iCode, $tNMHDR, $hWndTreeview $hWndTreeview = $hTreeView If Not IsHWnd($hTreeView) Then $hWndTreeview = GUICtrlGetHandle($hTreeView) $tNMHDR = DllStructCreate($tagNMHDR, $ilParam) $hWndFrom = HWnd(DllStructGetData($tNMHDR, "hWndFrom")) $iIDFrom = DllStructGetData($tNMHDR, "IDFrom") $iCode = DllStructGetData($tNMHDR, "Code") Switch $hWndFrom Case $hWndTreeview Switch $iCode Case $NM_CLICK; The user has clicked the left mouse button within the control Local $tPoint, $tTVHEx, $TVhItem, $mX, $mY $tPoint = _WinAPI_GetMousePos(True, $hWndTreeview) $mX = DllStructGetData($tPoint, "X") $mY = DllStructGetData($tPoint, "Y") $tTVHEx = _GUICtrlTreeView_HitTestEx($hWndTreeview, $mX, $mY) $TVhItem = DllStructGetData($tTVHEx, "Item") Switch DllStructGetData($tTVHEx, "Flags") Case $TVHT_ONITEM ConsoleWrite("$NM_CLICK" & @LF & "--> $TVHT_ONITEM Item Handle:" & @TAB & $TVhItem) Case $TVHT_ONITEMLABEL or $TVHT_ONITEMICON TreeView_RefreshItem ($hTreeView, $TVhItem) EndSwitch ;~ Return 1; nonzero to not allow the default processing Return 0; zero to allow the default processing EndSwitch EndSwitch Return $GUI_RUNDEFMSG EndFunc ;==>WM_NOTIFY ; --------------------------------------------------------------------- ; Refresh : Load Sub Containers (query AD) ; --------------------------------------------------------------------- Func TreeView_RefreshItem ($hTreeView, $hItem) Local $strItemAdsPath, $intNbChildren Local $strAdsContainer $strItemAdsPath = GetItemRecursiveAdsPath ($hTreeView, $hItem) $intNbChildren = _GUICtrlTreeView_GetChildCount($hTreeView, $hItem) If $intNbChildren < 0 Then $strAdsContainer = $strItemAdsPath & "," &$strAdsDomainPath BuildADtreeView ($hTreeView, $hItem, $strAdsContainer,$ADS_SCOPE_DEPTH) EndIf EndFunc ; --------------------------------------------------------------------- ; TreeView Function : Get Selected Item's Label ; --------------------------------------------------------------------- Func GetItemText ($hTreeView) Local $hItem, $Text $hItem = _GUICtrlTreeView_GetSelection ($hTreeView) ;MsgBox(64, "Information", $hItem) If $hItem = 0 Then $Text = "No item currently selected" Else $Text = _GUICtrlTreeView_GetText ($hTreeView, $hItem) EndIf Return $Text EndFunc ; --------------------------------------------------------------------- ; TreeView Function : Get Parent's Label of the Selected Item ; --------------------------------------------------------------------- Func GetParentItemText ($hTreeView) Local $hItem, $Text Local $hParentItem $hItem = _GUICtrlTreeView_GetSelection ($hTreeView) If $hItem = 0 Then $Text = "No item currently selected" Else $hParentItem = _GUICtrlTreeView_GetParentHandle($hTreeView, $hItem) ;MsgBox(64, "Parent", $hParentItem) If $hParentItem=0 Then $Text = "" Else $Text = _GUICtrlTreeView_GetText ($hTreeView, $hParentItem) EndIf EndIf Return $Text EndFunc ; --------------------------------------------------------------------- ; TreeView Function : Get Selected Item's ADS Path ; syntax like OU=Temp,OU=SALES,OU=Company ; --------------------------------------------------------------------- Func GetItemAdsPath ($hTreeView) Local $Text, $hItem, $hParentItem ; Get Item ID $hItem = _GUICtrlTreeView_GetSelection ($hTreeView) If $hItem <> 0 Then $Text = GetItemRecursiveAdsPath ($hTreeView, $hItem) EndIf Return $Text EndFunc ; --------------------------------------------------------------------- ;; TreeView Function : Get Specified Item's ADS Path ; syntax like OU=Temp,OU=SALES,OU=Company ; --------------------------------------------------------------------- Func GetItemRecursiveAdsPath ($hTreeView, $hItem) Local $Text, $hParentItem ; Get Parent Item ID $hParentItem = _GUICtrlTreeView_GetParentHandle($hTreeView, $hItem) If $hParentItem=0 Then $Text = "OU="&_GUICtrlTreeView_GetText ($hTreeView, $hItem) Else $Text = "OU="&_GUICtrlTreeView_GetText ($hTreeView, $hItem) & "," & GetItemRecursiveAdsPath ($hTreeView, $hParentItem) EndIf Return $Text EndFunc #endregion #region ; AD Functions ; --------------------------------------------------------------------- ; Requete AD ; $intScope = ADS_SCOPE_ONELEVEL or ADS_SCOPE_SUBTREE ; $strTypeFilter = USER, CONTACT, GROUP, COMPUTER ; $strAttributeQueried : Attribut retourné (ex: DistinguishedName, Name, CN, etc.) ; $strAttributeRequested : Critere de recherche (ex: SamAccountName, Name, DisplayName, GivenName, etc.) ; $strOperator: operation à effectuer (ex: "=", ">", "<>") ; $strAttributeValue : requete de valeur (ex: "toto" pour le Name) ; > Recherche possible avec le wildchar (ex: Test*) ; $strSort : Critère de tri alphabétique (ex: "Name" pour un tri sur le nom) ; > Mettre à "" pour ne faire aucun tri ; SORTIE: Si plusieurs réponses, séparation par ';' (ex: DN1;DN2;DN3) ; --------------------------------------------------------------------- Func QueryAD ($strLdapRootPath, $intScope, $strTypeFilter, $strAttributeQueried, $strAttributeRequested, $strOperator, $strAttributeValue, $strSort) Local $objCommand, $objRecordSet Local $strResultQuery, $strResultQueryMultiValued Local $arrTemp, $strValue, $CleanAdsPath $strResultQuery = "" $objCommand = ObjCreate("ADODB.Command") $objCommand.ActiveConnection = $objConnection ;Escape Special Characters for SQL Query $CleanAdsPath = StringReplace($strLdapRootPath,"'","''") $CleanAdsPath = StringReplace($CleanAdsPath,"+","\+") If StringCompare($strTypeFilter,"COMPUTER")=0 Then $objCommand.CommandText = _ "Select "& $strAttributeQueried &","&$strSort&" from 'LDAP://" & $CleanAdsPath & _ "' where objectClass='COMPUTER' and "&$strAttributeRequested&"='"&$strAttributeValue&"'" Else $objCommand.CommandText = _ "Select "& $strAttributeQueried &" from 'LDAP://" & $CleanAdsPath & _ "' where objectClass='"&$strTypeFilter&"' AND objectClass<>'computer' and "&$strAttributeRequested& $strOperator &"'"&$strAttributeValue&"'" EndIf $objCommand.Properties("Page Size") = 1000; Recherche par paquet de 1000 objets $objCommand.Properties("Timeout") = 30 $objCommand.Properties("Searchscope") = $intScope $objCommand.Properties("Cache Results") = False If $strSort<>"" Then $objCommand.Properties("Sort on") = $strSort EndIf $objRecordSet = $objCommand.Execute If $objRecordSet.EOF <> true Then $objRecordSet.MoveFirst EndIf If NOT $objRecordSet.EOF Then If IsArray($objRecordSet.Fields($strAttributeQueried)) Then $arrTemp = $objRecordSet.Fields($strAttributeQueried) $strResultQueryMultiValued = "" For $strValue In $arrTemp If $strResultQueryMultiValued="" Then $strResultQueryMultiValued = $strValue Else $strResultQueryMultiValued = $strResultQueryMultiValued &"§"& $strValue EndIf Next $strResultQuery = $strResultQueryMultiValued Else $strResultQuery = $objRecordSet.Fields($strAttributeQueried).Value EndIf $objRecordSet.MoveNext EndIf ;MsgBox (1,"Query AD","$strResultQuery : "&$strResultQuery) While NOT $objRecordSet.EOF If IsArray($objRecordSet.Fields($strAttributeQueried)) Then $arrTemp = $objRecordSet.Fields($strAttributeQueried) $strResultQueryMultiValued = "" For $strValue In $arrTemp If $strResultQueryMultiValued="" Then $strResultQueryMultiValued = $strValue Else $strResultQueryMultiValued = $strResultQueryMultiValued &"§"& $strValue EndIf Next $strResultQuery = $strResultQuery &";" &$strResultQueryMultiValued Else $strResultQuery = $strResultQuery &";" &$objRecordSet.Fields($strAttributeQueried).Value EndIf $objRecordSet.MoveNext Wend $objCommand = 0 $objRecordSet = 0 Return $strResultQuery EndFunc ; --------------------------------------------------------------------- ; Récupère la valeur d'un attribut d'un objet AD ; - StrObjectDN = Object DistinguishedName ; - StrAttribute = Attribut choisi ; --------------------------------------------------------------------- Func GetObjectInfo ($strObjectDN, $strAttribute) Local $objADObject, $strResult $objADObject = ObjGet ("LDAP://"&$strObjectDN) $objADObject.GetInfo $strResult = $objADObject.Get($strAttribute) Return $strResult EndFunc #endregion #endregion Edited July 17, 2008 by uruloke Link to comment Share on other sites More sharing options...
BrettF Posted July 8, 2008 Share Posted July 8, 2008 So your wanting something that looks like this? http://www.bristol.ac.uk/is/computing/advi...ff/winxp/ou.gif or similar? Vist my blog!UDFs: Opens The Default Mail Client | _LoginBox | Convert Reg to AU3 | BASS.au3 (BASS.dll) (Includes various BASS Libraries) | MultiLang.au3 (Multi-Language GUIs!)Example Scripts: Computer Info Telnet Server | "Secure" HTTP Server (Based on Manadar's Server)Software: AAMP- Advanced AutoIt Media Player | WorldCam | AYTU - Youtube Uploader Tutorials: Learning to Script with AutoIt V3Projects (Hardware + AutoIt): ArduinoUseful Links: AutoIt 1-2-3 | The AutoIt Downloads Section: | SciTE4AutoIt3 Full Version! Link to comment Share on other sites More sharing options...
uruloke Posted July 9, 2008 Author Share Posted July 9, 2008 So your wanting something that looks like this? http://www.bristol.ac.uk/is/computing/advi...ff/winxp/ou.gif or similar?Yes, exactly, the tree part (on the left pane)If I keep your exemple: suppose I wanna create a computer in the OU "student pc lab #1".1/ I have a script/function who takes the OU path in parameter (to know where i will create the computer object)2/ I want to keep the "AD tree" looklike: I click on "student pc lab #1" to specify the target OU. 3/ I need to get the OU path from the selected node to use it with my function createComputerObject Link to comment Share on other sites More sharing options...
BrettF Posted July 9, 2008 Share Posted July 9, 2008 Yes, exactly, the tree part (on the left pane)If I keep your exemple: suppose I wanna create a computer in the OU "student pc lab #1".1/ I have a script/function who takes the OU path in parameter (to know where i will create the computer object)2/ I want to keep the "AD tree" looklike: I click on "student pc lab #1" to specify the target OU. 3/ I need to get the OU path from the selected node to use it with my function createComputerObjectFor AD stuff, have a look here:http://www.autoitscript.com/forum/index.ph...tory&st=105I am unable to test AD stuff ATM, but I'll just use arrays, to show you how to populate the treeview, and also how to get an event such as a click. Give me an hour, as I've got to reject my friend to do this.... Wave to him now! muttley Vist my blog!UDFs: Opens The Default Mail Client | _LoginBox | Convert Reg to AU3 | BASS.au3 (BASS.dll) (Includes various BASS Libraries) | MultiLang.au3 (Multi-Language GUIs!)Example Scripts: Computer Info Telnet Server | "Secure" HTTP Server (Based on Manadar's Server)Software: AAMP- Advanced AutoIt Media Player | WorldCam | AYTU - Youtube Uploader Tutorials: Learning to Script with AutoIt V3Projects (Hardware + AutoIt): ArduinoUseful Links: AutoIt 1-2-3 | The AutoIt Downloads Section: | SciTE4AutoIt3 Full Version! Link to comment Share on other sites More sharing options...
uruloke Posted July 10, 2008 Author Share Posted July 10, 2008 (edited) For AD stuff, have a look here: http://www.autoitscript.com/forum/index.ph...tory&st=105 I am unable to test AD stuff ATM, but I'll just use arrays, to show you how to populate the treeview, and also how to get an event such as a click. Give me an hour, as I've got to reject my friend to do this.... Wave to him now! muttley Hi, thx Bert for your help. I'm thinking i maybe wrote a bad title for my topic, because my main problem is treeview, not Active Directory (maybe some moderator can change it for "Treeview : Advances Features?? / use for AD browsing" ?) Anyway, if i take 2 minutes to think about it, i think i can solve my problem if someone can give me a solution/exemple for the following issue: I want to obtain the following treeview: ------------------------------- [MyTree] +NodeA + nA_Sub1 - nASubSub1 - nA_Sub2+NodeB - nB_Sub1+NodeC ------------------------------- And a way / a function to obtain one (or both I you can) of the following information, when I Click and select the node "nASubSub1": 1/ result = "nASubSub1 / nA_Sub1 / NodeA" (or NodeA / nA_Sub1 / nASubSub1) 2/ result = "My Hidden Value for nASubSub1" Edited July 10, 2008 by uruloke Link to comment Share on other sites More sharing options...
JFee Posted July 11, 2008 Share Posted July 11, 2008 I actually was just looking for a similar thing (I just want to get the item and its parents), and if you use the user defined treeview controls I think it's possible. I haven't tried it out yet, but if you use _GUICtrlTreeView_Create(...) to make the control, and use _GUICtrlTreeView_AddChild(...) to create children, you should be able to recursively get all of the parents and create a string with something like this: ; assuming you have already generated the treeview, and $selectedItem is handle to the item you're getting info Dim $parentArray(100); 100 is arbitrary, pick a number well above the most parents you expect $i = 0 $parentArray[0] = $selectedItem While _GUICtrlTreeView_GetParentHandle($parentArray[$i]) <> $treeviewControl ; don't mess with things that are children of the root $parentArray[$i] = _GUICtrlTreeView_GetParentHandle($parentArray[$i - 1]) ; handle to the parent... read the handle to get the text $i = $i + 1 Wend Then you will have an array to all of the parent handles, and the number of parents, $i Dunno if its what you're looking for or if it will work but I figured I'd throw it out there Regards,Josh Link to comment Share on other sites More sharing options...
uruloke Posted July 11, 2008 Author Share Posted July 11, 2008 I actually was just looking for a similar thing (I just want to get the item and its parents), and if you use the user defined treeview controls I think it's possible. I haven't tried it out yet, but if you use _GUICtrlTreeView_Create(...) to make the control, and use _GUICtrlTreeView_AddChild(...) to create children, you should be able to recursively get all of the parents and create a string with something like this: ; assuming you have already generated the treeview, and $selectedItem is handle to the item you're getting info Dim $parentArray(100); 100 is arbitrary, pick a number well above the most parents you expect $i = 0 $parentArray[0] = $selectedItem While _GUICtrlTreeView_GetParentHandle($parentArray[$i]) <> $treeviewControl; don't mess with things that are children of the root $parentArray[$i] = _GUICtrlTreeView_GetParentHandle($parentArray[$i - 1]) ; handle to the parent... read the handle to get the text $i = $i + 1 Wend Then you will have an array to all of the parent handles, and the number of parents, $i Dunno if its what you're looking for or if it will work but I figured I'd throw it out there Hi! Thx for your answer, i looked for these user defined functions, and it seems i can use it for what i'm looking for! I will test it next week, and post here my solution if it works muttley Link to comment Share on other sites More sharing options...
JFee Posted July 11, 2008 Share Posted July 11, 2008 No problem. It worked for me, but I only wanted to get the first parent. I messed around with recursively getting all of the parents, but I gave up muttley Good luck! Regards,Josh Link to comment Share on other sites More sharing options...
uruloke Posted July 16, 2008 Author Share Posted July 16, 2008 No problem. It worked for me, but I only wanted to get the first parent. I messed around with recursively getting all of the parents, but I gave up Good luck! Hi! Here is the function I wrote for getting recursively all the parents! muttley You only have to call GetItemAdsPath Func GetItemAdsPath ($hTreeView) Local $Text, $hItem, $hParentItem ; Get Item ID $hItem = _GUICtrlTreeView_GetSelection ($hTreeView) If $hItem <> 0 Then $Text = GetItemRecursiveAdsPath ($hTreeView, $hItem) EndIf Return $Text EndFunc Func GetItemRecursiveAdsPath ($hTreeView, $hItem) Local $Text, $hParentItem ; Get Parent Item ID $hParentItem = _GUICtrlTreeView_GetParentHandle($hTreeView, $hItem) If $hParentItem=0 Then $Text = "OU="&_GUICtrlTreeView_GetText ($hTreeView, $hItem) Else $Text = "OU="&_GUICtrlTreeView_GetText ($hTreeView, $hItem) & "," & GetItemRecursiveAdsPath ($hTreeView, $hParentItem) EndIf Return $Text EndFunc Link to comment Share on other sites More sharing options...
uruloke Posted July 17, 2008 Author Share Posted July 17, 2008 I did an edit and post my solution on the first post muttley Link to comment Share on other sites More sharing options...
LiHang Posted September 16, 2008 Share Posted September 16, 2008 Seems very nice. I'm just working on such script. But I found some errors in your script. If the search is from the base of a AD, it will report wrong DN name. I'll work on it tomorrow. BTW: I have a stupid question. If the OU name has "/" in the name the script will complain. Maybe we need modify it in GetObjectInfo to replace those chars. But I don't know replace to what. Sorry for my ignorance. I'll try it myself first tomorrow. Link to comment Share on other sites More sharing options...
LiHang Posted September 17, 2008 Share Posted September 17, 2008 After research the script, I change below points: 1. To get accurate DN name, in GetItemRecursiveAdsPath Function Change $Text = "OU="&_GUICtrlTreeView_GetText ($hTreeView, $hItem) To: $Text = $strRootContainer; 2. To translate "/" character, in QueryAD Function Remove $CleanAdsPath = StringReplace($CleanAdsPath,"+","\+") Add $CleanAdsPath = StringReplace($CleanAdsPath,"/","\/") 3. To translate "/" character, in GetObjectInfo Function Add $strObjectDN = StringRegExpReplace ($strObjectDN, "/", "\\/") Maybe it's also useful for you. Link to comment Share on other sites More sharing options...
RichMinichiello Posted July 12, 2011 Share Posted July 12, 2011 Sorry to revive a dead thread. This script is 'almost' exactly what I need. I work in an organization that has many sites, all with their own unique network information. This allows me to query the network info from the adapter and identify which OU they are in. I would like to change the $strRootContainer to the user's specific OU. I notice that if I leave it as an OU in the root of the domain, Ex. "OU=North America,DC=Contoso,DC=Com", it works great. If I want to dive deeper and get the location's OU as the root container, Ex. "OU=California,OU=West Coast,OU=North America,DC=Contoso,DC=com", it shows the top item with the plus, then hitting the plus shows the child OUs in that OU...but then selecting a child OU crashes the app. The error is on this command: $objRecordSet = $objCommand.Execute within the QueryAD function. Any ideas? Link to comment Share on other sites More sharing options...
RichMinichiello Posted July 12, 2011 Share Posted July 12, 2011 Sorry to revive a dead thread. This script is 'almost' exactly what I need. I work in an organization that has many sites, all with their own unique network information. This allows me to query the network info from the adapter and identify which OU they are in. I would like to change the $strRootContainer to the user's specific OU. I notice that if I leave it as an OU in the root of the domain, Ex. "OU=North America,DC=Contoso,DC=Com", it works great. If I want to dive deeper and get the location's OU as the root container, Ex. "OU=California,OU=West Coast,OU=North America,DC=Contoso,DC=com", it shows the top item with the plus, then hitting the plus shows the child OUs in that OU...but then selecting a child OU crashes the app. The error is on this command: $objRecordSet = $objCommand.Execute within the QueryAD function. Any ideas? Alright, I think I have it working. It's a hack, but it works. What I saw was the objCommand.commandtext (ldap search) was putting the dc info twice...so, instead of the query being on "LDAP://OU=California,OU=West Coast,OU=North America,DC=Contoso,DC=com", it was doing "LDAP://OU=California,OU=West Coast,OU=North America,DC=Contoso,DC=com,DC=Contoso,DC=com"...so what I did was do a string replace to remove the extra domain name. I changed it here: Func GetItemRecursiveAdsPath ($hTreeView, $hItem) Local $Text, $hParentItem ; Get Parent Item ID $hParentItem = _GUICtrlTreeView_GetParentHandle($hTreeView, $hItem) If $hParentItem=0 Then $Text = $strRootContainer Else $Text = "OU="&_GUICtrlTreeView_GetText ($hTreeView, $hItem) & "," & stringReplace(GetItemRecursiveAdsPath ($hTreeView, $hParentItem),",DC=Contoso,DC=com","") EndIf Return $Text EndFunc If anyone knows a better way, please let me know. Thanks. Link to comment Share on other sites More sharing options...
water Posted July 12, 2011 Share Posted July 12, 2011 There is a successor to adfunctions.au3 available - AD.au3. For download please see my signature. This extended AD UDF has more functions, better error handling, help file, examples, a wiki ... Please have a look at function _AD_GetAllOUs. You can specify a OU where to start. My UDFs and Tutorials: Spoiler UDFs: Active Directory (NEW 2024-07-28 - Version 1.6.3.0) - Download - General Help & Support - Example Scripts - Wiki ExcelChart (2017-07-21 - Version 0.4.0.1) - Download - General Help & Support - Example Scripts OutlookEX (2021-11-16 - Version 1.7.0.0) - Download - General Help & Support - Example Scripts - Wiki OutlookEX_GUI (2021-04-13 - Version 1.4.0.0) - Download Outlook Tools (2019-07-22 - Version 0.6.0.0) - Download - General Help & Support - Wiki PowerPoint (2021-08-31 - Version 1.5.0.0) - Download - General Help & Support - Example Scripts - Wiki Task Scheduler (2022-07-28 - Version 1.6.0.1) - Download - General Help & Support - Wiki Standard UDFs: Excel - Example Scripts - Wiki Word - Wiki Tutorials: ADO - Wiki WebDriver - Wiki Link to comment Share on other sites More sharing options...
RichMinichiello Posted July 14, 2011 Share Posted July 14, 2011 There is a successor to adfunctions.au3 available - AD.au3.For download please see my signature. This extended AD UDF has more functions, better error handling, help file, examples, a wiki ...Please have a look at function _AD_GetAllOUs. You can specify a OU where to start.How would I use that to replace the functions in this script? Do you think it would require a full rewrite? All I really need is a form to pop up with the treeview. Is there an easy way of doing this without rewriting a bunch of code. Link to comment Share on other sites More sharing options...
water Posted July 14, 2011 Share Posted July 14, 2011 (edited) Check this example script. It lists all OUs in a TreeView. If you want to start in a sub OU set $sOU to the FQDN of this OU. expandcollapse popup#include <ad.au3> #include <TreeviewConstants.au3> #include <WindowsConstants.au3> #include <GUIConstants.au3> #Include <GuiTreeView.au3> _AD_Open() Global $sOU = "" Global $sSep = "\" Global $aResult = _AD_GetAllOUs($sOU, $sSep) Global $aTV[$aResult[0][0] + 1] = [$aResult[0][0]] For $i = 1 To $aResult[0][0] $aTemp = StringSplit($aResult[$i][0], $sSep) $aTV[$i] = StringFormat("%" & $aTemp[0] - 1 & "s", "") & "#" & $aTemp[$aTemp[0]] Next _AD_Close() $hMain = GUICreate("Treeview", 742, 683, -1, -1, -1798701056, 256) $hTree = GUICtrlCreateTreeView(6, 6, 600, 650, BitOR($TVS_HASBUTTONS, $TVS_HASLINES, $TVS_LINESATROOT, $TVS_DISABLEDRAGDROP, $TVS_SHOWSELALWAYS), $WS_EX_CLIENTEDGE) TV_Display($aTV) GUISetState() While 1 $Msg = GUIGetMsg() Switch $Msg Case $GUI_EVENT_CLOSE Exit EndSwitch WEnd Func TV_Display($aTree) Dim $hNode[50] ;Keep Parent on Level For $i = 1 To $aTree[0] $line = StringSplit(StringStripCR($aTree[$i]), @TAB) $level = StringInStr($line[1], "#") If $level = 0 Then ExitLoop If $level = 1 Then $hNode[$level] = _GUICtrlTreeView_Add($hTree, 0, StringMid($line[1], $level + 1)) Else $hNode[$level] = _GUICtrlTreeView_AddChild($hTree, $hNode[$level - 1], StringMid($line[1], $level + 1)) EndIf Next EndFunc ;==>TV_Display Edited July 15, 2011 by water My UDFs and Tutorials: Spoiler UDFs: Active Directory (NEW 2024-07-28 - Version 1.6.3.0) - Download - General Help & Support - Example Scripts - Wiki ExcelChart (2017-07-21 - Version 0.4.0.1) - Download - General Help & Support - Example Scripts OutlookEX (2021-11-16 - Version 1.7.0.0) - Download - General Help & Support - Example Scripts - Wiki OutlookEX_GUI (2021-04-13 - Version 1.4.0.0) - Download Outlook Tools (2019-07-22 - Version 0.6.0.0) - Download - General Help & Support - Wiki PowerPoint (2021-08-31 - Version 1.5.0.0) - Download - General Help & Support - Example Scripts - Wiki Task Scheduler (2022-07-28 - Version 1.6.0.1) - Download - General Help & Support - Wiki Standard UDFs: Excel - Example Scripts - Wiki Word - Wiki Tutorials: ADO - Wiki WebDriver - Wiki Link to comment Share on other sites More sharing options...
RichMinichiello Posted July 14, 2011 Share Posted July 14, 2011 (edited) Check this example script. It lists all OUs in a TreeView. Wow..Water, this is great! I should preface this with a little background info. I am not running this in a full Windows OS...This is run during an imaging process within WinPE. I need the ability to select the OU that the computer will be joined into so I can modify my unattend file. I manipulated the code a little bit because I needed to pass alternate credentials to AD since the workstations are not in the domain. While on my dev unit, the credentials appear to work, however, when I run it from the PE environment, it fails. It appears to be failing in the _AD_OPEN function, around line 389 which is $oAD_RootDSE = ObjGet("LDAP://" & $sAD_HostServerParam & "/RootDSE") Is there something that I am missing? Do these functions rely on some other Windows dlls or something that I need to have in the PE environment?I also noticed that the _AD_Open function's parameters are set to ""($sAD_UserIdParam = "")...Maybe I just don't understand it, but wouldn't that make all parameters sent to that function set to "" or is that just the way to define the default parameter if nothing is sent? Thanks for all your help!Rich. Edited July 14, 2011 by RichMinichiello Link to comment Share on other sites More sharing options...
water Posted July 14, 2011 Share Posted July 14, 2011 Please check this It descibes what needs to be installed on Windows PE to access the Active Directory. My UDFs and Tutorials: Spoiler UDFs: Active Directory (NEW 2024-07-28 - Version 1.6.3.0) - Download - General Help & Support - Example Scripts - Wiki ExcelChart (2017-07-21 - Version 0.4.0.1) - Download - General Help & Support - Example Scripts OutlookEX (2021-11-16 - Version 1.7.0.0) - Download - General Help & Support - Example Scripts - Wiki OutlookEX_GUI (2021-04-13 - Version 1.4.0.0) - Download Outlook Tools (2019-07-22 - Version 0.6.0.0) - Download - General Help & Support - Wiki PowerPoint (2021-08-31 - Version 1.5.0.0) - Download - General Help & Support - Example Scripts - Wiki Task Scheduler (2022-07-28 - Version 1.6.0.1) - Download - General Help & Support - Wiki Standard UDFs: Excel - Example Scripts - Wiki Word - Wiki Tutorials: ADO - Wiki WebDriver - Wiki Link to comment Share on other sites More sharing options...
RichMinichiello Posted July 14, 2011 Share Posted July 14, 2011 water...Thank you! I have my work cut out for me. I will get the PE env. setup and get back to you. Thanks again for your help! Rich. Link to comment Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now