Netz-Weise Logo

Weisheiten - der Netz-Weise Blog

Hier finden Sie Tipps und Tricks für vor, während und nach der Schulung.

MDT: Sysprep und Catpure zeigt das Register "Capture Image" nicht an und der Task schlägt fehl

Das Microsoft Deyployment Toolkit 2013 hat in der aktuellen Version 8443 einen Bug, der die Tasksequenz "Sysprep and Capture" funtionsunfähig macht. Leider hat Microsoft den Bug bisher nicht durch eine aktualisierte Version bereinigt. Man kann sich aber schnell selbst behelfen, denn es handelt sich um fehlerhaften VBS-Code in der Datei ZTIUtility.vbs im Ordner Scripts im Root des Deployment-Shares. Ersetzen Sie in Zeile 3327 den Code 

If (oTS.SelectSingleNode("//step[@type='BDD_InstallOS']") is nothing) and (oTS.SelectSingleNode("//step[@type='BDD_UpgradeOS']") is nothing) then

durch

if (oTS.SelectSingleNode("//step[@type='BDD_InstallOS' and @disable='false']") is nothing) and (oTS.SelectSingleNode("//step[@type='BDD_UpgradeOS' and @disable='false']") is nothing) then

Danach sollte die Tasksequenz problemlos durchlaufen.

Links
https://community.spiceworks.com/topic/1924854-mdt-8443-sysprep-capture-task-not-working

Sichere Kennwörter in Powershell generieren, jetzt mit dem .NET Framework

In meinem Blogeintrag Zufällige (Komplexe) Kennwörter erzeugen mit Powershell vom 23.04 habe ich gezeigt, wie man komplexe Kennwörter mit Powershell generieren kann, indem man zufällige Zeichen mit Get-Random erzeugt. Aber es geht auch einfacher, denn das .NET-Framework bietet bereits eine fertige statische Methode zum generieren von Kennwörtern, die man in Powershell nur noch laden muß. Die Methode heißt GeneratePassword und befindet sich in der [System.Web]-Assembly. Die Assembly ist in Powershell allerdings nicht standardmäßig geladen. Dies kann man mit dem Cmdlet Add-Type erledigen: 

Add-Type -AssemblyName System.web

Nun können Sie die Methode GeneratePassword aus der Klasse [System.Web.Security.Membership] aufrufen. Der Aufruf erfolgt über [Klasse]::Methodenname(Parameter):

[System.Web.Security.Membership]::GeneratePassword(10,3)

Die beiden Parameter 10 und 3 bestimmen die Anzahl der Zeichen sowie die nicht-Alphanumerischen Zeichen, die das Kennwort enthalten muß. 

Weiterlesen
Markiert in:

Inaktive Benutzer oder Computer mit Powershell finden und deaktivieren

Das Cmdlet Search-ADAccount ist das Schweizer Messer des AD-Administrators. Es zeigt gesperrte Konten genauso an wie deaktiviert Konten, ablaufende Konten und Konten, deren Kennwort niemals abläuft. Der vielleicht hilfreichste Parameter ist aber -AccountInactive, der Konten anzeigt, die sich schon lange nicht mehr in der Domäne angemeldet haben. Grundsätzlich kann man dieses auch mit Get-ADUser und Get-ADComputer lösen, aber das ist aufwändiger und außerdem muß man auch darauf achten, welches AD-Attribut man auswertet, denn es gibt mehrere Eigenschaften, die die letzte Anmeldung speichern, aber nicht alle sind gleich gut geeignet. Eine gute Auflistung der Attribute und deren Unterschiede finden Sie im Technet-Wiki

Um inaktive Konten anzuzeigen, nutzen Sie einfach

Search-ADAccount -AccountInactive

Der Parameter findet sowohl Benutzer- als auch Computerkonten, die sich seit 60 Tagen nicht mehr angemeldet haben. Wenn Sie nur Benutzer suchen, verwenden Sie den Parameter -Usersonly, wenn Sie die Zeitspanne angeben wollen, benutzen Sie den Parameter Timespan, gefolgt von den Tagen seit dem letzten Login:

Search-ADAccount -AccountInactive -TimeSpan 90 -UsersOnly

Weiterlesen

Einen Secure String oder ein PSCredential-Objekt wieder in ein Klartextkennwort umwandeln

In Powershell ist es oft  notwendig, einen Secure-String zu erzeugen. SecureStrings werden z.B. zum Erstellen eines AD-Benutzers verwendet, oder für alle möglichen Arten von Anmeldeinformationen. Das Geheimnis eines SecureStrings besteht darin, dass er über die Microsoft DPAPI (Data Protection API) durch das Konto des Benutzers geschützt ist, der den SecureString erzeugt hat. Dadurch kann nur er auf das Kennwort des SecureStrings zugreifen. 

Manchmal gibt es aber die Situation, in der man das Kennwort eines Securestrings gerne wieder im Klartext hätte. Als Beispiel dafür soll Read-Host herhalten, das Benutzereingaben von der Konsole liest. Ruf man Read-Host mit dem Parameter -Prompt auf, kann man den Benutzer zu einer Eingabe auffordern: 

$Password = Read-Host -Prompt "Bitte geben Sie ein Kennwort ein"

Das Kennwort wird als String in der Variablen $Password gespeichert. Leider wird das Kennwort aber bei der Eingabe im Klartext angezeigt. Das kann man über den Parameter -AsSecurestring verhindern. Dadurch wird die Eingabe in einen SecureString konvertiert und die Eingabe wird durch das * maskiert:

$Password = Read-Host -Prompt "Bitte geben Sie ein Kennwort ein" -AsSecureString
Bitte geben Sie ein Kennwort ein: ********

Weiterlesen
Markiert in:

Datums- und Zeitwerte Kulturunabhängig speichern

Wenn Sie Datums- und Zeitwerte speichern, gibt es ein ISO-Format, das Kulturunabhängig funktioniert. Es hat folgende Form:

yyyy-MM-dd HH:mm:ss (Jahr 4-stellig, Monat 2-stellig, Tag 2-stellig, Stunden im 24-Stunden Format, Minuten und Sekunden 2-stellig)

Sie können das Datumsformat mit Powershell im ISO-Format angeben, indem Sie den Format-Parameter verwenden: 

Get-Date -Format 'yyyy-MM-dd HH:mm:ss'
2017-04-17 22:31:30

Speichern Sie das Datum in einer Variablen, erstellen Sie ein Datetime-Objekt. Der-Format-Befehl hat auf das Datetime-Objekt keine Auswirkungen, sondern bezieht sich nur auf die Ausgabe. Sie können das Datum also auch folgendermaßen Kulturunabhängig erzeugen:

Weiterlesen

Windows Server 2016 Startmenü findet keine Programm

Wie man viele Probleme mit dem Windows 10 Startmenü lösen kann, habe ich im Artikel "Suchen im Windows 10 Startmenü findet keine installierten Programme" bereits beschrieben. Leider tritt ein ähnliches Problem auch bei Windows Server 2016 auf, was das Startmenü ziemlich ad-absurdum führt. Mein erster Tipp hierzu: Verwenden Sie die Kachelanzeige, um häufig verwendete Programm einfach zu hinterlegen. 

Das eigentliche Problem der Suche im Startmenü unter Windows Server 2016 besteht darin, dass das Startmenü in Windows jetzt als Datenbank implementiert ist. Die Programme im Menü werden indexiert und in der Datenbank abgelegt. Der Zugriff findet dann über Cortana statt. Auf dem Windows Server 2016 hat Microsoft aber den Suchdienst deaktiviert, der die Suche durch die Datenbank erst ermöglicht. Nach langem Recherchieren habe ich einen Thread gefunden, der das Problem und die Lösung beschreibt. beschreibt. Ein Microsoft-Mitarbeiter hierzu:

The “Windows Search” service is set to ‘Disabled’ by default on Windows Server 2016. This is because indexing of the volumes can negatively impact / break server scenarios, such as Cluster Shared Volumes (CSV) and running Remote Desktop Session Host (RDSH) with multiple simultaneous sessions. The side effect of the Windows Search service being disabled is that using Cortana with Start Menu searches has a degraded experience.

Windows Server is optimized to ensure server scenarios are rock solid, which may include trade-off's over shell user experience. If you plan to use Windows Server 2016 as your client desktop machine, you could re-enable the Windows Search service.

Sie können das Problem mit dem Startmenü also einfach beheben, indem Sie die Dienstkonfiguration gehen und den Suchdienst starten oder einfach folgendes Powershell-Kommando verwenden:

Weiterlesen

VLAN-Tagging ab Windows Server 2012 einrichten (am Beispiel HP Proliant Microserver Gen8)

Was ist VLAN-Tagging überhaupt?

(Update: Eine sehr detailllierte Beschreibung zum Thema VLAN-Tagging habe ich bei Altaro gefunden: How to Set up VLANs in Hyper-V)

VLANs oder virtuelle LANs werden benutzt, um Switche zu segmentieren. Mit Hilfe eines VLANs kann man die Ports eines Switches, die normalerweise alle direkt miteinander kommunizieren, in getrennte Bereiche aufteilen. Man macht also aus einem Switch "mehrere" Switche. Das VLAN-Tagging innerhalb eines einzelnen physikalischen Switches passiert vollständig Switch-intern. Datenpakete, die den Switch verlassen, verhalten sich wie völlig normale Netzwerkpakete. Ein Switch kann bis zu 4096 VLANs verwalten. 

VLANs können auch über mehrer Switche hinweg konfiguriert werden. Das ist vor allem im Umfeld größerer Netze wichtig, wo z.B. Rechner unterschiedlicher Etagen sich im gleichen Netzwerk befinden sollen. Hierfür benötigt man VLAN-Tagging. Beim VLAN-Tagging wird auf einem Switch auf einem oder mehreren Ports VLAN-Trunking eingerichtet. Beim Trunking werden die ausgehenden Datenpakete mit einer VLAN-ID versehen, die ein Datenpaket einem bestimmten VLAN zuordnet. Ein Trunk-Port kann sich auch in mehr als einem VLAN befinden. Dadurch kann ein dedizierter Port zwischen zwei Switches bestimmt werden, über den die Switche die Datenpakete eines oder mehrer VLANs direkt austauschen können. Das entspricht einem Uplink zwischen zwei Switches, wobei jedes ausgehende Datenpaket genau einem VLAN zugeordnet ist. Da die aus einem Switch augehenden Datenpakete einen Marker für das jeweilige Zielnetzwerk enthalten, spricht man auch von einem getaggten VLAN. 

Solange man nur einen Switch mit VLANs segmentiert, hat man grundsätzlich Clientseitig keinerlei Probleme, da der Switch die Zuordnung der Datenpakete durchführt. Sobald man mit getaggten VLANs arbeitet, muß der Client wissen, für welches VLAN er Daten annehmen soll. Das kann man direkt in den Einstellungen der Netzwerkkarte vornehmen. Das entsprechende Feld heißt "VLAN ID". Außerdem muß die Unterstützung für VLANs aktiviert sein. Dieses Feld heißt z.B. "Priority & VLAN". 

Man kann eine Netzwerkkarte aber auch wie einen Trunk-Port einrichten, so dass sie die Daten von mehrern VLANs annimmt. Während das vor Windows Server 2012 über herstellerspezifische Tools wie die Broadcom Advanced Control Suite ( z.B. beim HP Proliant Microserver Gen8) ging, verwendet man dazu ab Server 2012 das NIC-Teaming. Tatsächlich hat die von HP zur Verfügung gestellte BACS das Teaming-Feature gar nicht mehr verfügbar, und wenn man die etwas aktuellere Version von Broadcom verwendet, schlägt das Einrichten der getaggten VLANs einfach fehl. 

Weiterlesen
Markiert in:

DHCP-Server migrieren mit Powershell

Ich stand am Wochenende vor der Aufgabe, unseren Fileserver zu migrieren, der auch als DHCP-Server fungiert. Anstatt alle Scopes neu anzulegen, habe ich mit Powershell eine sehr einfache Möglichkeit gefunden, alle DHCP-Scopes, Leases und Einstellungen auf einen Rutsch zu migrieren. Alles, was dafür getan werden muß, ist die DHCP-Einstellungen per 

Export-DHCPServer -File <Export.xml>

zu exportieren. Die Konfiguration wird in eine XML-Datei exportiert und kann auf dem Zielserver einfach über 

Import-DHCPServer -File <Export.xml> 

wieder importiert werden. 

Weiterlesen
Markiert in:

Zufällige (Komplexe) Kennwörter erzeugen mit Powershell

Update: Eine Version mit Hilfe des .NET-Frameworks finden Sie im Artikel Sichere Kennwörter in Powershell generieren, jetzt mit dem .NET Framework

Kennwörter braucht man in Skripten an allen Ecken und Enden, speziell dann, wenn man Benutzer erstellen möchten. Bei einer größeren Anzahl von Konten kann da ein Skript ganz hilfreich sein, dass zufällige Kennwörter generiert. Das ist mit Powershell relativ einfach gemacht. Alles, was man benötigt, ist eine Funktionalität zum Erstellen von Zufallswerten und die Möglichkeit, Zahlen in Buchstaben umzuwandeln. Das Cmdlet Get-Random liefert Zufallszahlen zurück:

Get-Random -Min 10 -Max 100

Die vollständige Auflistung der Funktionen Get-Random können Sie in der Powershell-Hilfe nachlesen. Für uns interessant ist der Parameter -Inputobject, über den man Get-Random ein Array mit Werten übergeben kann, aus denen der Zielwert gewählt wird. 

$ZufallsListe = 65..90
$Zufallszahl = Get-Random -InputObject $Zufallsliste

Weiterlesen
Markiert in:

Mit [ValidateScript()] Powershell-Parameter prüfen und eine benutzerdefinierte Fehlermeldung ausgeben

Powershell stellt mit den Validate-Schlüsselwörtern eine großartige Möglichkeit zur Verfügung, Benutzereingaben in Skripten zu prüfen, und den Code dabei übersichtlich zu halten. Hierfür stehen diverse [Validate]-Attribute zur Verfügung. Folgendes Beispiel prüft z.B. ob ein Parameter sich innerhalb eines bestimmten Wertebereichs befindet:

param(
   [ValidateRange(1,6)]
   [int]$Wuerfelergebnis
)

Rufen Sie den Parameter jetzt z.B. mit 7 auf, erhalten Sie folgende Meldung und das Skript bricht ab:

test : Das Argument für den Parameter "Wuerfelergebnis" kann nicht überprüft werden. Das 7-Argument ist größer als der maximal zulässige Bereich von 6. Geben Sie ein Argument an, das kleiner oder gleich 6
ist, und führen Sie dann den Befehl erneut aus.

Es gibt eine ganze Reihe von Validierungs-Attributen. Eine vollständige Auflistung finden Sie, wenn Sie in der Powershell 

Weiterlesen
Markiert in: