Public/Import-pseModule.ps1

Function Import-pseModule {
    <#
    .SYNOPSIS
        Imports one or more PowerShell modules, ensuring specific versions are loaded if requested.
 
    .DESCRIPTION
        The Import-pseModule function provides enhanced module importing capabilities within your PowerShell workflows. Key features include:
 
            * Version Management: Imports a specific version of a module if provided.
            * Selective Unloading: If a different version of a module is already loaded and a specific version is requested, the function unloads the pre-existing one.
            * Robust Error Handling: Includes detailed error handling to help identify and troubleshoot module import issues.
 
    .PARAMETER moduleName
        One or more PowerShell module names to import. Can be provided as:
            * A single string
            * An array of strings
            * Pipeline input
 
    .PARAMETER version
        Optional. Specifies the target version of the module to import. If the correct version is already loaded, no action is taken.
 
    .EXAMPLE
        Import-pseModule -moduleName AzureAD
 
        Imports the latest available version of the 'AzureAD' module.
 
    .EXAMPLE
        Import-pseModule -moduleName DHCPServer -version 1.0.5
 
        Imports and loads version 1.0.5 of the 'DHCPServer' module. If a different version is loaded, it will be unloaded first.
 
    .EXAMPLE
        Import-pseModule -moduleName "ExchangeOnlineManagement", "MicrosoftTeams"
 
        Imports or loads the latest versions of multiple modules in one call.
 
    .NOTES
        Author : owen.heaume
        Version: 1.0.0 - Initial release
    #>


    [CmdletBinding()]
    Param (
        [Parameter(Mandatory = $true, ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true)]
        [string[]]$ModuleName,

        [Parameter(Mandatory = $false, ValueFromPipelineByPropertyName = $true)]
        [string]$Version
    )

    Process {
        foreach ($module in $moduleName) {
            if ($version) {
                Write-Host "Attempting to import module '$module' version $version" -ForegroundColor DarkCyan
            } else {
                Write-Host "Attempting to import module '$module'" -ForegroundColor DarkCyan
            }

            $existingModule = Get-Module -Name $module
            if ($existingModule) {
                if ($Version -and $existingModule.Version.ToString() -ne $Version) {
                    Write-Host "Module '$module' is loaded (different version) - unloading" -ForegroundColor DarkGray
                    Remove-Module -Name $module -Force
                } else {
                    Write-Host "Module '$module' is already loaded (correct version)`n" -ForegroundColor DarkGray
                    continue
                }
            } else {
                Write-Host "Module '$module' is not loaded" -ForegroundColor DarkGray
            }

            # Only attempt to import if the correct version is not already loaded
            try {
                if ($version) {
                    Write-Host "Importing module '$module'" -ForegroundColor DarkGray
                    Import-Module -Name $module -DisableNameChecking -RequiredVersion $Version -Global -ea Stop
                    Write-Host "Imported successfully`n" -ForegroundColor DarkGreen
                } else {
                    Write-Host "Importing module '$module'" -ForegroundColor DarkCyan
                    Import-Module -Name $module -DisableNameChecking -Global -ea stop
                    Write-Host "Imported successfully`n" -ForegroundColor DarkGreen
                }
            } catch [System.Management.Automation.ItemNotFoundException] {
                Write-Warning "Module '$module' (or the specified version) could not be found"
            } catch {
                Write-Error "Failed to import module '$module': $_"
            }
        }
    }
}