none
ACL Verknpfungen bzw. mit ACL auslesen RRS feed

  • Frage

  • Hallo,

    ich habe ein Probelm an dem ich jetzt schon seit geraum Zeit tüftle, ich würde gernen TerminalServer Profile die älter sind also 6 Monate mit Verzeichnis, LastWriteTime, Identität(IdentityReference) des Berechtigten, Email des Berechtigen und Name/Vorname in eine Excel Liste schreiben lassen, jedoch bekomme ich das nicht so ganz hin deshalb benötige ich hilfe dabei.

    Was ich beher schon habe:

    ls \\Server\TS-Profile$ | where { $_.LastWriteTime -lt (get-date).addmonths(-6) } | where {$_.attributes -match "Directory"} |select FullName,LastWriteTime,@{Expression={(Get-Acl | Select-Object Path -ExpandProperty Access | where { $_.IdentityReference -like "Domain\Spain*" -or $_.IdentityReference -like "Domain\Germany*" } | Select-Object @{n='Mail';e={ (Get-ADUser -Properties * -Identity $_.IdentityReference.Value.Split("\")[1]).mail }}, @{n='Surname';e={ (Get-ADUser -Properties * -Identity $_.IdentityReference.Value.Split("\")[1]).Surname }}) }} | Export-Csv -Path UNCPath:\Citrix-6Months"-"_$((Get-Date).ToString('MM-dd-yyyy_hh-mm-ss')).csv -notypeinformation -delimiter ";" -encoding utf8;

    PS. das script läuft druch ich bekomme aber Statt Email und Nachname immer nur :

     @{ (Get-ADUser -Properties * -Identity $_.IdentityReference.Value.Split("\")[1]).Surname =Mueller}

    oder

    System.Security.AccessControl.FileSystemAccessRule 

    Hilfe wäre echt super.

    Mittwoch, 7. August 2013 15:30

Antworten

  • Ich habe mich da mal durchgebissen....

    So müsst es gehen:

    # Durch TAB Einrückungen wird der Code leserlicher.
    # Eine schliessende Klammer steht dann immer auf der selben ebenen wie das öffnende Komando.
    # Kommentare im Code sind SEHR, SEHR wichtig! ;-)
    
    # damit das Datum nich bei jedem Ordner neu berechnet wird,
    # wird es hier nur einmal berechnet
    $OldDate = (get-date).addmonths(-6)
    
    Get-ChildItem '\\Server\TS-Profile$' | Where-Object { ($_.PSIsContainer -eq $True) -and ($_.LastWriteTime -lt $OldDate)} | ForEach-Object {
    
    	# Alle Usernamen von den ACL extrahieren.(Für die User aus Spanien und Deutschland)
    	# pipeline übersichtlich eingerückt
    	$UserNames = Get-Acl $_.Fullname |
    		Select-Object -ExpandProperty Access|
    			Where-Object { $_.IdentityReference -like "Domain\Spain*" -or $_.IdentityReference -like "Domain\Germany*"} |
    				ForEach-Object {$_.IdentityReference.Value.split('\')[1]} 
    	
    	# Für jeden User die E-Mail und den Nachnamen aus dem Aktive Directory holen
    	# ForEach Schleife übersichtlich eingerückt
    	ForEach($UserName in $UserNames) {
    		$ADUser = Get-ADUser -Identity $UserName -Properties mail
    
    		# Für jeden User die gesammelten Daten in einem Objekt vereinen und ausgeben
    		# -Property hashtable übersichtlich eingerückt
    		New-Object -TypeName PSObject -Property @{	Path=$_.Fullname;
    													LastWriteTime=$_.LastWriteTime;
    													Mail = $ADUser.Mail;
    													Username = $UserName;
    													Surname = $ADUser.Surname;
    													GivenName = $ADUser.GivenName
    													} # ende -Property
    	} # ende ForEach $UserName
    } <# ende ForEach-Object; Ausgabe an Export-Csv weiterreichen  #> |
    	Export-Csv -Path UNCPath:\Citrix-6Months"-"_$((Get-Date).ToString('MM-dd-yyyy_hh-mm-ss')).csv -notypeinformation -delimiter ";" -encoding utf8

    Es gibt in der PowerShell 2 Verschieden ForEach ! Da musst du aufpassen! Einmal das ForEach-Object { ... } Cmdlet und die ForEach ($File in Files) { ... } Schleife ! Gemeinerweise hat das ForEach-Object { ... } Cmdlet einen Alias der ForEach { ... } heisst! Da kommt man schnell durcheinander! Der unterschied ist das ForEach-Object { ... } Cmdlet wird in der Pipeline eingesetzt und die ForEach ($File in Files) { ... } Schleife nicht!


    Please click “Mark as Answer” if my post answers your question and click “Vote As Helpful” if my Post helps you.
    Bitte markiere hilfreiche Beiträge von mir als “Als Hilfreich bewerten” und Beiträge die deine Frage ganz oder teilweise beantwortet haben als “Als Antwort markieren”.
    My PowerShell Blog http://www.admin-source.info
    [string](0..21|%{[char][int]([int]("{0:d}" -f 0x28)+('755964655967-86965747271757624-8796158066061').substring(($_*2),2))})-replace' '
    German ? Come to German PowerShell Forum!



    Donnerstag, 8. August 2013 11:40

Alle Antworten

  • Hallo Alex!

    Bitte benutze die Funktion „Codeblock einfügen “ („</>“ -Symbol oben rechts) hier im Forum um Code zu posten!

    Ein Code muss nicht nur funktionieren, er muss auch leicht verständlich, leicht lesbar und leicht zu warten (Änderungen) seine. Wenn du einen Code in einem 1/2 Jahr wieder siehst musst auch du Ihn wieder neu verstehen. Oder eine fremde Person braucht diesen Code was dann?

    Schlecht geschriebener Code ist sehr schwer zu verstehen, dadurch erhöht sich auch die Fehler Quote und die Zeit die man Braucht um Fehler zu finden!
    Dadurch verschwendet man nicht  nur seine eigen Zeit und Nerven sondern auch die von denen, die dir hier helfen möchten / sollen.
    Die Zeit die man braucht den Code (immer wieder neu) zu verstehen und Fehler zu suchen, sollte man gleich in besseren Code investieren, das Zahlt sich aus!

    Sorry aber dein Code ist in diesem Aspekt echt mega gruselig und ein Musterbeispiel wie man es nicht machen sollte!

    Und für uns hier ist dein Code so schlimm verschachtelt und  gar nicht zu lesen!
    Ich kann dir da nicht helfen!

    Ich habe hier einige Tipps für dich:

    1. Auch wenn man in PowerShell fast jeden Code in eine Zeile schreiben kann, sollte man daraus keinen Wettbewerb machen. Der Code wird dadurch schwerer zu verstehen und es dient nicht der Lesbarkeit.

    2. Zwei Where-Object Filter hintereinander zu schalten funktioniert zwar, ist aber Unsinn und kostet unnötig rechenzeit! Dafür gibt es die Operatoren –and und –or !

    3. Directorys Filtert man in der PowerShell mit dem $_.PSIsContainer Attribut dies ist schneller als das -match auf einen String

    4. Zwischenergebnisse sollte man in Variablen ablegen, dadurch spart man sich komplizierte Verschachtelungen.

    5. Versuche statt des Select-Object mit den Expressions, Zwischenergebnisse zu bilden und das ForEach-Object Cmdlet zu nehmen oder eine ForEach Schleife.

    6. in einem Script sollte man niemals die Alias Namen oder andere Abkürzungen benutzen. Man sollte die Cmdlet Namen und die Parameter immer ausschreiben, das vermeidet zukünftige Inkompatibilitäten!

    7. Nutze DRY (Dont Repeat Yourself). Das heist: Wenn man eine Code (Abschnitt) mehr als einmal braucht, dann Nutzt man entweder ein wieder verwendbares Zwischenergebnis oder eine Funktion.


    Please click “Mark as Answer” if my post answers your question and click “Vote As Helpful” if my Post helps you.
    Bitte markiere hilfreiche Beiträge von mir als “Als Hilfreich bewerten” und Beiträge die deine Frage ganz oder teilweise beantwortet haben als “Als Antwort markieren”.
    My PowerShell Blog http://www.admin-source.info
    [string](0..21|%{[char][int]([int]("{0:d}" -f 0x28)+('755964655967-86965747271757624-8796158066061').substring(($_*2),2))})-replace' '
    German ? Come to German PowerShell Forum!



    • Bearbeitet Peter Kriegel Donnerstag, 8. August 2013 07:25 SADSD
    Donnerstag, 8. August 2013 07:01
  • Ich habe mich da mal durchgebissen....

    So müsst es gehen:

    # Durch TAB Einrückungen wird der Code leserlicher.
    # Eine schliessende Klammer steht dann immer auf der selben ebenen wie das öffnende Komando.
    # Kommentare im Code sind SEHR, SEHR wichtig! ;-)
    
    # damit das Datum nich bei jedem Ordner neu berechnet wird,
    # wird es hier nur einmal berechnet
    $OldDate = (get-date).addmonths(-6)
    
    Get-ChildItem '\\Server\TS-Profile$' | Where-Object { ($_.PSIsContainer -eq $True) -and ($_.LastWriteTime -lt $OldDate)} | ForEach-Object {
    
    	# Alle Usernamen von den ACL extrahieren.(Für die User aus Spanien und Deutschland)
    	# pipeline übersichtlich eingerückt
    	$UserNames = Get-Acl $_.Fullname |
    		Select-Object -ExpandProperty Access|
    			Where-Object { $_.IdentityReference -like "Domain\Spain*" -or $_.IdentityReference -like "Domain\Germany*"} |
    				ForEach-Object {$_.IdentityReference.Value.split('\')[1]} 
    	
    	# Für jeden User die E-Mail und den Nachnamen aus dem Aktive Directory holen
    	# ForEach Schleife übersichtlich eingerückt
    	ForEach($UserName in $UserNames) {
    		$ADUser = Get-ADUser -Identity $UserName -Properties mail
    
    		# Für jeden User die gesammelten Daten in einem Objekt vereinen und ausgeben
    		# -Property hashtable übersichtlich eingerückt
    		New-Object -TypeName PSObject -Property @{	Path=$_.Fullname;
    													LastWriteTime=$_.LastWriteTime;
    													Mail = $ADUser.Mail;
    													Username = $UserName;
    													Surname = $ADUser.Surname;
    													GivenName = $ADUser.GivenName
    													} # ende -Property
    	} # ende ForEach $UserName
    } <# ende ForEach-Object; Ausgabe an Export-Csv weiterreichen  #> |
    	Export-Csv -Path UNCPath:\Citrix-6Months"-"_$((Get-Date).ToString('MM-dd-yyyy_hh-mm-ss')).csv -notypeinformation -delimiter ";" -encoding utf8

    Es gibt in der PowerShell 2 Verschieden ForEach ! Da musst du aufpassen! Einmal das ForEach-Object { ... } Cmdlet und die ForEach ($File in Files) { ... } Schleife ! Gemeinerweise hat das ForEach-Object { ... } Cmdlet einen Alias der ForEach { ... } heisst! Da kommt man schnell durcheinander! Der unterschied ist das ForEach-Object { ... } Cmdlet wird in der Pipeline eingesetzt und die ForEach ($File in Files) { ... } Schleife nicht!


    Please click “Mark as Answer” if my post answers your question and click “Vote As Helpful” if my Post helps you.
    Bitte markiere hilfreiche Beiträge von mir als “Als Hilfreich bewerten” und Beiträge die deine Frage ganz oder teilweise beantwortet haben als “Als Antwort markieren”.
    My PowerShell Blog http://www.admin-source.info
    [string](0..21|%{[char][int]([int]("{0:d}" -f 0x28)+('755964655967-86965747271757624-8796158066061').substring(($_*2),2))})-replace' '
    German ? Come to German PowerShell Forum!



    Donnerstag, 8. August 2013 11:40