functions/Update-Psm1FromSource.ps1

function Update-Psm1FromSource {
    [CmdletBinding()]
    param (
        [Parameter(Mandatory)]
        [string]$ModuleRoot,

        [switch]$UpdateManifest
    )

    #Requires -RunAsAdministrator

    $ModuleRoot = (Resolve-Path -Path $ModuleRoot).Path
    $moduleName = Split-Path -Path $ModuleRoot -Leaf

    $psm1Path = Join-Path $ModuleRoot "$moduleName.psm1"
    $manifestPath = Join-Path $ModuleRoot "$moduleName.psd1"
    $functionsFolder = Join-Path $ModuleRoot 'functions'
    $dllRelativePath = "lib\$moduleName.dll"
    $ExcludeListFile = Join-Path $ModuleRoot 'exclude-files.json'

    # Erstelle temporäres Verzeichnis
    $tempRoot = Join-Path $env:TEMP "$moduleName"
    if (-not (Test-Path $tempRoot)) { New-Item -Path $tempRoot -ItemType Directory | Out-Null }
    $tempModulePath = Join-Path $tempRoot "$moduleName.psm1"

    # Header mit literalem Pfad (kein $PSScriptRoot im Temp-Modul!)
    $header = @"
#Requires -RunAsAdministrator
 
# Load the compiled C# DLL
Import-Module '$tempRoot\$dllRelativePath'
"@


    $tempFilePath = Join-Path -Path $tempRoot -ChildPath $dllRelativePath
    $tempFileDir  = Split-Path -Path $tempFilePath
    if (-not (Test-Path -Path $tempFileDir)) {
        Write-Verbose "Create directory $tempFileDir"
        New-Item -ItemType Directory -Path $tempFileDir | Out-Null
    }
    Write-Verbose "Copy $(Split-Path -Leaf $dllRelativePath) to $tempFilePath"
    Copy-Item -Path $(Join-Path -Path $ModuleRoot -ChildPath $dllRelativePath) -Destination $tempFilePath

    # Dot-source Zeilen sammeln
    $dotSourceLines = @()
    $functionFiles = Get-ChildItem -Path $functionsFolder -Recurse -Filter '*.ps1' | Sort-Object FullName
    $functionFiles = Get-FilteredFiles -Files $functionFiles -ExcludeListFile $ExcludeListFile -RootPath $ModuleRoot
    foreach ($file in $functionFiles) {
        $relativePath = $file.FullName.Substring($ModuleRoot.Length).TrimStart('\')
        $dotSourceLines += ". `"$tempRoot\$relativePath`""
        $tempFilePath = Join-Path -Path $tempRoot -ChildPath $relativePath
        $tempFileDir  = Split-Path -Path $tempFilePath
        if (-not (Test-Path -Path $tempFileDir)) {
            Write-Verbose "Create directory $tempFileDir"
            New-Item -ItemType Directory -Path $tempFileDir | Out-Null
        }
        Write-Verbose "Copy $($file.Name) to $tempFilePath"
        Copy-Item -Path $file.FullName -Destination $tempFilePath
    }

    # Erzeuge temporäre psm1-Datei zum Importieren
    $tempContent = @(
        $header
        ""
        $dotSourceLines
    ) -join "`n"
    Set-Content -Path $tempModulePath -Value $tempContent -Encoding UTF8

    # Temporär importieren, um Funktionen zu erkennen
    Import-Module $tempModulePath -Force -PassThru | Out-Null

    $exportFunctions = Get-Command -Module $moduleName |
        Where-Object { $_.CommandType -eq 'Function' } |
        Select-Object -ExpandProperty Name

    Remove-Module -Name $moduleName -Force
    Remove-Item -Path $tempRoot -Recurse -Force

    # Export-Zeilen schreiben
    $exportLines = @()
    if ($exportFunctions.Count -gt 0) {
        $grouped = $exportFunctions | Sort-Object | Group-Object { ($_ -split '-')[0] }
        foreach ($group in $grouped) {
            $exportLines += "Export-ModuleMember -Function " + ($group.Group -join ', ')
        }
    }

    # Schreibe neue .psm1-Datei
    $finalHeader = @"
#Requires -RunAsAdministrator
 
# Load the compiled C# DLL
Write-Verbose "Import `'`$PSScriptRoot\$dllRelativePath`'"
Import-Module "`$PSScriptRoot\$dllRelativePath"
"@


    # Dot-source Zeilen sammeln
    $dotSourceLines = @()
    $functionFiles = Get-ChildItem -Path $functionsFolder -Recurse -Filter '*.ps1' | Sort-Object FullName
    $functionFiles = Get-FilteredFiles -Files $functionFiles -ExcludeListFile $ExcludeListFile -RootPath $ModuleRoot
    foreach ($file in $functionFiles) {
        $relativePath = $file.FullName.Substring($ModuleRoot.Length).TrimStart('\')
        if ($excludedFiles -notcontains $relativePath) {
            $dotSourceLines += ". `$PSScriptRoot\$relativePath` "
        }
    }

    $psm1Content = @(
        $finalHeader
        ""
        $dotSourceLines
        ""
        $exportLines
    )

    Set-Content -Path $psm1Path -Value $psm1Content -Encoding UTF8
    
    Write-Host "✅ Updated $psm1Path with $($dotSourceLines.Count) dot-sourced files and $($exportFunctions.Count) exported functions."

    if ($UpdateManifest) {
        Update-ModuleManifest -Path $manifestPath -FunctionsToExport $exportFunctions
        Write-Host "✅ Updated $manifestPath with $($exportFunctions.Count) functions."
    }
}