<# .SYNOPSIS Performance-Messung fuer Process-ADObjects.ps1 mit PSProfiler. .DESCRIPTION Misst den kompletten Lauf des Rahmenskripts Process-ADObjects.ps1 inklusive aller dot-gesourcten Dateien - insbesondere des dynamisch zusammengesetzten Process-ADObjects-Work-.ps1 mit der eigentlich zu analysierenden Funktion ProcessADObjects. Die Messung laeuft ueber Measure-Script (PSProfiler). PSProfiler instrumentiert den gesamten Aufrufbaum und behaelt die Zeilenzuordnung pro Quelldatei bei, auch ueber dot-gesourcte Dateien hinweg. Steuerung erfolgt ausschliesslich ueber ein temporaeres Configuration-Local- Override, damit am Produktivcode nichts geaendert werden muss. Das Override wird nach dem Lauf wieder entfernt (es sei denn, es existierte bereits - dann wird es NICHT angetastet). .PARAMETER Sparkasse Institut/Mandant, gegen den gemessen wird. Default: R125. .PARAMETER ScriptRoot Verzeichnis, in dem Process-ADObjects.ps1 und die zugehoerigen Skripte liegen. Default: aktuelles Verzeichnis. .PARAMETER Warmup Anzahl Aufwaerm-Laeufe, deren Ergebnisse verworfen werden (gegen JIT-/Cache- Effekte). Default: 1. .PARAMETER Runs Anzahl gemessener Laeufe, die gespeichert werden. Default: 1. .EXAMPLE ./Measure-ProcessADObjects.ps1 -Sparkasse R125 -ScriptRoot /Users/edmond/Develop/PowerShell/BIT-BV .NOTES Ergebnis-XML wird neben diesem Skript bzw. unter -OutputDir abgelegt und kann mit Analyze-ProfileResult.ps1 ausgewertet werden. #> [CmdletBinding()] param( [string]$Sparkasse = "R125", [string]$ScriptRoot = (Get-Location).Path, [int]$Warmup = 1, [int]$Runs = 1, [string]$OutputDir = $PSScriptRoot + "/Data/" + $Sparkasse + "/Log" ) $ErrorActionPreference = "Stop" # --- PSProfiler vorhanden? ------------------------------------------------- if (-not (Get-Command Measure-Script -ErrorAction SilentlyContinue)) { Write-Host "PSProfiler (Measure-Script) nicht gefunden. Bitte importieren:" -ForegroundColor Yellow Write-Host " Import-Module PSProfiler" -ForegroundColor Yellow throw "Measure-Script nicht verfuegbar." } # --- Pfade aufloesen ------------------------------------------------------- $ScriptRoot = (Resolve-Path $ScriptRoot).Path $mainScript = Join-Path $ScriptRoot "Process-ADObjects.ps1" if (-not (Test-Path $mainScript)) { throw "Process-ADObjects.ps1 nicht gefunden unter: $mainScript" } $localOverridePath = Join-Path $ScriptRoot "Process-ADObjects-Configuration-Local.ps1" if (-not (Test-Path $OutputDir)) { New-Item -ItemType Directory -Path $OutputDir -Force | Out-Null } # --- Configuration-Local-Override: nur ProcessDAW, ohne teures Verbose ------ # Wird NUR angelegt, wenn nicht bereits eine eigene Local-Datei existiert. $createdOverride = $false # Hinweis: Measure-Script reicht keine Skript-Argumente durch (-ArgumentList # wird nicht unterstuetzt). Das Institut wird daher hier ueber # $Config.DefaultInstitute gesetzt. Das Rahmenskript faellt bei leerem # -sparkasse auf diesen Default zurueck (checkInput -> isProbablyDevelopmentUser), # sodass kein Argument noetig ist. $overrideContent = @" # === AUTO-GENERATED by Measure-ProcessADObjects.ps1 === # Engt den Lauf auf die ProcessDAW-Phase ein und schaltet teure Diagnose ab, # damit die Messung nicht durch WriteKURS/TransferDAW/PostProcess, Analyze und # das sehr teure "Get-Variable | Out-String" (Verbose) verfaelscht wird. # Diese Datei wird vom Mess-Wrapper nach dem Lauf automatisch geloescht. `$Config.DefaultInstitute = "$Sparkasse" `$Config.ProcessDAW = `$true `$Config.WriteKURS = `$false `$Config.TransferDAW = `$false `$Config.PostProcess = `$false `$Config.Analyze = `$false `$Config.Verbose = `$false `$Config.TestMode = 0 "@ if (Test-Path $localOverridePath) { Write-Host "HINWEIS: Es existiert bereits ein Configuration-Local-Override." -ForegroundColor Yellow Write-Host " Es wird NICHT veraendert. Stelle sicher, dass darin steht:" -ForegroundColor Yellow Write-Host " ProcessDAW=true, WriteKURS/TransferDAW/PostProcess/Analyze/Verbose=false" -ForegroundColor Yellow } else { Set-Content -Path $localOverridePath -Value $overrideContent -Encoding UTF8 $createdOverride = $true Write-Host "Temporaeres Configuration-Local-Override angelegt." -ForegroundColor DarkGray } # --- Messung --------------------------------------------------------------- $timestamp = Get-Date -Format "yyyyMMdd-HHmmss" $savedFiles = @() try { $totalRuns = $Warmup + $Runs for ($i = 1; $i -le $totalRuns; $i++) { $isWarmup = ($i -le $Warmup) $label = if ($isWarmup) { "WARMUP $i/$Warmup" } else { "RUN $($i - $Warmup)/$Runs" } Write-Host "" Write-Host "=== $label : Measure-Script $mainScript -sparkasse $Sparkasse ===" -ForegroundColor Cyan # Wichtig: aus dem ScriptRoot heraus laufen lassen, da das Rahmenskript # selbst Set-Location $PSScriptRoot macht und relative Pfade nutzt. Push-Location $ScriptRoot try { # Measure-Script unterstuetzt KEINE Skript-Argumente. Das Institut # kommt ueber $Config.DefaultInstitute aus dem Local-Override (siehe # oben). Daher hier bewusst OHNE -ArgumentList. $result = Measure-Script -Path $mainScript } finally { Pop-Location } if ($isWarmup) { Write-Host " (Warmup-Ergebnis verworfen)" -ForegroundColor DarkGray continue } $runNo = $i - $Warmup # $xmlPath = Join-Path $OutputDir "Profile-MainScript.$Sparkasse-$timestamp-run$runNo.xml" $xmlPath = Join-Path $OutputDir ("Profile-MainScript-{0}-{1}.xml" -f $Sparkasse, $timestamp) $result | Export-Clixml -Path $xmlPath -Depth 6 $savedFiles += $xmlPath Write-Host " Ergebnis gespeichert: $xmlPath" -ForegroundColor Green } } finally { # --- Aufraeumen: nur das selbst angelegte Override entfernen ------------ if ($createdOverride -and (Test-Path $localOverridePath)) { Remove-Item -Path $localOverridePath -ErrorAction SilentlyContinue Write-Host "Temporaeres Configuration-Local-Override entfernt." -ForegroundColor DarkGray } } Write-Host "" Write-Host "Fertig. Gespeicherte Ergebnis-Dateien:" -ForegroundColor Cyan $savedFiles | ForEach-Object { Write-Host " $_" } Write-Host "" Write-Host "Auswertung:" -ForegroundColor Cyan Write-Host " ./Analyze-ProfileResult.ps1 -XmlPath '$($savedFiles | Select-Object -Last 1)'" -ForegroundColor Gray