374 lines
16 KiB
PowerShell
374 lines
16 KiB
PowerShell
# ============================================================
|
||
# ByteTrail GmbH – GPO, File Server & DFS Namespace Setup Script
|
||
# Domäne: bytetrail.local
|
||
# Ausführen auf: Domain Controller / Fileserver als Domain Admin
|
||
# ============================================================
|
||
|
||
Import-Module GroupPolicy -ErrorAction Stop
|
||
|
||
#region KONFIGURATION
|
||
$Domain = "bytetrail.local"
|
||
$DomainDN = "DC=bytetrail,DC=local"
|
||
$NetBIOSDom = "BYTETRAIL"
|
||
$MailDomain = "bytetrail.at"
|
||
$FreigabePfad = "D:\Freigabe"
|
||
$DfsRootPfad = "D:\DfsRoot" # NEU für Variante 1: Separater, leerer Pfad für den DFS-Root
|
||
#endregion
|
||
|
||
Write-Host "`n=== ByteTrail GPO, Fileserver & DFS Setup gestartet ===" -ForegroundColor Cyan
|
||
|
||
# Dynamische Namensauflösung via SID
|
||
try {
|
||
Import-Module ActiveDirectory -ErrorAction Stop
|
||
|
||
$DomainSID = (Get-ADDomain).DomainSID.Value
|
||
|
||
$DomainAdminsSID = "$DomainSID-512"
|
||
$DomainUsersSID = "$DomainSID-513"
|
||
|
||
$DomainAdminsName = (Get-ADGroup -Identity $DomainAdminsSID).Name
|
||
$DomainUsersName = (Get-ADGroup -Identity $DomainUsersSID).Name
|
||
}
|
||
catch {
|
||
Write-Host " [!] Fehler beim Auflösen der Standardgruppen: $($_.Exception.Message)" -ForegroundColor Red
|
||
return
|
||
}
|
||
|
||
# ============================================================
|
||
# TEIL 1: GRUPPENRICHTLINIEN (GPOs) SKELETT
|
||
# ============================================================
|
||
Write-Host "`n[1/4] Konfiguriere Gruppenrichtlinien (GPOs)..." -ForegroundColor Yellow
|
||
|
||
$GpoSecurityName = "ByteTrail_Base_Security"
|
||
$GpoDrivesName = "ByteTrail_Mapped_Drives"
|
||
|
||
# 1.1 Basis-Sicherheit (Domänenweit)
|
||
if (!(Get-GPO -Name $GpoSecurityName -ErrorAction SilentlyContinue)) {
|
||
try {
|
||
$gpoSec = New-GPO -Name $GpoSecurityName -Comment "Basis-Sicherheitsrichtlinien (Bildschirmsperre etc.)"
|
||
New-GPLink -Name $GpoSecurityName -Target $DomainDN -LinkEnabled Yes | Out-Null
|
||
|
||
Set-GPRegistryValue -Name $GpoSecurityName -Key "HKCU\Software\Policies\Microsoft\Windows\Control Panel\Desktop" -ValueName "ScreenSaveActive" -Type String -Value "1" | Out-Null
|
||
Set-GPRegistryValue -Name $GpoSecurityName -Key "HKCU\Software\Policies\Microsoft\Windows\Control Panel\Desktop" -ValueName "ScreenSaverIsSecure" -Type String -Value "1" | Out-Null
|
||
Set-GPRegistryValue -Name $GpoSecurityName -Key "HKCU\Software\Policies\Microsoft\Windows\Control Panel\Desktop" -ValueName "ScreenSaveTimeOut" -Type String -Value "900" | Out-Null
|
||
|
||
Write-Host " [+] GPO '$GpoSecurityName' erstellt, konfiguriert und mit Domäne verknüpft." -ForegroundColor Green
|
||
} catch {
|
||
Write-Host " [!] Fehler bei GPO '$GpoSecurityName': $($_.Exception.Message)" -ForegroundColor Red
|
||
}
|
||
} else {
|
||
Write-Host " [~] GPO '$GpoSecurityName' existiert bereits." -ForegroundColor Gray
|
||
}
|
||
|
||
# 1.2 Netzlaufwerke GPO-Hülle
|
||
if (!(Get-GPO -Name $GpoDrivesName -ErrorAction SilentlyContinue)) {
|
||
try {
|
||
New-GPO -Name $GpoDrivesName -Comment "Automatische Netzlaufwerk-Zuweisungen fuer Fachabteilungen" | Out-Null
|
||
|
||
New-GPLink -Name $GpoDrivesName -Target "OU=Geschaeftsfuehrung,$DomainDN" -LinkEnabled Yes | Out-Null
|
||
New-GPLink -Name $GpoDrivesName -Target "OU=Sales,$DomainDN" -LinkEnabled Yes | Out-Null
|
||
New-GPLink -Name $GpoDrivesName -Target "OU=Marketing,$DomainDN" -LinkEnabled Yes | Out-Null
|
||
New-GPLink -Name $GpoDrivesName -Target "OU=Service,$DomainDN" -LinkEnabled Yes | Out-Null
|
||
|
||
Write-Host " [+] GPO '$GpoDrivesName' erstellt und mit OUs verknüpft." -ForegroundColor Green
|
||
} catch {
|
||
Write-Host " [!] Fehler bei GPO '$GpoDrivesName': $($_.Exception.Message)" -ForegroundColor Red
|
||
}
|
||
} else {
|
||
Write-Host " [~] GPO '$GpoDrivesName' existiert bereits." -ForegroundColor Gray
|
||
}
|
||
|
||
|
||
# ============================================================
|
||
# TEIL 2: FILESERVER ORDNER & BERECHTIGUNGEN (NTFS)
|
||
# ============================================================
|
||
Write-Host "`n[2/4] Konfiguriere Ordnerstruktur & NTFS-Berechtigungen auf $FreigabePfad..." -ForegroundColor Yellow
|
||
|
||
# Haupt-Datenverzeichnis
|
||
if (!(Test-Path $FreigabePfad)) { New-Item -Path $FreigabePfad -ItemType Directory -Force | Out-Null }
|
||
|
||
try {
|
||
Get-SmbShare -Name "Freigabe" -ErrorAction Stop | Out-Null
|
||
Write-Host " [~] SMB-Freigabe 'Freigabe' existiert bereits." -ForegroundColor Gray
|
||
} catch {
|
||
New-SmbShare -Name "Freigabe" -Path $FreigabePfad -FullAccess "$NetBIOSDom\$DomainAdminsName" -ChangeAccess "$NetBIOSDom\$DomainUsersName" | Out-Null
|
||
Write-Host " [+] SMB-Freigabe 'Freigabe' erstellt." -ForegroundColor Green
|
||
}
|
||
|
||
# NEU für Variante 1: Separates Verzeichnis für den DFS-Root (Muss physisch komplett leer bleiben!)
|
||
if (!(Test-Path $DfsRootPfad)) { New-Item -Path $DfsRootPfad -ItemType Directory -Force | Out-Null }
|
||
|
||
try {
|
||
Get-SmbShare -Name "DfsRoot$" -ErrorAction Stop | Out-Null
|
||
Write-Host " [~] SMB-Freigabe 'DfsRoot$' existiert bereits." -ForegroundColor Gray
|
||
} catch {
|
||
# Versteckte Freigabe für das DFS-Root-Skelett
|
||
New-SmbShare -Name "DfsRoot$" -Path $DfsRootPfad -FullAccess "$NetBIOSDom\$DomainAdminsName" -ReadAccess "$NetBIOSDom\$DomainUsersName" | Out-Null
|
||
Write-Host " [+] SMB-Freigabe 'DfsRoot$' für DFS erstellt." -ForegroundColor Green
|
||
}
|
||
|
||
$AclBase = Get-Acl $FreigabePfad
|
||
$AclBase.SetAccessRuleProtection($true, $true)
|
||
Set-Acl -Path $FreigabePfad -AclObject $AclBase
|
||
|
||
$Folders = @(
|
||
@{ Name = "Geschaeftsfuehrung"; Group = "GRP-GF-VOLLZUGRIFF" }
|
||
@{ Name = "Sales"; Group = "GRP-SALES-FILES" }
|
||
@{ Name = "Marketing"; Group = "GRP-MKT-FILES" }
|
||
@{ Name = "Service"; Group = "GRP-SVC-FILES" }
|
||
)
|
||
|
||
$RightsModify = [System.Security.AccessControl.FileSystemRights]::Modify
|
||
$RightsRead = [System.Security.AccessControl.FileSystemRights]::ReadAndExecute
|
||
$RightsFull = [System.Security.AccessControl.FileSystemRights]::FullControl
|
||
$Inheritance = [System.Security.AccessControl.InheritanceFlags]::ContainerInherit, [System.Security.AccessControl.InheritanceFlags]::ObjectInherit
|
||
$Propagation = [System.Security.AccessControl.PropagationFlags]::None
|
||
$Allow = [System.Security.AccessControl.AccessControlType]::Allow
|
||
|
||
$RuleAdmin = New-Object System.Security.AccessControl.FileSystemAccessRule("$NetBIOSDom\GRP-ADMINS", $RightsFull, $Inheritance, $Propagation, $Allow)
|
||
$RuleSystem = New-Object System.Security.AccessControl.FileSystemAccessRule("NT AUTHORITY\SYSTEM", $RightsFull, $Inheritance, $Propagation, $Allow) # Wichtig für Backup/Windows-Dienste
|
||
$RuleGFRead = New-Object System.Security.AccessControl.FileSystemAccessRule("$NetBIOSDom\GRP-GF-VOLLZUGRIFF", $RightsRead, $Inheritance, $Propagation, $Allow)
|
||
|
||
foreach ($Folder in $Folders) {
|
||
$FolderPath = "$FreigabePfad\$($Folder.Name)"
|
||
if (!(Test-Path $FolderPath)) { New-Item -Path $FolderPath -ItemType Directory -Force | Out-Null }
|
||
|
||
$Acl = Get-Acl -Path $FolderPath
|
||
$Acl.SetAccessRuleProtection($true, $false)
|
||
$Acl.AddAccessRule($RuleAdmin)
|
||
$Acl.AddAccessRule($RuleSystem)
|
||
|
||
$RuleDept = New-Object System.Security.AccessControl.FileSystemAccessRule("$NetBIOSDom\$($Folder.Group)", $RightsModify, $Inheritance, $Propagation, $Allow)
|
||
$Acl.AddAccessRule($RuleDept)
|
||
|
||
if ($Folder.Name -ne "Geschaeftsfuehrung") {
|
||
$Acl.AddAccessRule($RuleGFRead)
|
||
}
|
||
|
||
Set-Acl -Path $FolderPath -AclObject $Acl
|
||
Write-Host " [+] Rechte für Ordner '$($Folder.Name)' erfolgreich gesetzt." -ForegroundColor Green
|
||
}
|
||
|
||
$AustauschPath = "$FreigabePfad\Austausch"
|
||
if (!(Test-Path $AustauschPath)) { New-Item -Path $AustauschPath -ItemType Directory -Force | Out-Null }
|
||
$AclAustausch = Get-Acl -Path $AustauschPath
|
||
$AclAustausch.SetAccessRuleProtection($true, $false)
|
||
|
||
$RuleAll = New-Object System.Security.AccessControl.FileSystemAccessRule("$NetBIOSDom\$DomainUsersName", $RightsModify, $Inheritance, $Propagation, $Allow)
|
||
$AclAustausch.AddAccessRule($RuleAll)
|
||
$AclAustausch.AddAccessRule($RuleAdmin)
|
||
$AclAustausch.AddAccessRule($RuleSystem)
|
||
Set-Acl -Path $AustauschPath -AclObject $AclAustausch
|
||
Write-Host " [+] Rechte für Ordner 'Austausch' erfolgreich gesetzt." -ForegroundColor Green
|
||
|
||
|
||
# ============================================================
|
||
# TEIL 3: DFS-NAMESPACES (Kollisionsfrei nach Variante 1)
|
||
# ============================================================
|
||
Write-Host "`n[3/4] Konfiguriere DFS-Namespace..." -ForegroundColor Yellow
|
||
|
||
if (!(Get-WindowsFeature -Name FS-DFS-Namespace).Installed) {
|
||
Write-Host " [..] Installiere DFS-Namespace Server-Rolle..." -ForegroundColor Gray
|
||
Install-WindowsFeature FS-DFS-Namespace -IncludeManagementTools | Out-Null
|
||
}
|
||
Import-Module DFSN
|
||
|
||
$NamespaceRoot = "\\$Domain\Daten"
|
||
$LocalServerFQDN = "$env:COMPUTERNAME.$Domain"
|
||
|
||
# DFS-Root erstellen (Verweist nun exklusiv auf die leere Freigabe)
|
||
try {
|
||
Get-DfsnRoot -Path $NamespaceRoot -ErrorAction Stop | Out-Null
|
||
Write-Host " [~] DFS-Root '$NamespaceRoot' existiert bereits." -ForegroundColor Gray
|
||
} catch {
|
||
New-DfsnRoot -Path $NamespaceRoot -Type DomainV2 -TargetPath "\\$LocalServerFQDN\DfsRoot$" -ErrorAction Stop | Out-Null
|
||
Write-Host " [+] DFS-Root '$NamespaceRoot' erfolgreich erstellt." -ForegroundColor Green
|
||
}
|
||
|
||
# DFS-Ordner (Links) im leeren Namespace-Verzeichnis einrichten
|
||
foreach ($Folder in $Folders) {
|
||
$DfsFolderPath = "$NamespaceRoot\$($Folder.Name)"
|
||
try {
|
||
Get-DfsnFolder -Path $DfsFolderPath -ErrorAction Stop | Out-Null
|
||
} catch {
|
||
New-DfsnFolder -Path $DfsFolderPath -TargetPath "\\$LocalServerFQDN\Freigabe\$($Folder.Name)" -ErrorAction Stop | Out-Null
|
||
Write-Host " [+] DFS Link erstellt: $($Folder.Name) -> $NamespaceRoot\$($Folder.Name)" -ForegroundColor Green
|
||
}
|
||
}
|
||
|
||
# DFS Link für den öffentlichen Austausch-Ordner
|
||
$DfsAustauschPath = "$NamespaceRoot\Austausch"
|
||
try { Get-DfsnFolder -Path $DfsAustauschPath -ErrorAction Stop | Out-Null } catch {
|
||
New-DfsnFolder -Path $DfsAustauschPath -TargetPath "\\$LocalServerFQDN\Freigabe\Austausch" -ErrorAction Stop | Out-Null
|
||
Write-Host " [+] DFS Link erstellt: Austausch -> $DfsAustauschPath" -ForegroundColor Green
|
||
}
|
||
|
||
|
||
# ============================================================
|
||
# TEIL 4: GPP DRIVE MAPS (EMPFOHLENE VARIANTE)
|
||
# ============================================================
|
||
Write-Host "`n[4/4] Konfiguriere GPP Drive Maps..." -ForegroundColor Yellow
|
||
|
||
$Gpo = Get-GPO -Name $GpoDrivesName
|
||
$GpoGuid = $Gpo.Id.Guid
|
||
|
||
# SYSVOL Pfade
|
||
$GpoRoot = "\\$Domain\SYSVOL\$Domain\Policies\{$GpoGuid}"
|
||
$PreferencesPath = "$GpoRoot\User\Preferences"
|
||
$DriveMapPath = "$PreferencesPath\Drives"
|
||
|
||
# Ordner erzeugen
|
||
New-Item -Path $DriveMapPath -ItemType Directory -Force | Out-Null
|
||
|
||
# ============================================================
|
||
# DRIVE MAP XML
|
||
# ============================================================
|
||
|
||
$XmlContent = @"
|
||
<?xml version="1.0" encoding="utf-8"?>
|
||
<Drives clsid="{8FDDCC1A-0C3C-43cd-A6B4-71A6DF20DA8C}">
|
||
|
||
<!-- Geschäftsführung -->
|
||
<Drive clsid="{935D1B74-9CB8-4e3c-9914-7DD559B7A417}" name="G:" status="G">
|
||
<Properties action="U"
|
||
thisDrive="SHOW"
|
||
allDrives="NOCHANGE"
|
||
userName=""
|
||
path="\\$Domain\Daten\Geschaeftsfuehrung"
|
||
label="Geschaeftsfuehrung"
|
||
persistent="1"
|
||
useLetter="1"
|
||
letter="G" />
|
||
<Filters>
|
||
<FilterGroup bool="AND"
|
||
not="0"
|
||
name="$NetBIOSDom\GRP-GF-VOLLZUGRIFF"
|
||
sid=""
|
||
userContext="1"
|
||
primaryGroup="0"
|
||
localGroup="0" />
|
||
</Filters>
|
||
</Drive>
|
||
|
||
<!-- Sales -->
|
||
<Drive clsid="{935D1B74-9CB8-4e3c-9914-7DD559B7A417}" name="S:" status="S">
|
||
<Properties action="U"
|
||
thisDrive="SHOW"
|
||
allDrives="NOCHANGE"
|
||
userName=""
|
||
path="\\$Domain\Daten\Sales"
|
||
label="Sales"
|
||
persistent="1"
|
||
useLetter="1"
|
||
letter="S" />
|
||
<Filters>
|
||
<FilterGroup bool="AND"
|
||
not="0"
|
||
name="$NetBIOSDom\GRP-SALES-FILES"
|
||
sid=""
|
||
userContext="1"
|
||
primaryGroup="0"
|
||
localGroup="0" />
|
||
</Filters>
|
||
</Drive>
|
||
|
||
<!-- Marketing -->
|
||
<Drive clsid="{935D1B74-9CB8-4e3c-9914-7DD559B7A417}" name="M:" status="M">
|
||
<Properties action="U"
|
||
thisDrive="SHOW"
|
||
allDrives="NOCHANGE"
|
||
userName=""
|
||
path="\\$Domain\Daten\Marketing"
|
||
label="Marketing"
|
||
persistent="1"
|
||
useLetter="1"
|
||
letter="M" />
|
||
<Filters>
|
||
<FilterGroup bool="AND"
|
||
not="0"
|
||
name="$NetBIOSDom\GRP-MKT-FILES"
|
||
sid=""
|
||
userContext="1"
|
||
primaryGroup="0"
|
||
localGroup="0" />
|
||
</Filters>
|
||
</Drive>
|
||
|
||
<!-- Service -->
|
||
<Drive clsid="{935D1B74-9CB8-4e3c-9914-7DD559B7A417}" name="T:" status="T">
|
||
<Properties action="U"
|
||
thisDrive="SHOW"
|
||
allDrives="NOCHANGE"
|
||
userName=""
|
||
path="\\$Domain\Daten\Service"
|
||
label="Service"
|
||
persistent="1"
|
||
useLetter="1"
|
||
letter="T" />
|
||
<Filters>
|
||
<FilterGroup bool="AND"
|
||
not="0"
|
||
name="$NetBIOSDom\GRP-SVC-FILES"
|
||
sid=""
|
||
userContext="1"
|
||
primaryGroup="0"
|
||
localGroup="0" />
|
||
</Filters>
|
||
</Drive>
|
||
|
||
<!-- Austausch -->
|
||
<Drive clsid="{935D1B74-9CB8-4e3c-9914-7DD559B7A417}" name="X:" status="X">
|
||
<Properties action="U"
|
||
thisDrive="SHOW"
|
||
allDrives="NOCHANGE"
|
||
userName=""
|
||
path="\\$Domain\Daten\Austausch"
|
||
label="Austausch"
|
||
persistent="1"
|
||
useLetter="1"
|
||
letter="X" />
|
||
</Drive>
|
||
|
||
</Drives>
|
||
"@
|
||
|
||
# XML speichern
|
||
$XmlContent | Out-File "$DriveMapPath\Drives.xml" -Encoding UTF8 -Force
|
||
|
||
# ============================================================
|
||
# GPT.INI Version erhöhen
|
||
# ============================================================
|
||
|
||
$GptIni = "$GpoRoot\GPT.INI"
|
||
|
||
if (Test-Path $GptIni) {
|
||
|
||
$Content = Get-Content $GptIni
|
||
|
||
$VersionLine = $Content | Where-Object { $_ -match "^Version=" }
|
||
|
||
if ($VersionLine) {
|
||
|
||
$CurrentVersion = [int]($VersionLine -replace "Version=", "")
|
||
$NewVersion = $CurrentVersion + 1
|
||
|
||
$Content = $Content -replace "Version=$CurrentVersion", "Version=$NewVersion"
|
||
|
||
$Content | Set-Content $GptIni -Encoding ASCII
|
||
}
|
||
}
|
||
|
||
# ============================================================
|
||
# Netzwerk-Wartezeit aktivieren
|
||
# ============================================================
|
||
|
||
Set-GPRegistryValue `
|
||
-Name $GpoSecurityName `
|
||
-Key "HKLM\Software\Policies\Microsoft\Windows NT\CurrentVersion\Winlogon" `
|
||
-ValueName "SyncForegroundPolicy" `
|
||
-Type DWord `
|
||
-Value 1 | Out-Null
|
||
|
||
Write-Host " [+] GPP Drive Maps erfolgreich konfiguriert." -ForegroundColor Green
|
||
|
||
Write-Host "`n=== Setup erfolgreich abgeschlossen ===" -ForegroundColor Cyan |