none
Bestehendes PowerShell-Loginscript erweitern RRS feed

  • Frage

  • Hallo zusammen,

    ich habe da ein Problem bzw. eine Erweiterung an unserem bestehnden Loginscript auf PS Basis.

    Das Mappen der Netzlaufwerke usw. funktioniert bereits ohne Problem. Was ich nun noch möchte ist das z.B. das Script nicht auf unseren Terminalservern ausgeführt wird. Weiterhin sollte noch ein user-Prüfung stattfindet die ermittelt in welcher OU oder AD Site sich der User befindet und danach die Netzlaufwerke verbindet (werden momentan in Powershell über ein externes XML-File eingelesen, wenn es hier alternativen gibt wäre ich auch dankbar!).

    Kann mir jemand bei diesem anliegen helfen da ich momentan nichts brauchbares gefunden habe?
    Danke im Voraus

     

    Gruß Thorsten

     


    Mittwoch, 4. Januar 2012 10:42

Antworten

  • mhm.. also: wie du auf ein bestimmtes Attribut prüfst, hatte ich dir oben bereits gezeigt. Um also z.b zu prüfen ob sich der User in einer OU namens SRV_Hannover befindet, also so:

     

    $ADsearcher = New-Object System.DirectoryServices.DirectorySearcher 
    $ADsearcher.Filter = "(&(objectCategory=user)(samaccountname=$env:username*))"
    $user = $ADsearcher.findone()
    $path = $user.properties.adspath
    
    if ($path -like "*SRV_Hannover*") {
        "do stuff"
    }
    
    
    

    Grüße, Denniver

     

     


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".


    Mittwoch, 4. Januar 2012 15:30
    Moderator
  • Deine XML-Datei ist so wie sie dasteht ungültig. Zum einen öffnest du jeweils zuerst ein Knoten "locations" und schließt dann einen der heißt "location". Das muß gleich sein. Wenn du dann noch einen Wert direkt zuweisen möchstest, muss dieser extra stehen, also zb.

    <location name="xyz"></location>

    Ich bevorzuge:

     

    <location>
          <name>SRV_Seattle</name>
          <driveletter>R</driveletter>
          <remotepath>\\server2\data</remotepath>
          <altremotepath></altremotepath>
          <memberof></memberof>
    </location>

    ...da sich alle Werte so einfach und einheitlich abfragen lassen. Aber das ist Geschmacksache.

     

    Grundsätzlich solltest du nun, was den Abgleich angeht, mit der Xml-Datei nun anders herum vorgehen:

    Zuerst die XML einlesen und dann jeden location name mit der OU des User vergleichen, also z.b. so:

     

    $script:XML = [xml](Get-Content "yourXML.xml" ) 
    
    foreach	($location in $xml.config.location) {
    	if ($path -like "*$($location.name)*") {
    	  "...do stuff..."
    	}
    }
    

    Und dann muß ich leider nochmal den Oberlehrer geben: Generell fällt auf das du sehr viele Flüchtigkeitsfehler machst. Scripting ist ähnlich wie ein Diktat: jeder winzige Fehler wird gnadenlos bestraft. Oft mit Malfunktion ohne Hinweis auf das Problem. Du kannst dir sehr viel Ärger und Arbeit ersparen, in dem du sorgfältiger arbeitest und alles am Ende noch mal sehr genau kontrollierst.

     

    Grüße, Denniver


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".



    Donnerstag, 5. Januar 2012 14:30
    Moderator
  • Deine XML-Abfrage geht so nicht. Hatte ich nicht auch schon gesagt das du die $networkdrives - Variable weglassen sollst? :)

    So gehts:

    #import the XML File
    $script:XML = [xml](Get-Content "E:\Scripte\Powershell\Win7\configs\ad_groups.xml")
    
    #  <<<<<<<<<<<< gelöscht
    
    foreach ($location in $xml.config.location) {
     if ($path -like "*$($location.name)*") {
    	foreach($drive in $location.networkdrives.networkdrive ){  # <<<<<<<<< geändert
    		#first remove the drive
    		remove-networkdrive $drive.driveletter
    		#map the network drive
    		map-networkdrive $drive.driveletter ($drive.remotepath -replace ("%username%",$env:username))
    	}
     }
    }
    

     

    XMLs sind nicht ganz trivial. Ich würde dir wirklich empfehlen mal den Link den ich oben zu dem Thema gepostet habe, zu studieren. Andernfalls wirst du immer wieder in Probleme laufen.

    Grüße, Denniver

     


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".
    Mittwoch, 11. Januar 2012 13:25
    Moderator

Alle Antworten

  • > Was ich nun noch möchte ist das z.B. das Script nicht auf unseren Terminalservern ausgeführt wird

    Für solche und möglicherweise zukünftige Filter (z.b. auf Usergruppen-Basis) würde ich empfehlen das Logonscript per GPO zu starten und diese entsprechend auf die gewünschten Server zu filtern.

    >Weiterhin sollte noch ein user-Prüfung stattfindet die ermittelt in welcher OU oder AD Site sich
    >der User befindet

    Dieses Script listet alle Attribute des gerade angemeldeten Users. Da kannst du dir rausfiltern was du brauchst:

    $ADsearcher = New-Object System.DirectoryServices.DirectorySearcher 
    $ADsearcher.Filter = "(&(objectCategory=user)(samaccountname=$env:username*))"
    $user = $ADsearcher.findone()
    
    $user.properties | ft 
    
    

    >..Netzlaufwerke verbindet (werden momentan in Powershell über ein externes XML-File eingelesen

    Wenn du damit die Zuordnung User<->Laufwerke meinst, dann ist eine XML-Datei ein guter Weg (vorrausgesetzt da stehen nicht nur drei Einträge drin), auch um schnell und einfach Änderungen machen zu können.

    Grüße, Denniver

     


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".


    Mittwoch, 4. Januar 2012 12:59
    Moderator
  • Hallo Denniver,

    Danke für die schnelle Antwort. Das mit dem GPO habe ich mir auch schon überlegt aber wir wollen eher Powershell. Alternative wäre ja auch GPP dann kann ich ja so ziemlich alles filtern oder?

    Momentan setzen wir ein XML-File für den Hauptstandort ein, weitere sollten folgen aber solange ich das Problem mit der Site bzw. OU Abfrage nicht gelöst habe brauch ich an dieser Baustelle nicht weitermachen.

    Bei dem von dir hinterlegten Scriptcode kann ich ja anschließend eine Abfrage einbauen das wenn ja verwende das XML-file. Aber bei der Anzahl der Außenstellen sehe ich das etwas als problem an.

    Soll ich dann wohl eher auf Windows GPP wechseln?

    Mittwoch, 4. Januar 2012 13:05
  • Meine Bemerkung bezüglich der GPO bezog sich nur auf das Starten des Logonscripts. Wenn du die Verwendung von Powershell als Logonscript allerdings grundsätzlich noch in Frage stellst und meine Meinung hören willst: ich bin da kein Fan von. (ich hatte das hier mal begründet) Kurzform: falls die Funktionalität von GPO CSE nicht ausreicht und es ein Skript sein muß, halte nach wie vor KIX für besser geeignet.

    Möglichereise erledigt deine Entscheidung dann auch die Frage nach der XML Datei. Wenn nicht, müsstest du das mal genauer erläutern: was willst du wann, wem verbinden auf Basis welcher Kriterien? Welche Möglichen Probleme siehst du dabei? etc.

    Grüße, Denniver

     


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".
    Mittwoch, 4. Januar 2012 13:22
    Moderator
  • Hallo Denniver,

    wenn möglich sollte es Powershell sein da das Grundgerüst bereits für unseren Hauptstandort vorhanden ist. Folgendes wollen wir erreichen:

    - Ein Script für alle Niederlassungen (unterschiedliche Netzlaufwerke in den Niederlassungen)
    - Es soll geprüft werden ob es sich bei dem anmeldenden System um ein Citrix-Server handelt, wenn ja script beenden
    - Beim Start des Scriptes soll weiterhin geprüft werden in welcher GPO oder AD Site der User sich befindet (z.B. OU SRV_Hannover)
    - wenn SRV_Hannover dann XML-Datei Hannover.xml einlesen und die darin hinterlegten Laufwerke verbinden, wenn OU SRV_Hamburg dann Hamburg.xml einlesen und diese Laufwerke verbinden

    Das wars fürs erste eigentlich, die Abfrage auf eine Gruppe bezogen habe ich soweit nun hinbekommen aber auf OU bezogen leider noch nicht.
    Wenn dies alles mit Powershell nicht gehen sollte bzw. die verarbeitung des Scriptes auch zu lange dauert würde ich dann auf GPP umsteigen. aber zuerst wie erwähnt der Ansatz per Powershell.

    Das mit den GPO habe ich nun auch soweit verstanden ist ja eigentlich Standard aber wir wollen das zu verwendende Script weiterhin über die AD bei den Usern pflegen. Momentan haben wir halt für jede Niederlassung ein eigenes

     

    Gruß

    Thorsten

    Mittwoch, 4. Januar 2012 13:48
  • Hallo,

    anbei mein erster Versuch mit OU-Abfrage. Leider wie anders zu erwarten erfolglos:(

    function

     

     Get-ADOrganizationalUnit($DNName,$cGroup

    ){

     

     

     

     

    $strFilter =  

     

    "(&(objectCategory=User)(samAccountName=$strName))"

     

     

     

    $DN = $objUser

    .distinguishedName

     

    [Moderator: mehrseitigen Code der Übersichtlichkeit halber gelöscht.]

     

     

     


    Steigerung wäre beim Laufwerksmapping dann das einlesen der XML.

     
    Mittwoch, 4. Januar 2012 14:30
  • Poste das Script bitte nochmal unter Verwendung einer Codebox ( das "</>" - Symbol rechts oben wenn du einen Post erstellst) und ohne Zeilenumbrüche und die ganzen Leerzeilen. Desweiteren: was heist erfolglos? Was geht nicht? Fehlermeldung?

     

    Grüße, Denniver


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".
    Mittwoch, 4. Januar 2012 14:37
    Moderator
  • Hallo,

    anbei mein Script. Sorry das mit dem Code wusste ich nicht!

    # ====================================================
    # Queries user account in AD for user group membership
    # ====================================================
    
    $strName = $env:username
    
    function Get-ADOrganizationalUnit($DNName,$cGroup){
    	
    	$strFilter = "(&(objectCategory=User)(samAccountName=$strName))"
    
    	$objSearcher = New-Object System.DirectoryServices.DirectorySearcher
    	$objSearcher.Filter = $strFilter
    
    	$objPath = $objSearcher.FindOne()
    	$objUser = $objPath.GetDirectoryEntry()
    	$DN = $objUser.distinguishedName
    		
    	$strGrpFilter = "(&(objectCategory=group)(name=$cGroup))"
    	$objGrpSearcher = New-Object System.DirectoryServices.DirectorySearcher
    	$objGrpSearcher.Filter = $strGrpFilter
    	
    	$objGrpPath = $objGrpSearcher.FindOne()
    	
    	If (!($objGrpPath -eq $Null)){
    		
    		$objGrp = $objGrpPath.GetDirectoryEntry()
    		
    		$grpDN = $objGrp.distinguishedName
    		$ADVal = [ADSI]"LDAP://$DN"
    	
    		if ($ADVal.memberOf.Value -eq $grpDN){
    			$returnVal = 1
    			return $returnVal = 1
    		}else{
    			$returnVal = 0
    			return $returnVal = 0
    	
    		}
    	
    	}else{
    			$returnVal = 0
    			return $returnVal = 0
    	
    	}
    		
    }
    
    # ====================================================
    
    
    # Map network drives
    # ====================================================
    
    $result = get-groupMembership $strName "SRV_Hannover"
    if ($result -eq '1') {
    	$(New-Object -ComObject WScript.Network).RemoveNetworkDrive("K:");
    	$(New-Object -ComObject WScript.Network).MapNetworkDrive("K:", "\\server\data");
    }

     

    Das Problem ist das das Laufwerk nicht verbunden wird. Im PowerGui Script Editor erhalte ich keine Fehlermeldung. Es passiert einfach nichts.

    Wie erwähnt Steigerung wäre dann das einlesen der XML-Files!

    Danke für die Hilfe


    $result = get-groupMembership $strName "SRV_Hannover"
    Heist natürlich auf die OU bezogen!
    Mittwoch, 4. Januar 2012 14:45
  • Abgesehen davon das deine Funktion " Get-ADOrganizationalUnit" heisst und du dann eine Funktion namens "get-groupMembership" aufrufst (was natürlich nicht gehen kann :-) ) - was willst du denn eigentlich auslesen, eine Gruppenmitgliedschaft oder die OU in der sich der User befindet?

    ...und was das auslesen der XML betrifft: ich dachte das machst du bereits? ("werden momentan in Powershell über ein externes XML-File eingelesen?

    Wenn nicht, gibts hier eine gute Anleitung dazu.

    Darüber hinaus wundert mich warum für jeden Standort eine eigene XML hast. Die XML-Struktur eignet sich doch hervorragend für jeden Standort einen Knoten in der gleichen XML anzulegen.

    Grüße, Denniver


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".




    Mittwoch, 4. Januar 2012 15:13
    Moderator
  • Hallo Denniver,

    das mit dem GroupMemebership habe ich auch gemerkt. Hatte das was falsches in der Zwischenablage.
    Auslesen möchte ich die OU in der Sich der User befindet. Das mit der Gruppe habe ich auch schon getestet und funktionier. Nur kann ja ein User Mitglied meherer Gruppen sein und das könnte bei einem internationalen Umfeld etwas probleme auslösen.

    Mittwoch, 4. Januar 2012 15:18
  • Hallo,

    bis lang habe ich nur eine XML. Aber die Idee mit einer hört sich auch gut an. Denke das sind aber feinheiten die nach der generellen Funktion angepasst werden können.

    Den Bereich XML habe ich momentan mal ausgelassen werde ich aber sobald die Abfrage bzw. Prüfung funzt wieder integrieren.

    Gruß

     


    Mittwoch, 4. Januar 2012 15:21
  • mhm.. also: wie du auf ein bestimmtes Attribut prüfst, hatte ich dir oben bereits gezeigt. Um also z.b zu prüfen ob sich der User in einer OU namens SRV_Hannover befindet, also so:

     

    $ADsearcher = New-Object System.DirectoryServices.DirectorySearcher 
    $ADsearcher.Filter = "(&(objectCategory=user)(samaccountname=$env:username*))"
    $user = $ADsearcher.findone()
    $path = $user.properties.adspath
    
    if ($path -like "*SRV_Hannover*") {
        "do stuff"
    }
    
    
    

    Grüße, Denniver

     

     


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".


    Mittwoch, 4. Januar 2012 15:30
    Moderator
  • OK dann hatte ich da wohl dn falschen Denkansatz!
    Werde ich doch gleich mal testen.

    Danke

    Mittwoch, 4. Januar 2012 15:32
  • Hallo Denniver,

    danke nochmals für den Tipp jetzt funzt es (mit meinem Account zumindest): Jetzt muss ich mir nur noch die sache mit dem XML-anschauen wie ich das am besten gelöst bekomme. Der nächste Schritt ist dann noch die Prüfung des OS.
    Gruß

    Thorsten

    Mittwoch, 4. Januar 2012 15:46
  • Am 04.01.2012 schrieb Thorsten Hanke:

    Das Mappen der Netzlaufwerke usw. funktioniert bereits ohne Problem. Was ich nun noch möchte ist das z.B. das Script nicht auf unseren Terminalservern ausgeführt wird. Weiterhin sollte noch ein user-Prüfung stattfindet die ermittelt in welcher OU oder AD Site sich der User befindet und danach die Netzlaufwerke verbindet (werden momentan in Powershell über ein externes XML-File eingelesen, wenn es hier alternativen gibt wäre ich auch dankbar!).

    Ich habe den Thread nicht vollständig gelesen, aber IMHO sind die
    Group Policy Preferences mit der Zielgruppenadressierung in diesem
    Fall wohl die bessere und einfachere Lösung.
    http://www.gruppenrichtlinien.de/Vista/GPP_Group_Policy_Preferences.htm

    Servus
    Winfried


    Connect2WSUS: http://www.grurili.de/tools/Connect2WSUS.exe
    GPO's: http://www.gruppenrichtlinien.de
    Community Forums NNTP Bridge: http://communitybridge.codeplex.com/

    Mittwoch, 4. Januar 2012 19:05
  • Hallo Winfried,

    vor der Entscheidung bin ich auch schon gestanden. Momentan wollen wir es aber erst über Powershell versuchen, alternative wäre dann zum Vergleich auch noch GPP.
    Danke trotzdem für den Tipp

    Gruß

    Thorsten

    Donnerstag, 5. Januar 2012 07:20
  • Hallo nochmal,

    ich glaube ich benötige doch noch mal euere Hilfe!

    Wie gesagt funktioniert die Abfrage auf OU nun ja, nun habe ich aber das Problem wie ich am besten auf OU bezogen die Netzlaufwerke verbunden bekomme? Angedacht war ja per XML aber leider bekomme ich das nicht hin.
    Kann mir jemand weiterhelfen?
    Danke im Voraus.


    Gruß

    Donnerstag, 5. Januar 2012 08:15
  • Hallo noch mal,

    so ich bin nun mal wieder ein Stückchen weiter (langsam ernährt sich das Eichhörnchen!).

    Das einlesen der XML Funktioniert nun, leider habe ich noch das Problem das wenn die Gruppe z.B. nicht übereinstimmt soll er ja die nächste Prüfung durchführen. Wie bekomme ich das denn am besten gelöst?
    Anbei mein PS-Script und die dazugehörige XML.

    Danke

    ###################################################################
    # Check AD OU Membership                                          #
    ###################################################################
    
    	
    	$ADsearcher = New-Object System.DirectoryServices.DirectorySearcher 
    	$ADsearcher.Filter = "(&(objectCategory=user)(samaccountname=$env:username*))"
    	$user = $ADsearcher.findone()
    	$path = $user.properties.adspath
    	
    if ($path -like "*SRV_Hannover*") {
    	#read invocation path
    	$path = Split-Path -Path $MyInvocation.MyCommand.Definition -Parent
    	#get config file
    	$config_file = $path + "\configs\test.xml"
    	#import the XML File
    	$xml = [xml](get-content $config_file)
    	
    	
    ###################################################################
    # Map Network drives	                                          #
    ###################################################################
    
    	#save the networkdrive config in the variable
    	$networkdrives = $xml.config.locations.networkdrives.get_ChildNodes()
    	#connect each networkdrive
    	
    foreach($drive in $networkdrives){
    	#first remove the drive
    	remove-networkdrive $drive.driveletter
    	#if you don't have to be in a special group or if you are member of the group
    	if(($drive.memberof -eq "") -or (member-of $drive.memberof)){
    		#map the network drive
    		map-networkdrive $drive.driveletter ($drive.remotepath -replace ("%username%",$env:username))
    		#if there is an alternative path, connect that
    	}elseif($drive.altremotepath -ne ""){
    		#map network drive
    		map-networkdrive $drive.driveletter ($drive.altremotepath -replace ("%username%",$env:username))
    	}
    }
    	
    }

    XML

    <?xml version="1.0" encoding="utf-8"?> 
    <config>
    <locations="SRV_Hannover">
          <networkdrives>
          <driveletter>K</driveletter>
          <remotepath>\\server\data</remotepath>
          <altremotepath></altremotepath>
          <memberof></memberof>
         </networkdrives>
    </location>
    <locations="SRV_Bochum">
          <networkdrives>
          <driveletter>F</driveletter>
          <remotepath>\\server1\data</remotepath>
          <altremotepath></altremotepath>
          <memberof></memberof>
         </networkdrives>
    </location>
    <locations="SRV_Seattle">
          <networkdrives>
          <driveletter>R</driveletter>
          <remotepath>\\server2\data</remotepath>
          <altremotepath></altremotepath>
          <memberof></memberof>
         </networkdrives>
    </location>
    </config>      



     

     

    Donnerstag, 5. Januar 2012 10:37
  • Deine XML-Datei ist so wie sie dasteht ungültig. Zum einen öffnest du jeweils zuerst ein Knoten "locations" und schließt dann einen der heißt "location". Das muß gleich sein. Wenn du dann noch einen Wert direkt zuweisen möchstest, muss dieser extra stehen, also zb.

    <location name="xyz"></location>

    Ich bevorzuge:

     

    <location>
          <name>SRV_Seattle</name>
          <driveletter>R</driveletter>
          <remotepath>\\server2\data</remotepath>
          <altremotepath></altremotepath>
          <memberof></memberof>
    </location>

    ...da sich alle Werte so einfach und einheitlich abfragen lassen. Aber das ist Geschmacksache.

     

    Grundsätzlich solltest du nun, was den Abgleich angeht, mit der Xml-Datei nun anders herum vorgehen:

    Zuerst die XML einlesen und dann jeden location name mit der OU des User vergleichen, also z.b. so:

     

    $script:XML = [xml](Get-Content "yourXML.xml" ) 
    
    foreach	($location in $xml.config.location) {
    	if ($path -like "*$($location.name)*") {
    	  "...do stuff..."
    	}
    }
    

    Und dann muß ich leider nochmal den Oberlehrer geben: Generell fällt auf das du sehr viele Flüchtigkeitsfehler machst. Scripting ist ähnlich wie ein Diktat: jeder winzige Fehler wird gnadenlos bestraft. Oft mit Malfunktion ohne Hinweis auf das Problem. Du kannst dir sehr viel Ärger und Arbeit ersparen, in dem du sorgfältiger arbeitest und alles am Ende noch mal sehr genau kontrollierst.

     

    Grüße, Denniver


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".



    Donnerstag, 5. Januar 2012 14:30
    Moderator
  • Danke ich denke so bekomme ich es hin, ich weis das Sauber arbeiten die halbe Miete ist aber wenn man das parallel zu anderen scahen macht?

    Naja ich gelobe Besserung!

    Schönes Wochenende.

    Donnerstag, 5. Januar 2012 14:35
  • Hallo Denniver,

    sorry das ich dich nochmal nerven muss aber ich habe nochmals eine kurze Frage.
    Ich habe nun alles soweit angepasst und umgestellt. ich habe noch das Problem das in dem Forech Bereich nach Abfrage der Gruppe in der XML nicht weiterkomme.

    MeiN script sieht nun so aus:

    $ADsearcher = New-Object System.DirectoryServices.DirectorySearcher
    $ADsearcher.Filter = "(&(objectCategory=user)(samaccountname=$env:username*))"
    $user = $ADsearcher.findone()
    $path = $user.properties.adspath



    $script:XML = [xml](Get-Content "E:\Scripte\Powershell\Win7\configs\AD_Groups.xml" )

    foreach ($location in $xml.config.location) {
    if ($path -like "*$($location.name)*") {

    hier sollte nun ja der Aufruf stehen indem die Netzlaufwerke verbunden werden!

    }

    Kannst du mir hier nochmals weiterhelfen? ich stehe irgendwie auf dem Schlauch!!
    Danke im Voraus.


    Gruß

    Thorsten

     


    Montag, 9. Januar 2012 12:29
  • Wenn die XML wie in meinem Beispiel aufgebaut ist, mit Net use und invoke-expression:

    $script:XML = [xml](Get-Content ""E:\Scripte\Powershell\Win7\configs\AD_Groups.xml" )
    
    foreach ($location in $xml.config.location) {
     if ($path -like "*$($location.name)*") {
         Invoke-Expression "net use $($location.driveletter): $($location.remotepath)"
     }
    }
    


    Die Networkdrive-Variable ist überflüssig.

    Grüße, Denniver


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".


    Montag, 9. Januar 2012 12:44
    Moderator
  • Hallo,

    vielen Dank nun erhalte ich den Fehler :

    net.exe : Systemfehler 67 aufgetreten.

    Bei Zeile:1 Zeichen:4

    + net <<<< use :

    + CategoryInfo : NotSpecified: (Systemfehler 67 auf

    getreten.:String) [], RemoteException

    + FullyQualifiedErrorId : NativeCommandError

     

    Der Netzwerkname wurde nicht gefunden.

    Hast du noch eine Idee?
    Danek

    Montag, 9. Januar 2012 12:56
  • Hallo Denniver,

     

    so nun nochmal ich. Mein Script läuft nun (bis auf eine kleine Kleinigkeit) dazu komme ich gleich.

    Anbei falls jemand interesse hat:

    cls
    ###################################################################
    # Map Network Drives                                              #
    ###################################################################
    function map-networkdrive([char]$driveletter,[string]$remotepath){
    	trap {
    		#write error
    		Write-Host "Fehler beim verbinden der Netzlaufwerke!"	
    	}
    	#create network object
    	$network = new-object -com WScript.Network
    	#map the network drive
    	$network.MapNetworkDrive($driveletter + ":", $remotepath)
    }
    ###################################################################
    
    
    
    ###################################################################
    # Removetwork Drives                                              #
    ###################################################################
    function remove-networkdrive([char]$driveletter){
    	trap {
    		#ignore errors
    		continue
    	}
    	#create network object
    	$network = new-object -com WScript.Network
    	#remove the network drive
    	$network.RemoveNetworkDrive($driveletter + ":", $true, $true)
    }
    ###################################################################
    
    
    
    ###################################################################
    # check member of                                                 #
    ###################################################################
    function member-of([string]$groupname){
    	trap {
    		#write error
    		Write-Host "Fehler beim auslesen der Gruppe!"
    	}
    	#set root domain
    	$objDomain = New-Object System.DirectoryServices.DirectoryEntry("LDAP://dc=herrenknecht,dc=com")
    	#do a new Search in the Active Directory
    	$objSearcher = New-Object System.DirectoryServices.DirectorySearcher
    	#use the root domain
    	$objSearcher.SearchRoot = $objDomain
    	#filter for the current user
    	$objSearcher.Filter = "(&(objectCategory=User)(sAMAccountName=$env:username))"
    	#process the search
    	$objPath = $objSearcher.FindOne()
    	#get the user object
    	$objUser = $objPath.GetDirectoryEntry()
    	
    	#do a new search for the group
    	$objSearcher = New-Object System.DirectoryServices.DirectorySearcher
    	#use the root domain
    	$objSearcher.SearchRoot = $objDomain
    	#filter for the specified group
    	$objSearcher.Filter = "(&(objectCategory=Group)(Name=$groupname))"
    	#process the search
    	$objPath = $objSearcher.FindOne()
    	#get the group object
    	$objGroup = $objPath.GetDirectoryEntry()
    	
    	#check if the user is member of the group
    	if($objGroup.member -contains ($objUser.Path).Substring(7)){
    		#return true if it is a member
    		return $true
    	}
    }
    ###################################################################
    
    
    $ADsearcher = New-Object System.DirectoryServices.DirectorySearcher 
    $ADsearcher.Filter = "(&(objectCategory=user)(samaccountname=$env:username*))"
    $user = $ADsearcher.findone()
    $path = $user.properties.adspath
    
    #import the XML File
    $script:XML = [xml](Get-Content "E:\Scripte\Powershell\Win7\configs\ad_groups.xml")
    
    #save the networkdrive config in the variable
    $networkdrives = $xml.config.networkdrives.get_ChildNodes()
    
    foreach ($location in $xml.config.location) {
    if ($path -like "*$(location.name)*") {
    	foreach($drive in $networkdrives){
    	#first remove the drive
    	remove-networkdrive $drive.driveletter
    	#if you don't have to be in a special group or if you are member of the group
    	if(($drive.memberof -eq "") -or (member-of $drive.memberof)){
    		#map the network drive
    		map-networkdrive $drive.driveletter ($drive.remotepath -replace ("%username%",$env:username))
    		#if there is an alternative path, connect that
    	}elseif($drive.altremotepath -ne ""){
    		#map network drive
    		map-networkdrive $drive.driveletter ($drive.altremotepath -replace ("%username%",$env:username))
    	}
    }
    }
    }

     

    Das Problem das ich noch habe ist das über die Abfrage if ($path -like "*$(location.name)*") ich eine Meldung erhalte das das CmdLet nicht existiert.Wenn ich hier eine existierende Gruppe aus meine XML direkt eingebe funzt alles ohne Probleme.

    Falls mir jemand bei diesem Problem noch helfen kann wäre ich mehr als dankbar.

    gruß

    Thorsten und danke für die tiefgehende Hilfe!!!


    Montag, 9. Januar 2012 16:08
  • >Das Problem das ich noch habe ist das über die Abfrage if ($path -like "*$(location.name)*") ich eine Meldung erhalte das das CmdLet nicht existiert

    Deine Zeile: if ($path -like "*$(location.name)*")

    Meine Zeile: if ($path -like "*$($location.name)*")

    Grüße, Denniver


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".
    Montag, 9. Januar 2012 16:27
    Moderator
  • Naja, wer lesen kann ist klar im Vorteitl.Hab das ganze mehrfach geprüft aber immer übersehen.
    Werde ich morgen gleich mal testen

     

    Danke

    Montag, 9. Januar 2012 19:24
  • Hallo zusammen,

    ich habe da noch ein kleines Problem beim einlesen der XML mit mehreren Locations.

    Anbei meine XML und die Fehlermeldung in Powershell. Leider kann ich momentan das Problem nicht nachvollziehen:

    XML-Datei
    <?xml version="1.0" encoding="utf-8"?> 
    <config>
     <location>
       <name>SRV_Seattle</name>
    	<networkdrives>
    		<networkdrive>
    		<driveletter>M</driveletter>
    		<remotepath>\\server1\group</remotepath>
    		<altremotepath></altremotepath>
    		</networkdrive>
    		<networkdrive>
    		<driveletter>L</driveletter>
    		<remotepath>\\server1\group</remotepath>
    		<altremotepath></altremotepath>
    		</networkdrive>
    	</networkdrives>
     </location>
     <location>
      <name>SRV_Seattle</name>
    	<networkdrives>
    		<networkdrive>
    		<driveletter>M</driveletter>
    		<remotepath>\\server2\group</remotepath>
    		<altremotepath></altremotepath>
    		</networkdrive>
    		<networkdrive>
    		<driveletter>L</driveletter>
    		<remotepath>\\server2\group</remotepath>
    		<altremotepath></altremotepath>
    		</networkdrive>
    	</networkdrives>
     </location>
    </config>   
    

     

    Powershell Script:

    ###################################################################
    # Map Network Drives                                              #
    ###################################################################
    function map-networkdrive([char]$driveletter,[string]$remotepath){
    	trap {
    		#write error
    		Write-Host "Fehler beim verbinden der Netzlaufwerke!"	
    	}
    	#create network object
    	$network = new-object -com WScript.Network
    	#map the network drive
    	$network.MapNetworkDrive($driveletter + ":", $remotepath)
    }
    ###################################################################
    
    
    ###################################################################
    # Removetwork Drives                                              #
    ###################################################################
    function remove-networkdrive([char]$driveletter){
    	trap {
    		#ignore errors
    		continue
    	}
    	#create network object
    	$network = new-object -com WScript.Network
    	#remove the network drive
    	$network.RemoveNetworkDrive($driveletter + ":", $true, $true)
    }
    ###################################################################
    
    
    ###################################################################
    # check member of                                                 #
    ###################################################################
    function member-of([string]$groupname){
    	trap {
    		#write error
    		Write-Host "Fehler beim auslesen der Gruppe!"
    	}
    	#set root domain
    	$objDomain = New-Object System.DirectoryServices.DirectoryEntry("LDAP://dc=herrenknecht,dc=com")
    	#do a new Search in the Active Directory
    	$objSearcher = New-Object System.DirectoryServices.DirectorySearcher
    	#use the root domain
    	$objSearcher.SearchRoot = $objDomain
    	#filter for the current user
    	$objSearcher.Filter = "(&(objectCategory=User)(sAMAccountName=$env:username))"
    	#process the search
    	$objPath = $objSearcher.FindOne()
    	#get the user object
    	$objUser = $objPath.GetDirectoryEntry()
    	
    	#do a new search for the group
    	$objSearcher = New-Object System.DirectoryServices.DirectorySearcher
    	#use the root domain
    	$objSearcher.SearchRoot = $objDomain
    	#filter for the specified group
    	$objSearcher.Filter = "(&(objectCategory=Group)(Name=$groupname))"
    	#process the search
    	$objPath = $objSearcher.FindOne()
    	#get the group object
    	$objGroup = $objPath.GetDirectoryEntry()
    	
    	#check if the user is member of the group
    	if($objGroup.member -contains ($objUser.Path).Substring(7)){
    		#return true if it is a member
    		return $true
    	}
    }
    ###################################################################
    
    
    $ADsearcher = New-Object System.DirectoryServices.DirectorySearcher 
    $ADsearcher.Filter = "(&(objectCategory=user)(samaccountname=$env:username*))"
    $user = $ADsearcher.findone()
    $path = $user.properties.adspath
    
    #import the XML File
    $script:XML = [xml](Get-Content "E:\Scripte\Powershell\Win7\configs\ad_groups.xml")
    
    #save the networkdrive config in the variable
    $networkdrives = $xml.config.location.get_ChildNodes()
    
    foreach ($location in $xml.config.location) {
     if ($path -like "*$($location.name)*") {
    	foreach($drive in $networkdrives){
    		#first remove the drive
    		remove-networkdrive $drive.driveletter
    		#map the network drive
    		map-networkdrive $drive.driveletter ($drive.remotepath -replace ("%username%",$env:username))
    	}
    
    }
    }
    
    


    Fehlermeldung Powershell:

    Sie k

     

    önnen keine Methode für einen Ausdruck mit dem Wert NULL

    aufrufen.

    Bei Zeile:93 Zeichen:67

    + $networkdrives = $xml.config.location.networkdrives.get_Chil

    dNodes <<<< ()

    + CategoryInfo : InvalidOperation: (get_ChildNod

    es:String) [], RuntimeException

    + FullyQualifiedErrorId : InvokeMethodOnNull

     

     

     

     

    Danke im Voraus

    Gruß Thorsten

     

     

     

     

    Mittwoch, 11. Januar 2012 09:13
  • Deine XML-Abfrage geht so nicht. Hatte ich nicht auch schon gesagt das du die $networkdrives - Variable weglassen sollst? :)

    So gehts:

    #import the XML File
    $script:XML = [xml](Get-Content "E:\Scripte\Powershell\Win7\configs\ad_groups.xml")
    
    #  <<<<<<<<<<<< gelöscht
    
    foreach ($location in $xml.config.location) {
     if ($path -like "*$($location.name)*") {
    	foreach($drive in $location.networkdrives.networkdrive ){  # <<<<<<<<< geändert
    		#first remove the drive
    		remove-networkdrive $drive.driveletter
    		#map the network drive
    		map-networkdrive $drive.driveletter ($drive.remotepath -replace ("%username%",$env:username))
    	}
     }
    }
    

     

    XMLs sind nicht ganz trivial. Ich würde dir wirklich empfehlen mal den Link den ich oben zu dem Thema gepostet habe, zu studieren. Andernfalls wirst du immer wieder in Probleme laufen.

    Grüße, Denniver

     


    Blog: http://bytecookie.wordpress.com

    Hilf mit und markiere hilfreiche Beiträge als "Hilfreich" und Beiträge die deine Frage ganz oder teilweise beantwortet haben als "Antwort".
    Mittwoch, 11. Januar 2012 13:25
    Moderator
  • Hallo,

    Danke danke jetzt funzt es. Ich muss mich denke ich in beide Themen mal sehr sehr tief einarbeiten.

    Was man da alles für Möglichkeiten hat

    Gruß

    Thorsten

    Mittwoch, 11. Januar 2012 14:28