function Test-Server{ <# .SYNOPSIS validate mininum software requirement on server .PARAMETER dotNetMinimumVersion The minimum .NET version allowed to be installed. Throws if the version is less than this value. Defaults to 4.7.1 #> [Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSAvoidUsingInvokeExpression', '', Justification = 'Alkami generates this string manually, no user injection')] [CmdletBinding()] Param( [string]$dotNetMinimumVersion = "4.7.1" ) $logLead = (Get-LogLeadName); Write-Output ("$logLead : Checking Powershell Version") if ($PSVersionTable.PSVersion.Major -lt 5 -or ($PSVersionTable.PSVersion.Major -eq 5 -and $PSVersionTable.PSVersion.Minor -eq 0)) { Write-Warning ("$logLead : PowerShell 5.1 or Higher is Required. Detected version: {0}" -f $PSVersionTable.PSVersion) throw ("$logLead : PowerShell 5.1 or Higher Required | https://go.microsoft.com/fwlink/?linkid=839516") } Write-Output ("$logLead : Ensuring Chocolatey Version >= V0.10.11") $currentChocolateyVersion = (Invoke-Expression "choco --version" -ErrorAction SilentlyContinue) $version = New-Object System.Version($currentChocolateyVersion) if (($null -ne $version) -and ($version.Minor -ge 10 -or ($version.Minor -eq 10 -and $version.Build -ge 11))) { Write-Output ("$logLead : Chocolatey Version is 0.10.11 or greater. Detected version: {0}" -f $currentChocolateyVersion) } elseif ($null -eq $currentChocolateyVersion) { Write-Warning ("$logLead : Chocolatey Not Found -- Attempting to Install") Set-ExecutionPolicy Bypass -Scope Process -Force;Invoke-Expression ((New-Object System.Net.WebClient).DownloadString('https://chocolatey.org/install.ps1')) } else { Write-Warning ("$logLead : Detected Chocolatey Version {0} -- Attempting to Upgrade" -f $logVersion) choco upgrade chocolatey -y --version 0.10.11 -s="https://chocolatey.org/api/v2/" } Write-Output ("$logLead : Ensuring that a chocolatey feed source URL is not configured multiple times, and that SDK feeds are authenticated.") $knownFeeds = @{} $sources = choco source list -r foreach($source in $sources) { $properties = $source.Split("|") $feedName = $properties[0] $feedUrl = $properties[1] $isDefaultFeed = $feedName -eq "chocolatey"; $isSdkFeed = (!$isDefaultFeed) -and ($feedUrl -notlike "*packagerepo.orb.alkamitech.com*"); $isDisabled = if ($properties[2] -like "true") { $true; } else { $false; } $authUser = $properties[3] if($isDisabled) { Write-Host "Skipping choco feed $feedName because it is disabled." continue } # Check that the every feed URL is only configured once. if($knownFeeds.ContainsKey($feedUrl)) { throw "The feed '$feedUrl' is configured multiple times. Remove one of them!" } else { Write-Host "Discovered feed '$feedUrl'" $knownFeeds[$feedUrl] = 1 } # Check that SDK feeds are authenticated. if($isSdkFeed -and [string]::IsNullOrWhiteSpace($authUser)) { throw "The SDK feed '$feedName' at source '$feedUrl' is not authenticated. Add credentials to this source!" } else { Write-Host "SDK Feed '$feedName' is authenticated." } } Write-Output ("$logLead : Checking for 7-Zip in the System Path Variable") $paths = [Environment]::GetEnvironmentVariable("Path", "Machine") if ($paths -notmatch '7-Zip') { Write-Warning ("$logLead : 7-Zip Install Directory Not Found in the System Path Variable") throw ("$logLead : Verify 7-Zip Installed & System Env:Path Added") } elseif (!(Invoke-Expression 7z.exe)){ Write-Warning ("$logLead : Could Not Invoke 7z.exe") throw ("$logLead : 7-Zip Could Not be Called") } Write-Output ("$logLead : Checking .NET Framework Version") $dotNetVersion = Get-DotNetVersion $dotNetMinimumKey = ([array]($Global:DotNetVersionTranslation | Where-Object {$_.FriendlyVersion -match $dotNetMinimumVersion}) | Select-Object -First 1).Key if ($dotNetVersion.Key -ge $dotNetMinimumKey) { Write-Host ("$logLead : .NET Framework {0} or higher detected, version = '{1}'" -f $dotNetMinimumVersion, $dotNetVersion.FriendlyVersion) } else { Write-Verbose ("$logLead : Minimum Version Key: {0}" -f $dotNetMinimumKey) Write-Verbose ("$logLead : Detected Version Key: {0}" -f $dotNetVersion) $dotNetError = ("$logLead : .NET Framework {0} or Higher is Required, but Found Version '{1}'" -f $dotNetMinimumVersion, $dotNetVersion.FriendlyVersion) Write-Warning $dotNetError throw ($dotNetError) } $requiredProducts = @( "Microsoft Web Platform Installer 5", "Microsoft Application Request Routing 3" "IIS URL Rewrite Module 2" ) Write-Output "$logLead : Checking for Microsoft Web Platform Installer 5+ and Required Components" $installedProducts = Get-CIMInstance -Class Win32_Product | Select-Object -ExpandProperty Name $allProductsInstalled = $true foreach ($product in $requiredProducts) { if ($installedProducts -match $product) { continue; } $allProductsInstalled = $false Write-Warning ("$logLead : Required Component <{0}> Not Found" -f $product) } if (!($allProductsInstalled)) { throw "$logLead : One or More Required Components Not Found" } else { Write-Output ("$logLead : All Expected Components Found") } Write-Output "$logLead : Validating that both machine.config files are valid xml" # This only checks that the files are valid xml. If they don't conform to MS's schema, that's a different issue that won't be caught here. try { [xml]$XmlDocument = Read-MachineConfig $false Write-Host "$logLead : Loaded 32 bit machine.config without issues." } catch [System.SystemException] { Write-Warning "Something's broken, something's broken..." Write-Warning $_.exception.message throw } try { [xml]$XmlDocument = Read-MachineConfig Write-Host "$logLead : Loaded 64 bit machine.config without issues." } catch [System.SystemException] { Write-Warning "Something's broken, something's broken..." Write-Warning $_.exception.message throw } }