Skip to content

Instantly share code, notes, and snippets.

@LordVeovis
Last active October 11, 2023 11:38
Show Gist options
  • Save LordVeovis/fb446be3381bd30557a374b2fbd2f279 to your computer and use it in GitHub Desktop.
Save LordVeovis/fb446be3381bd30557a374b2fbd2f279 to your computer and use it in GitHub Desktop.
Quick setup a workstation on Windows 11
#Requires -RunAsAdministrator
# launch: powershell -NoLogo -ExecutionPolicy ByPass .\Desktop\Clean-Bloatware.ps1
# crap removal
$apps = @(
'Microsoft.549981C3F5F10', # cortana
'Microsoft.BingNews',
'Microsoft.GetHelp',
'Microsoft.Getstarted',
'Microsoft.MicrosoftOfficeHub',
'Microsoft.MicrosoftSolitaireCollection',
'Microsoft.Paint',
'microsoft.windowscommunicationsapps',
'Microsoft.WindowsFeedbackHub',
'Microsoft.WindowsNotepad',
'Microsoft.WindowsMaps'
)
$apps_wilcard = @(
'*XBox*',
'*Zune*'
)
$provisionedApps = Get-AppxProvisionedPackage -Online
$i=1
foreach ($a in $apps) {
Write-Progress -PercentComplete ($i/$apps.Count) -Status "Removing crapware" -Activity $a
$provisionedApps | Where-Object DisplayName -EQ $a | Remove-AppxProvisionedPackage -Online -AllUsers
$i++
}
$i=1
foreach ($a in $apps_wilcard) {
Write-Progress -PercentComplete ($i/$apps_wilcard.Count) -Status "Removing crapware" -Activity $a
$provisionedApps | Where-Object DisplayName -Like $a | Remove-AppxProvisionedPackage -Online -AllUsers
$i++
}
# dism
$dism_wildcard = @(
'*Kernel-LA57-FoD-Package~*~amd64~~*',
'*Notepad-System-FoD-Package~*~amd64~~*',
'*WordPad-FoD-Package~*~amd64~~*'
)
$p = Get-WindowsPackage -Online | Where-Object PackageState -EQ Installed
foreach ($a in $dism_wildcard) {
Write-Host Removing $a
$pp = $p | Where-Object PackageName -CLike $a
if ($pp.Count -gt 0) {
Remove-WindowsPackage -Online -PackageName $pp.PackageName -NoRestart
}
}
$p | Where-Object PackageName -ILike *wordpad*~amd64~~* | Remove-WindowsPackage
#Requires -RunAsAdministrator
# step1: features list to enable
$features = @(
'Microsoft-Hyper-V-All',
'Containers',
'Microsoft-Windows-Subsystem-Linux'
)
$msstore = @(
'XP89DCGQ3K6VLD', # powertoys
'9P7KNL5RWT25', # sysinternals
'9PJSDV0VPK04', # bitwarden
'9NFNG39387K0', # yubico authenticator
'XPFFH613W8V6LV', # OBS
'9nblggh4vvnh', # VLC
'9PN20MSR04DW' # Ubuntu 22.04.2 LTS
)
$choco = @(
# simple packages
@{ Name = 'aida64-engineer'; PostInstall = { Remove-Item "$env:USERPROFILE\Desktop\AIDA64 Engineer.lnk" } },
@{ Name = '7zip' },
@{ Name = 'ferdium'; PostInstall = { Remove-Item "$env:PUBLIC\Desktop\Ferdium.lnk" } },
@{ Name = 'filezilla' },
@{ Name = 'goggalaxy'; IaParams = '/TASKS="!desktopicon"' }
@{ Name = 'mpc-hc-clsid2'; IaParams = '/TASKS="!desktopicon"' }
@{ Name = 'notepadplusplus' },
@{ Name = 'paint.net'; IaParams = '"DESKTOPSHORTCUT=0"' },
@{ Name = 'steam'; PostInstall = { Remove-Item "$env:PUBLIC\Desktop\Steam.lnk"; Remove-ItemProperty HKCU:\Software\Microsoft\Windows\CurrentVersion\Run\ Steam } },
@{ Name = 'treesizefree' },
@{ Name = 'ida-free'; ChocoParams = @('--ignore-checksums'); PostInstall = { Remove-Item "$env:PUBLIC\Desktop\IDA Freeware*.lnk" }},
# packages with params
@{ Name = 'git'; Params = '"/GitOnlyOnPath /NoAutoCrlf /WindowsTerminal /NoShellIntegration /SChannel /NoOpenSSH /WindowsTerminalProfile /DefaultBranchName:master /Editor:VisualStudioCode"' },
@{ Name = 'vscode'; Params = '"/NoDesktopIcon /DontAddToPath"' },
# fat packages
@{ Name = 'vmwareworkstation'; IaParams = 'DESKTOP_SHORTCUT=0' },
@{ Name = 'sql-server-management-studio' },
@{ Name = 'visualstudio2022enterprise'; Params = '"--add Microsoft.VisualStudio.Workload.ManagedDesktop --add Microsoft.VisualStudio.Workload.NativeDesktop --includeRecommended --includeOptional --passive --locale en-US"'; PostInstall = {
(Get-Service Incredibuild*) + (Get-Service IBXDashboard) | ForEach-Object {
Set-Service $_.Name -StartupType Manual;
Stop-Service $_.Name }
Remove-ItemProperty HKLM:\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Run "IncrediBuild Agent Monitor"
} },
@{ Name = 'windows-adk'; IaParams = '"/ceip off /q /features OptionId.DeploymentTools"'; OverrideParams = $true },
@{ Name = 'docker-desktop'; IaParams = '"install --quiet --accept-license --always-run-service"'; OverrideParams = $true; PostInstall = {
Remove-Item "$env:userprofile\desktop\docker desktop.lnk"
Remove-ItemProperty HKCU:\Software\Microsoft\Windows\CurrentVersion\Run\ "Docker Desktop"
} },
@{ Name = 'eset-internet-security'; ChocoParams = @('--ignore-checksums') }
)
#region Install installers
function Update-Winget {
$currentVersion = (Get-AppxPackage Microsoft.DesktopAppInstaller).Version
if ($currentVersion -lt '1.20.2201.0') {
$wc = New-Object System.Net.WebClient
# install microsoft.ui.xaml 2.7
$url = "https://github.com/microsoft/microsoft-ui-xaml/releases/download/v2.7.3/Microsoft.UI.Xaml.2.7.x64.appx"
$wc.DownloadFile($url, "$env:temp\microsoft.ui.xaml.appx")
Add-AppxPackage -Path "$env:temp\microsoft.ui.xaml.appx"
Remove-Item "$env:temp\microsoft.ui.xaml.appx"
# install Microsoft.VCLibs.140.00.UWPDesktop
$url = 'https://aka.ms/Microsoft.VCLibs.x64.14.00.Desktop.appx'
$wc.DownloadFile($url, "$env:temp\Microsoft.VCLibs.x64.14.00.Desktop.appx")
Add-AppxPackage -Path "$env:temp\Microsoft.VCLibs.x64.14.00.Desktop.appx"
Remove-Item "$env:temp\Microsoft.VCLibs.x64.14.00.Desktop.appx"
# get latest download url
$url = "https://api.github.com/repos/microsoft/winget-cli/releases/latest"
$url = (Invoke-WebRequest -Uri $url).Content | ConvertFrom-Json |
Select-Object -ExpandProperty "assets" |
Where-Object "browser_download_url" -Match '.msixbundle' |
Select-Object -ExpandProperty "browser_download_url"
# download
$wc.DownloadFile($url, "$env:temp\Setup.msix")
# install
Add-AppxPackage -Path "$env:temp\Setup.msix"
# delete file
Remove-Item "$env:temp\Setup.msix"
$wc.Dispose()
}
}
function Install-Choco {
Set-ExecutionPolicy -ExecutionPolicy Bypass -Scope Process -Force
Invoke-WebRequest https://community.chocolatey.org/install.ps1 -UseBasicParsing | Invoke-Expression
$env:Path = [System.Environment]::GetEnvironmentVariable("Path","Machine") + ";" + [System.Environment]::GetEnvironmentVariable("Path","User") + ";%ALLUSERSPROFILE%\chocolatey\bin"
}
#endregion
function Install-Step1-DISM {
param (
[string[]]$Features
)
$needsReboot = $false
foreach ($f in $features) {
$p = Get-WindowsOptionalFeature -Online -FeatureName $f
if ($p.State -ne 'Enabled') {
Write-Host Enabling feature $f
Enable-WindowsOptionalFeature -Online -FeatureName $f -NoRestart
$needsReboot = $true
}
}
if ($needsReboot) {
Restart-Computer
}
& wsl --update
}
function Install-Step2-MsStore {
param (
[string[]]$MsStoreIds
)
# BUG windows 11 2023-08: need "Programme d'installation d'application" à jour dans Windows Store manuellement
#Write-Host Open the Windows Store and update "Programme d'installation d'application"
#Write-Host Press a key when it`'s done
#Read-Host
foreach ($id in $MsStoreIds) {
Write-Host Installing $id from Microsoft Store
winget install -e --id $id --source=msstore --accept-source-agreements --accept-package-agreements
}
# post-install clean steps
Remove-Item "$env:PUBLIC\Desktop\OBS Studio.lnk" -ErrorAction SilentlyContinue
}
function Install-Step3-Choco {
param (
$ChocoPakages
)
$ChocoPakages | ForEach-Object {
Install-Choco-Package -PackageName $_.Name -Params $_.Params -IaParams $_.IaParams -ChocoParams $_.ChocoParams -OverrideParams:$_.OverrideParams -PostInstallScriptBlock $_.PostInstall
}
}
function Install-Choco-Package {
param (
[Parameter(Mandatory)]
[string]$PackageName,
[string]$Params,
[string]$IaParams,
[string[]]$ChocoParams,
[switch]$OverrideParams = $false,
[System.Management.Automation.ScriptBlock]$PostInstallScriptBlock
)
Write-Host Installing $PackageName with choco
$installed = (& choco list -e $PackageName | Select-String '0 packages installed').Matches.Count -ne 1
if (-Not $installed) {
$_params = @('install', '-y', $PackageName)
if ($ChocoParams.Count -gt 0) {
$_params += , $ChocoParams
}
if (-Not([string]::IsNullOrWhiteSpace($IaParams))) {
$_params += '--ia'
$_params += $IaParams
}
if ($OverrideParams) {
$_params += '-o'
}
if (-Not([string]::IsNullOrWhiteSpace($Params))) {
$_params += '--params'
$_params += $Params
}
& choco $_params
if ($null -ne $PostInstallScriptBlock) {
$PostInstallScriptBlock.Invoke()
}
}
}
function Switch-BlackTheme {
New-ItemProperty -Path HKCU:\SOFTWARE\Microsoft\Windows\CurrentVersion\Themes\Personalize -Name AppsUseLightTheme -Value 0 -Type Dword -Force
New-ItemProperty -Path HKCU:\SOFTWARE\Microsoft\Windows\CurrentVersion\Themes\Personalize -Name SystemUsesLightTheme -Value 0 -Type Dword -Force
}
Switch-BlackTheme
Install-Step1-DISM -Features $features
Update-Winget
Install-Step2-MsStore -MsStoreIds $msstore
Install-Choco
Install-Step3-Choco -ChocoPakages $choco
#Requires -Modules Hyper-V
$_root = "E:\windows11"
$iso = ".\output\windows11.iso"
$vmName = 'win11'
$swName = 'Eth Switch'
$FunctionsToExport = @()
function Remove-TestVM {
param (
[Parameter(Mandatory)]
[string]$VMName
)
$vm = Get-VM -Name $VMName
if ($null -ne $vm) {
Stop-VM -VMName $VMName -TurnOff -Force
# merging disks
do {
$s = (Get-VM $VMName).OperationalStatus
sleep 5
} until ($s.Count -eq 1 -and $s[0] -eq 'Ok')
$hd = Get-VMHardDiskDrive -VMName $VMName
$hdpath = $hd.Path
Remove-VMHardDiskDrive $hd
Remove-Item $hdpath
Remove-VM -Name $VMName -Force
}
}
function Update-TestISO {
param (
[Parameter(Mandatory)]
[string]$UnattendFile,
[Parameter(Mandatory)]
[string]$WindowsSourceRoot,
[Parameter(Mandatory)]
[string]$IsoDest,
[bool]$ArchiveUnattendFile = $true
)
$_oscdimg = "${env:ProgramFiles(x86)}\Windows Kits\10\Assessment and Deployment Kit\Deployment Tools\amd64\Oscdimg\oscdimg.exe"
$efiBin = [System.IO.Path]::Combine($WindowsSourceRoot, 'efi\microsoft\boot\efisys_noprompt.bin')
$targetUnattendFile = [System.IO.Path]::Combine($WindowsSourceRoot, 'autounattend.xml')
$archiveDir = [System.IO.Path]::Combine($_root, 'archive')
if ($ArchiveUnattendFile) {
if (-not (Test-Path -Path "$archiveDir" -PathType Container)) {
New-Item $archiveDir -ItemType Directory
}
if (Test-Path -Path "$targetUnattendFile") {
$archiveName = [System.IO.Path]::Combine($archiveDir, ".\_autounattend.xml.$((Get-Date).ToString("yyyyMMddHHmmss"))")
Copy-Item $targetUnattendFile $archiveName
}
}
Copy-Item $UnattendFile $targetUnattendFile
& $_oscdimg -m -o -u2 -udfver102 -bootdata:1#pEF,e,b$efiBin "$WindowsSourceRoot" "$IsoDest"
}
function Create-TestVM {
param (
[Parameter(Mandatory)]
[string]$VMName,
[Parameter(Mandatory)]
[string]$IsoSource
)
$vmDiskDir = [System.IO.Path]::Combine($_root, 'vm')
$vhdx = [System.IO.Path]::Combine($vmDiskDir, 'win11.vhdx')
if (-not (Test-Path $vmDiskDir -PathType Container)) {
New-Item $vmDiskDir -ItemType Directory
}
$vm = New-VM -Name $VMName -MemoryStartupBytes 4GB -Generation 2 -NewVHDPath $vhdx -NewVHDSizeBytes 100GB -SwitchName $swName
$dvd = Add-VMDvdDrive -VM $vm -Path $IsoSource -Passthru
Set-VMFirmware -VM $vm -FirstBootDevice $dvd
Set-VMProcessor -VM $vm -Count 2
# disable checkpoints
Set-VM $vm -AutomaticCheckpointsEnabled:$false
# tpm
$owner = Get-HgsGuardian UntrustedGuardian
$kp = New-HgsKeyProtector -Owner $owner -AllowUntrustedRoot
Set-VMKeyProtector -VM $vm -KeyProtector $kp.RawData
Enable-VMTPM -VM $vm
# start
Start-VM $vm
}
$isoFullName = [System.IO.Path]::Combine($_root, $iso)
Remove-TestVM -VMName $vmName
Update-TestISO -UnattendFile $_root\autounattend.xml -WindowsSourceRoot $_root\iso -IsoDest $isoFullName
Create-TestVM -VMName $vmName -IsoSource $isoFullName
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment