Replaces the single-session "cancel PPKG reboot and cram everything into
one autologon" flow with a staged chain where each reboot advances to the
next step automatically. The technician touches the keyboard 3 times total
(UNPLUG prompt, Y to reboot, Configure-PC selections).
New Stage-Dispatcher.ps1:
Reads C:\Enrollment\setup-stage.txt and chains through:
shopfloor-setup -> sync-intune -> configure-pc
Each stage re-registers HKLM RunOnce so the dispatcher fires again on
the next logon. Stage file is deleted when the chain completes.
Transcript logged to C:\Logs\SFLD\stage-dispatcher.log.
Stage "shopfloor-setup": runs Run-ShopfloorSetup.ps1 (which reboots via
shutdown /r /t 10). Dispatcher advances stage to sync-intune in the
~10 second window before the machine goes down, re-registers RunOnce.
Stage "sync-intune": launches Monitor-IntuneProgress.ps1 -Unattended.
Exit 2 (pre-reboot done, user confirmed): dispatcher re-registers
RunOnce and initiates shutdown /r /t 5. Stage stays at sync-intune so
the monitor picks up post-reboot state on next boot.
Exit 0 (post-reboot install complete): dispatcher chains directly to
Configure-PC.ps1 in the same session, then deletes the stage file.
Stage "configure-pc": runs Configure-PC.ps1 and deletes the stage file.
Fallback entry point if the post-reboot chain was interrupted.
Modified run-enrollment.ps1:
Removed the shutdown /a that canceled the PPKG reboot. Instead writes
setup-stage.txt = "shopfloor-setup" and registers RunOnce for the
dispatcher. PPKG reboot fires naturally (handles PendingFileRename
operations like Zscaler rename and PPKG self-cleanup). Now tracked in
the git repo at playbook/shopfloor-setup/run-enrollment.ps1.
Modified Monitor-IntuneProgress.ps1:
New -Unattended switch. When set:
Invoke-SetupComplete exits 0 without waiting for keypress.
Invoke-RebootPrompt exits 2 without prompting or rebooting (dispatcher
handles both). Manual sync_intune.bat usage (no flag) unchanged.
RetriggerMinutes bumped from 3 to 5 (user request).
Modified startnet.cmd:
Now also copies Stage-Dispatcher.ps1 from the PXE server to
W:\Enrollment\Stage-Dispatcher.ps1 alongside run-enrollment.ps1.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
79 lines
3.1 KiB
PowerShell
Executable File
79 lines
3.1 KiB
PowerShell
Executable File
# run-enrollment.ps1
|
|
# Installs GCCH enrollment provisioning package via Install-ProvisioningPackage
|
|
# Called by FirstLogonCommands as SupportUser (admin) after imaging
|
|
|
|
$ErrorActionPreference = 'Continue'
|
|
$logFile = "C:\Logs\enrollment.log"
|
|
New-Item -ItemType Directory -Path "C:\Logs" -Force -ErrorAction SilentlyContinue | Out-Null
|
|
|
|
function Log {
|
|
param([string]$Message)
|
|
$ts = Get-Date -Format "yyyy-MM-dd HH:mm:ss"
|
|
$line = "$ts $Message"
|
|
Write-Host $line
|
|
Add-Content -Path $logFile -Value $line
|
|
}
|
|
|
|
Log "=== GE Aerospace GCCH Enrollment ==="
|
|
|
|
# --- Find the .ppkg ---
|
|
$ppkgFile = Get-ChildItem "C:\Enrollment\*.ppkg" -ErrorAction SilentlyContinue | Select-Object -First 1
|
|
if (-not $ppkgFile) {
|
|
Log "ERROR: No .ppkg found in C:\Enrollment\"
|
|
exit 1
|
|
}
|
|
Log "Package: $($ppkgFile.Name)"
|
|
|
|
# --- Set computer name to E<serial> ---
|
|
$serial = (Get-CimInstance Win32_BIOS).SerialNumber
|
|
$newName = "E$serial"
|
|
Log "Setting computer name to $newName"
|
|
Rename-Computer -NewName $newName -Force -ErrorAction SilentlyContinue
|
|
|
|
# --- Install provisioning package ---
|
|
Log "Installing provisioning package..."
|
|
try {
|
|
Install-ProvisioningPackage -PackagePath $ppkgFile.FullName -ForceInstall -QuietInstall
|
|
Log "Provisioning package installed successfully."
|
|
} catch {
|
|
Log "ERROR: Install-ProvisioningPackage failed: $_"
|
|
Log "Attempting fallback with Add-ProvisioningPackage..."
|
|
try {
|
|
Add-ProvisioningPackage -PackagePath $ppkgFile.FullName -ForceInstall -QuietInstall
|
|
Log "Provisioning package added successfully (fallback)."
|
|
} catch {
|
|
Log "ERROR: Fallback also failed: $_"
|
|
exit 1
|
|
}
|
|
}
|
|
|
|
# --- Set OOBE complete ---
|
|
Log "Setting OOBE as complete..."
|
|
reg add "HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Setup\OOBE" /v OOBEComplete /t REG_DWORD /d 1 /f | Out-Null
|
|
reg add "HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Setup\OOBE" /v SetupDisplayedEula /t REG_DWORD /d 1 /f | Out-Null
|
|
|
|
# --- Stage the imaging chain for next boot ---
|
|
# The PPKG schedules a reboot (PendingFileRenameOperations for Zscaler
|
|
# rename, PPKG self-cleanup, etc). Instead of canceling it and cramming
|
|
# Run-ShopfloorSetup into this same session, we let the reboot happen
|
|
# and register a RunOnce entry that fires Stage-Dispatcher.ps1 on the
|
|
# next autologon. The dispatcher reads setup-stage.txt and chains
|
|
# through: shopfloor-setup -> sync-intune -> configure-pc.
|
|
$stageFile = 'C:\Enrollment\setup-stage.txt'
|
|
$dispatcherPath = 'C:\Enrollment\Stage-Dispatcher.ps1'
|
|
$runOnceKey = 'HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\RunOnce'
|
|
|
|
Log "Writing stage file: shopfloor-setup"
|
|
Set-Content -LiteralPath $stageFile -Value 'shopfloor-setup' -Force
|
|
|
|
if (Test-Path -LiteralPath $dispatcherPath) {
|
|
Log "Registering RunOnce for Stage-Dispatcher.ps1"
|
|
Set-ItemProperty -Path $runOnceKey -Name 'ShopfloorSetup' `
|
|
-Value "powershell.exe -NoProfile -ExecutionPolicy Bypass -File `"$dispatcherPath`"" `
|
|
-Type String -Force
|
|
} else {
|
|
Log "WARNING: Stage-Dispatcher.ps1 not found at $dispatcherPath - RunOnce not set"
|
|
}
|
|
|
|
Log "=== Enrollment complete. PPKG reboot will fire and Stage-Dispatcher picks up on next logon. ==="
|