Introduction

PowerShell 4.0, which ships with Windows Server 2012 R2, brings Desired State Configuration (DSC), enhanced debugging, and improved workflows to Windows administration. Performing initial configuration through PowerShell rather than the GUI creates repeatable, auditable, and scriptable setup procedures that work consistently across all servers. This guide covers every initial configuration task using PowerShell 4.0 commands specific to Windows Server 2012 R2.

Setting Execution Policy

Before running any configuration scripts, set the appropriate execution policy:

# Allow signed scripts from the internet and unsigned local scripts
Set-ExecutionPolicy RemoteSigned -Force

# For automation servers, use AllSigned or Bypass within constrained sessions
Get-ExecutionPolicy -List

Computer Name and Domain/Workgroup

# Set computer name (triggers restart)
Rename-Computer -NewName 'SRV-PROD01' -Force -Restart

# After restart — join domain
$cred = Get-Credential 'CONTOSOAdministrator'
Add-Computer -DomainName 'contoso.local' -Credential $cred -Restart

# Or join workgroup
Add-Computer -WorkgroupName 'WORKGROUP'

# Verify
$env:COMPUTERNAME
(Get-WmiObject Win32_ComputerSystem).Domain

Network Configuration

# List available network adapters
Get-NetAdapter | Select-Object Name,InterfaceDescription,Status,MacAddress

# Set static IP on the first active adapter
$adapter = (Get-NetAdapter | Where-Object {$_.Status -eq 'Up'})[0].Name
New-NetIPAddress -InterfaceAlias $adapter -IPAddress '10.0.1.50' `
    -PrefixLength 24 -DefaultGateway '10.0.1.1'
Set-DnsClientServerAddress -InterfaceAlias $adapter `
    -ServerAddresses '10.0.1.10','10.0.1.11'

# Disable IPv6 if not needed
Disable-NetAdapterBinding -Name $adapter -ComponentID ms_tcpip6

# Verify
Get-NetIPConfiguration -InterfaceAlias $adapter

Time Zone and Regional Settings

# List available time zones
Get-TimeZone -ListAvailable | Where-Object {$_.Id -like '*UTC*'}

# Set time zone
Set-TimeZone -Id 'UTC'

# Sync time with domain controller or NTP server
w32tm /config /manualpeerlist:"time.windows.com" /syncfromflags:manual /reliable:YES /update
Restart-Service w32tm
w32tm /resync /force
w32tm /query /status

Windows Firewall Configuration

# Enable all firewall profiles
Set-NetFirewallProfile -Profile Domain,Private,Public -Enabled True

# Set default inbound policy to Block
Set-NetFirewallProfile -Profile Domain,Private,Public -DefaultInboundAction Block

# Enable Remote Desktop
Enable-NetFirewallRule -DisplayGroup 'Remote Desktop'
Set-ItemProperty -Path 'HKLM:SystemCurrentControlSetControlTerminal Server' `
    -Name 'fDenyTSConnections' -Value 0

# Allow ICMP ping (useful for troubleshooting)
New-NetFirewallRule -DisplayName 'Allow ICMPv4 Echo' -Protocol ICMPv4 `
    -IcmpType 8 -Direction Inbound -Action Allow

PowerShell Remoting and WinRM

# Enable PSRemoting (sets WinRM to auto-start, creates listeners)
Enable-PSRemoting -Force

# Configure WinRM HTTPS listener for secure remoting
$cert = New-SelfSignedCertificate -DnsName $env:COMPUTERNAME `
    -CertStoreLocation Cert:LocalMachineMy
New-WSManInstance winrm/config/listener `
    -SelectorSet @{Address='*'; Transport='HTTPS'} `
    -ValueSet @{CertificateThumbprint=$cert.Thumbprint; Enabled='true'}

# Set WinRM max envelope and memory
Set-Item WSMan:localhostShellMaxMemoryPerShellMB 1024
Set-Item WSMan:localhostMaxEnvelopeSizekb 500

Configuring Windows Update via PowerShell

# Configure automatic update settings via registry
$wuPath = 'HKLM:SOFTWAREPoliciesMicrosoftWindowsWindowsUpdateAU'
New-Item -Path $wuPath -Force | Out-Null
Set-ItemProperty -Path $wuPath -Name 'NoAutoUpdate' -Value 0
Set-ItemProperty -Path $wuPath -Name 'AUOptions' -Value 4   # Auto download and install
Set-ItemProperty -Path $wuPath -Name 'ScheduledInstallDay' -Value 0   # Every day
Set-ItemProperty -Path $wuPath -Name 'ScheduledInstallTime' -Value 3  # 3 AM

# Check pending updates
(New-Object -ComObject Microsoft.Update.Session).CreateUpdateSearcher().Search('IsInstalled=0').Updates | 
    Select-Object Title,MsrcSeverity

Setting Up PowerShell Profile and Logging

# Create PowerShell profile
if (-not (Test-Path $PROFILE)) {
    New-Item -Path $PROFILE -ItemType File -Force | Out-Null
}
Add-Content $PROFILE @'
# Set window title to show server name
$Host.UI.RawUI.WindowTitle = "PS @ $env:COMPUTERNAME"
# Custom prompt showing current path
function prompt { "PS [$env:COMPUTERNAME] $($ExecutionContext.SessionState.Path.CurrentLocation)> " }
'@

# Enable script block logging (PowerShell 4.0 DSC feature)
$logPath = 'HKLM:SOFTWAREPoliciesMicrosoftWindowsPowerShellScriptBlockLogging'
New-Item -Path $logPath -Force | Out-Null
Set-ItemProperty -Path $logPath -Name EnableScriptBlockLogging -Value 1

Summary

PowerShell 4.0 on Windows Server 2012 R2 provides all the tools needed for complete initial server configuration: network setup, domain join, time synchronisation, firewall configuration, WinRM setup, and update management. Using PowerShell for initial configuration creates documentation-quality records of exactly what was configured and enables you to reproduce the same setup across multiple servers with a single script.