Some checks failed
CD Pipeline / workflow-shape (push) Successful in 0s
CD Pipeline / cancel-stale-cd (push) Has been skipped
CD Pipeline / build-and-deploy (push) Has been cancelled
CD Pipeline / post-deploy-checks (push) Has been cancelled
CD Pipeline / tests (push) Has been cancelled
163 lines
5.6 KiB
PowerShell
163 lines
5.6 KiB
PowerShell
param(
|
|
[ValidateSet("Verify", "DryRun", "Apply")]
|
|
[string]$Mode = "Verify",
|
|
[string]$VmrunPath = "C:\Program Files (x86)\VMware\VMware Workstation\vmrun.exe",
|
|
[string]$Host111Vmx = "",
|
|
[string]$Host188Vmx = "",
|
|
[string]$Host120Vmx = "",
|
|
[string]$Host121Vmx = "",
|
|
[string]$Host112Vmx = "",
|
|
[string[]]$DiscoveryRoot = @("D:\VMs", "E:\VMs", "C:\VMs", "C:\Users\Public\Documents\Virtual Machines")
|
|
)
|
|
|
|
$ErrorActionPreference = "Stop"
|
|
|
|
$TaskName = "AWOOOI-Start-VMware-VMs"
|
|
$ProgramDataDir = "C:\ProgramData\AWOOOI"
|
|
$StartScript = Join-Path $ProgramDataDir "Start-AWOOOI-VMs.ps1"
|
|
$VmOrder = @("111", "188", "120", "121", "112")
|
|
$SuppliedVmx = @{
|
|
"111" = $Host111Vmx
|
|
"188" = $Host188Vmx
|
|
"120" = $Host120Vmx
|
|
"121" = $Host121Vmx
|
|
"112" = $Host112Vmx
|
|
}
|
|
|
|
function Resolve-VmxPath {
|
|
param([string]$HostAlias)
|
|
|
|
$supplied = $SuppliedVmx[$HostAlias]
|
|
if ($supplied -and (Test-Path -LiteralPath $supplied)) {
|
|
return (Resolve-Path -LiteralPath $supplied).Path
|
|
}
|
|
|
|
foreach ($root in $DiscoveryRoot) {
|
|
if (-not (Test-Path -LiteralPath $root)) {
|
|
continue
|
|
}
|
|
$match = Get-ChildItem -LiteralPath $root -Recurse -Filter "*.vmx" -ErrorAction SilentlyContinue |
|
|
Where-Object { $_.FullName -match "(^|[\\_\-\s])$HostAlias([\\_\-\s]|$)" } |
|
|
Select-Object -First 1
|
|
if ($match) {
|
|
return $match.FullName
|
|
}
|
|
}
|
|
return ""
|
|
}
|
|
|
|
function Get-VmMap {
|
|
$map = [ordered]@{}
|
|
foreach ($alias in $VmOrder) {
|
|
$map[$alias] = Resolve-VmxPath -HostAlias $alias
|
|
}
|
|
return $map
|
|
}
|
|
|
|
function Write-StartupScript {
|
|
param([hashtable]$VmMap)
|
|
|
|
New-Item -ItemType Directory -Path $ProgramDataDir -Force | Out-Null
|
|
$vmRows = foreach ($alias in $VmOrder) {
|
|
" @{ Alias = `"$alias`"; Path = `"$($VmMap[$alias])`" }"
|
|
}
|
|
$body = @"
|
|
`$ErrorActionPreference = "Continue"
|
|
`$VmrunPath = "$VmrunPath"
|
|
`$VMs = @(
|
|
$($vmRows -join ",`n")
|
|
)
|
|
|
|
Start-Service -Name "VMAuthdService" -ErrorAction SilentlyContinue
|
|
Start-Service -Name "VMnetDHCP" -ErrorAction SilentlyContinue
|
|
Start-Service -Name "VMware NAT Service" -ErrorAction SilentlyContinue
|
|
Start-Sleep -Seconds 30
|
|
|
|
foreach (`$vm in `$VMs) {
|
|
if (-not (Test-Path -LiteralPath `$vm.Path)) {
|
|
Write-Output "VMX_MISSING alias=`$(`$vm.Alias) path=`$(`$vm.Path)"
|
|
continue
|
|
}
|
|
& `$VmrunPath -T ws start `$vm.Path nogui
|
|
Write-Output "VM_START_REQUESTED alias=`$(`$vm.Alias) path=`$(`$vm.Path) exit=`$LASTEXITCODE"
|
|
Start-Sleep -Seconds 20
|
|
}
|
|
"@
|
|
Set-Content -LiteralPath $StartScript -Value $body -Encoding UTF8
|
|
}
|
|
|
|
function Apply-WindowsUpdatePolicy {
|
|
$auPath = "HKLM:\SOFTWARE\Policies\Microsoft\Windows\WindowsUpdate\AU"
|
|
New-Item -Path $auPath -Force | Out-Null
|
|
New-ItemProperty -Path $auPath -Name "NoAutoRebootWithLoggedOnUsers" -Value 1 -PropertyType DWord -Force | Out-Null
|
|
New-ItemProperty -Path $auPath -Name "AlwaysAutoRebootAtScheduledTime" -Value 0 -PropertyType DWord -Force | Out-Null
|
|
New-ItemProperty -Path $auPath -Name "AUOptions" -Value 3 -PropertyType DWord -Force | Out-Null
|
|
New-ItemProperty -Path $auPath -Name "ScheduledInstallDay" -Value 0 -PropertyType DWord -Force | Out-Null
|
|
New-ItemProperty -Path $auPath -Name "ScheduledInstallTime" -Value 3 -PropertyType DWord -Force | Out-Null
|
|
New-ItemProperty -Path $auPath -Name "AUPowerManagement" -Value 0 -PropertyType DWord -Force | Out-Null
|
|
}
|
|
|
|
function Apply-ScheduledTask {
|
|
$action = New-ScheduledTaskAction `
|
|
-Execute "powershell.exe" `
|
|
-Argument "-NoProfile -ExecutionPolicy Bypass -File `"$StartScript`""
|
|
$trigger = New-ScheduledTaskTrigger -AtStartup
|
|
$principal = New-ScheduledTaskPrincipal -UserId "SYSTEM" -RunLevel Highest
|
|
$settings = New-ScheduledTaskSettingsSet `
|
|
-AllowStartIfOnBatteries `
|
|
-DontStopIfGoingOnBatteries `
|
|
-MultipleInstances IgnoreNew `
|
|
-RestartCount 3 `
|
|
-RestartInterval (New-TimeSpan -Minutes 2) `
|
|
-StartWhenAvailable
|
|
Register-ScheduledTask `
|
|
-TaskName $TaskName `
|
|
-Action $action `
|
|
-Trigger $trigger `
|
|
-Principal $principal `
|
|
-Settings $settings `
|
|
-Force | Out-Null
|
|
}
|
|
|
|
$vmMap = Get-VmMap
|
|
$missing = @($VmOrder | Where-Object { -not $vmMap[$_] })
|
|
$vmrunPresent = Test-Path -LiteralPath $VmrunPath
|
|
|
|
Write-Output "AWOOOI_WINDOWS99_VMWARE_AUTOSTART=1"
|
|
Write-Output "MODE=$Mode"
|
|
Write-Output "VMRUN_PRESENT=$([int]$vmrunPresent)"
|
|
foreach ($alias in $VmOrder) {
|
|
Write-Output "VMX alias=$alias path=$($vmMap[$alias]) present=$([int][bool]$vmMap[$alias])"
|
|
}
|
|
|
|
if (-not $vmrunPresent) {
|
|
Write-Error "vmrun.exe not found at $VmrunPath"
|
|
}
|
|
|
|
if ($missing.Count -gt 0) {
|
|
Write-Output "MISSING_VMX_ALIASES=$($missing -join ',')"
|
|
if ($Mode -eq "Apply") {
|
|
throw "Apply requires explicit or discoverable VMX paths for every required VM."
|
|
}
|
|
}
|
|
|
|
if ($Mode -eq "Verify") {
|
|
exit 0
|
|
}
|
|
|
|
if ($Mode -eq "DryRun") {
|
|
Write-Output "DRY_RUN would_write_start_script=$StartScript"
|
|
Write-Output "DRY_RUN would_register_task=$TaskName"
|
|
Write-Output "DRY_RUN would_apply_windows_update_no_auto_reboot_policy=1"
|
|
exit 0
|
|
}
|
|
|
|
Write-StartupScript -VmMap $vmMap
|
|
Set-Service -Name "VMAuthdService" -StartupType Automatic -ErrorAction SilentlyContinue
|
|
Set-Service -Name "VMnetDHCP" -StartupType Automatic -ErrorAction SilentlyContinue
|
|
Set-Service -Name "VMware NAT Service" -StartupType Automatic -ErrorAction SilentlyContinue
|
|
Apply-ScheduledTask
|
|
Apply-WindowsUpdatePolicy
|
|
|
|
Write-Output "APPLIED scheduled_task=$TaskName start_script=$StartScript windows_update_no_auto_reboot_policy=1"
|