src/private/Invoke-GenerateModuleFile.ps1

function Invoke-GenerateModuleFile {
    [CmdletBinding()]
    param (
        [int] 
        $TemplateOption, 
        [string[]] 
        $RequiredModules,
        [PSCustomObject]
        $Parameters,
        [string]
        $AdditionalCommands,
        [string] 
        $OutputPath
    )
    
    $moduleValidationTemplate = @"
__val__
`$notFound = @()
foreach (`$moduleName in `$requiredModules) {
    `$module = Get-Module -ListAvailable -Name `$moduleName
    if (`$null -eq `$module) {
        `$notFound += `$moduleName
    }
}
if (`$notFound.Count -gt 0) {
    throw "Following modules cannot be found on machine: `$notFound. Install missing modules using command 'Install-Module'"
}
"@

    
    $template1 = @"
__val__
     
`$script:ModuleName = Split-Path -Path `$PSScriptRoot -Leaf
`$Public = @( Get-ChildItem -Path `$PSScriptRoot\Public\*.ps1 -ErrorAction SilentlyContinue )
`$Private = @( Get-ChildItem -Path `$PSScriptRoot\Private\*.ps1 -ErrorAction SilentlyContinue )
         
foreach ( `$FunctionFilePath in @( `$Public + `$Private ) ) {
    try {
        . `$FunctionFilePath.FullName
    } catch {
        Write-Error -Message "Failed to import function '`$(`$FunctionFilePath.FullName)': `$_"
    }
}
         
Export-ModuleMember -Function `$Public.Basename
"@

    
    $template2 = @"
__val__
     
`$Functions = @( Get-ChildItem -Path `$PSScriptRoot\*.ps1 -ErrorAction SilentlyContinue )
     
foreach ( `$FunctionFilePath in `$Functions ) {
    try {
        . `$FunctionFilePath.FullName
    } catch {
        Write-Error -Message "Failed to import function '`$(`$FunctionFilePath.FullName)': `$_"
    }
}
         
Export-ModuleMember -Function *-*
"@

    
    $templates = @( $template1, $template2 )
    
    $arr = $requiredModules | ForEach-Object { "'$_'" }
    $arr = $arr -join ", "
    $requiredModulesArr = "`$requiredModules = @( $arr )"

    if ( $parameters.Keys.Length -eq 0 ) {
        $paramsCmd = $null
    } else {
        $params = ( $parameters.Keys | ForEach-Object {
            $prop = $_
            $type = $parameters[$prop]
            "[$type] `$$prop"
        } ) -join [System.Environment]::NewLine
    
        $paramsCmd = @"
param(
$params
)
 
"@

    }

    $validation = $moduleValidationTemplate -replace "__val__", $requiredModulesArr 
    $moduleFile = $templates[$templateOption] -replace "__val__", $validation
    $moduleFile += [System.Environment]::NewLine + $additionalCommands

    if ( $null -ne $paramsCmd ) {
        $moduleFile = $paramsCmd + [System.Environment]::NewLine + $moduleFile
    }

    $moduleFile | Out-String | Out-File $outputPath
}