Initialize-PC.ps1

<#PSScriptInfo
.VERSION 1.33
.GUID c7e4c2a6-c3a3-45af-b82a-01d0a2ca28c1
.AUTHOR Dave Farinelli
.LICENSEURI https://www.gnu.org/licenses/gpl-3.0.en.html
.PROJECTURI https://github.com/dfar-io/initialize-pc
#>


<#
.DESCRIPTION
 Run this script to set up a new Windows PC. This script is safe to run multiple
 times to allow for reconfiguration.
#>


#Requires -RunAsAdministrator

Param(
  [switch] $SkipPrompts
)

function InstallChocolatey {
  [Diagnostics.CodeAnalysis.SuppressMessageAttribute( `
      "PSAvoidUsingInvokeExpression", `
      "", `
      Justification = "Using Chocolatey-provided call")]
  param()

  try {
    choco -v | Out-Null
    Write-Output 'Chocolatey already installed.'
    return
  }
  catch {
    $downloadUrl = 'https://chocolatey.org/install.ps1'
    Write-Output 'Installing Chocolatey...'
    Set-ExecutionPolicy Bypass -Scope Process -Force; `
      Invoke-Expression `
    ((New-Object System.Net.WebClient).DownloadString($downloadUrl))
  }
}

function InstallSoftwareWithChocolatey {
  Write-Output 'Installing Software with Chocolatey...'
  choco install -y `
    greenshot `
    googlechrome `
    divvy `
    7zip `
    ccleaner `
    dropbox `
    filezilla `
    git `
    nodejs `
    libreoffice-fresh `
    vscode `
    rescuetime `
    bitnami-xampp `
    mysql.workbench `
    qbittorrent `
    sql-server-management-studio `
    azure-cli `
    franz `
    intellijidea-community `
    psscriptanalyzer `
    kubernetes-cli `
    jdk8 `
    wsl-ubuntu-1804 `
    terraform `
    kubernetes-helm `
    insomnia-rest-api-client `
    azure-functions-core-tools `
    visualstudio2017-workload-netcorebuildtools `
    dotnetcore-sdk `
    sql-server-express `
    autohotkey `
    youtube-dl `
    vlc `
    steam
}

function InstallAdditionalSoftware {
  npm i -g @angular/cli

  if (IsSoftwareAlreadyInstalled("OpenVPN Connect")) {
    Write-Output "OpenVPN Connect already installed."
    return;
  }

  Write-Output 'Installing OpenVPN Connect...'
  Invoke-WebRequest `
    -Uri "https://swupdate.openvpn.net/as/clients/openvpn-connect-2.7.1.101_signed.msi" `
    -OutFile "install.msi"
  Start-Process install.msi -Wait
  Remove-Item install.msi
}

function IsSoftwareAlreadyInstalled($name) {
  $x86 = ((Get-ChildItem "HKLM:\Software\Microsoft\Windows\CurrentVersion\Uninstall") |
    Where-Object { $_.GetValue( "DisplayName" ) -like "*$name*" } ).Length -gt 0;

  $x64 = ((Get-ChildItem "HKLM:\Software\Wow6432Node\Microsoft\Windows\CurrentVersion\Uninstall") |
    Where-Object { $_.GetValue( "DisplayName" ) -like "*$name*" } ).Length -gt 0;

  return $x86 -or $x64;
}

function InvokeWindowsUpdate {
  if ($SkipPrompts) {
    Write-Output "Skipping updating Windows."
    return
  }

  WaitForPrompt("Update Windows")
}

function UninstallApplication($name) {
  $app = Get-CimInstance -Class Win32_Product `
    -Filter "Name = '$name'"

  if ($null -eq $app) {
    Write-Output "$name not found, no need to uninstall."
    return
  }
  else {
    $app.Uninstall()
  }
}

function ImportStartMenu {
  if ($SkipPrompts) {
    Write-Output "Skipping importing Start Menu."
    return;
  }

  WaitForPrompt("Clean up the start menu of all tiles")
  WaitForPrompt("Unpin all items")
}

function WaitForPrompt($prompt) {
  do {
    $value = Read-Host "$prompt ('y' to continue)"
  }
  while ($value -notmatch 'y')
}

function InitializeSoftware {
  if ($SkipPrompts) {
    Write-Output "Skipping configuration of software."
    return;
  }

  WaitForPrompt("OpenVPN - Add all VPN servers")
  WaitForPrompt("Mail - add accounts, create linked inbox, turn off email notifications, signature, calendar on Monday")
  WaitForPrompt("Chrome - sign in")
  WaitForPrompt("Dropbox - sign in, change to simple directory")
  WaitForPrompt("Divvy - register, start at Login, hide from tray, set shortcut")
  WaitForPrompt("VSCode - install FiraCode")
  WaitForPrompt("VSCode - Perform Settings Sync (Shift-Alt-D)")
  WaitForPrompt("Greenshot - Increase icon size to 32, set output, remove magnifier")
  WaitForPrompt("PowerShell - Increase font size, use Fira Code")
  WaitForPrompt("Franz - Login to all services")
  WaitForPrompt("CCleaner - Add /pictures, /desktop, /download (clear after 24 hours), Save all settings to INI file.")
}

function SetTimeZone {
  Write-Output "Setting Time Zone..."
  tzutil /s "Eastern Standard Time"
}

function SetPowershellProfile {
  Write-Output "Setting PowerShell profile..."
  New-Item -Path $Profile -Type File -Force | Out-Null
  Write-Output "Set-Location D:/" | Out-File $Profile
}

function InitializeGit {
  Write-Output "Configuring git..."
  git config --global user.name "Dave Farinelli"
  git config --global user.email "d@dfar.io"
}

function ClearDesktop {
  Write-Output 'Deleting desktop icons...'
  Remove-Item C:\Users\*\Desktop\*lnk -Force
}

function Edit-Registry {
  ModifyRegistryValue `
    -Name "Cortana" `
    -RegPath "HKLM:\SOFTWARE\Policies\Microsoft\Windows" `
    -RegName "Windows Search" `
    -PropName "AllowCortana" 0

  ModifyRegistryValue `
    -Name "Search Button" `
    -RegPath "HKCU:\Software\Microsoft\Windows\CurrentVersion" `
    -RegName "Search" `
    -PropName "SearchboxTaskbarMode" 0

  ModifyRegistryValue `
    -Name "Task View" `
    -RegPath "HKCU:\Software\Microsoft\Windows\CurrentVersion\Explorer" `
    -RegName "Advanced" `
    -PropName "ShowTaskViewButton" 0

  ModifyRegistryValue `
    -Name "People Button" `
    -RegPath "HKCU:\Software\Microsoft\Windows\CurrentVersion\Explorer\Advanced" `
    -RegName "People" `
    -PropName "PeopleBand" 0

  ModifyRegistryValue `
    -Name "Multi Taskbar" `
    -RegPath "HKCU:\Software\Policies\Microsoft\Windows" `
    -RegName "Explorer" `
    -PropName "TaskbarNoMultimon" 1

  ModifyRegistryValue `
    -Name "Start Menu Suggestions" `
    -RegPath "HKCU:\SOFTWARE\Microsoft\Windows\CurrentVersion" `
    -RegName "ContentDeliveryManager" `
    -PropName "SystemPaneSuggestionsEnabled" 0

  #Restart Explorer to change it immediately
  Stop-Process -name explorer
}
function ModifyRegistryValue {
  Param (
    [Parameter(Mandatory = $true)]
    [string] $Name,
    [Parameter(Mandatory = $true)]
    [string] $RegPath,
    [Parameter(Mandatory = $true)]
    [string] $RegName,
    [Parameter(Mandatory = $true)]
    [string] $PropName,
    [Parameter(Mandatory = $true)]
    [int] $Value
  )

  Write-Output "Disabling $Name..."
  $path = "$RegPath\$RegName"
  IF (!(Test-Path -Path $path)) {
    New-Item -Path $RegPath -Name $RegName
  }
  Set-ItemProperty -Path $path -Name $PropName -Value $Value
}

function Remove-Clutter {
  [CmdletBinding(SupportsShouldProcess = $true, ConfirmImpact = "Medium")]
  param()

  Write-Output "Deleting Windows Appx packages..."

  $appxPackagesToDelete = @(
    "windowsalarms",
    "getstarted",
    "zunemusic",
    "windowsapps",
    "SolitaireCollection",
    "bingnews",
    "onenote",
    "windowsphone",
    "weather",
    "DellInc.DellSupportAssistforPCs",
    "DellInc.DellDigitalDelivery",
    "DellInc.DellCommandUpdate",
    "WindowsFeedbackHub",
    "Microsoft.Office.Desktop",
    "ScreenSketch",
    "YourPhone",
    "GetHelp",
    "MobilePlans",
    "MixedReality",
    "LinkedIn",
    "Microsoft3DViewer",
    "WindowsMaps",
    "Microsoft.Messaging",
    "Spotify",
    "Microsoft.Xbox.TCUI",
    "Microsoft.Wallet",
    "Microsoft.XboxSpeechToTextOverlay",
    "Microsoft.XboxApp",
    "Microsoft.XboxIdentityProvider"
  )

  $appxPackagesToDelete | ForEach-Object -Process { DeleteAppxPackage($_) }

  UninstallOneDrive
}

function DeleteAppxPackage($packageName) {
  Write-Output "Removing $packageName appx package."
  Get-AppxPackage *$packageName* | Remove-AppxPackage
}

function UninstallOneDrive {
  Write-Output "Uninstalling OneDrive..."
  taskkill /f /im OneDrive.exe | Out-Null
  C:\WINDOWS\SysWOW64\OneDriveSetup.exe /uninstall
}



################################################################################

SetTimeZone
Edit-Registry
Remove-Clutter
ImportStartMenu
InvokeWindowsUpdate
InstallChocolatey
InstallSoftwareWithChocolatey
InstallAdditionalSoftware
InitializeSoftware
InvokeWindowsUpdate
SetPowershellProfile
InitializeGit
ClearDesktop