Rebooting a Citrix Server
2013, Jan 25
Rebooting a Citrix Server, restarting using the default scheme in Citrix wasn’t cutting it. So I created a script for it.
#
# $Author: Berry $
# $Rev: 1.4 $
#
# Version control:
#
# 1.0 Initial version in powershell scripting
# 1.1 Changed the log rotate to 90 days, added the print spooler task kill
# 1.2 20-11-2012 Added Function GetCurrentDateTime to proper logfile entry creation
# 1.3 03-01-2013 Completely restructured and re-written
# 1.4 23-06-2013 Added Function SetMachineConfigRights and set email alert to: alert@bogus.tld
#
# Functions definitions
#
Function LogAction
{
Param([string]$a)
[string]$LogDate = Get-Date -format “dd-MM-yyyy HH:mm:ss.ms”
Add-Content -path $LogFileName -value “$LogDate – $a”
}
Function LogRotate
{
param([int]$a)
# Check for logfiles older than <$a> days
LogAction “—————————————————-”
LogAction “Starting to rotate log files”
[int]$DaysToKeep = $a
$CompareDate = (Get-Date).AddDays(-$DaysToKeep)
Get-ChildItem $LogFolder\*$LogFile | Where-Object {$_.LastWriteTime -lt $CompareDate} | Remove-Item
LogAction ” Finished to rotating log files”
}
Function LogOffCitrixUsers
{
Add-PSSnapin Citrix* -ErrorAction SilentlyContinue
[array]$CheckActiveSessions = Get-XASession -ServerName $CitrixServer | where {$_.Protocol -match “ICA” -and $_.AccountName -match “$UserDomain”}
If ($CheckActiveSessions.length -gt 0){
do {
[array]$ActiveSessions = Get-XASession -ServerName $CitrixServer | where {$_.Protocol -match “ICA” -and $_.AccountName -match “$Userdomain”}
for ($i=0; $i -lt $ActiveSessions.length ; $i++)
{
LogAction “Attempting to log off”
LogAction $ActiveSessions[$i].AccountName
LogAction $ActiveSessions[$i].SessionId
LogOff $ActiveSessions[$i].SessionId
LogAction “Sleeping for 8192 milliseconds.”
Start-Sleep -Milliseconds 8192
}
} while ($ActiveSessions.Count -gt 0 )
}
else
{
LogAction “No active user sessions found.”
}
}
Function ApplyPatchesAndReboot
{
Param([string]$a)
[string]$EmailAddress = $a
[string]$StartExe = “c:\windows\syswow64\ApplyPatchesAndreboot.exe”
[string]$StartExeArgs = “/noreboot /mailonfail:$EmailAddress”
LogAction “Starting to apply patches”
start-process $StartExe $StartExeArgs -Wait
LogAction ” Finished applying Patches”
}
Function SetMachineConfigRights
{
LogAction “Starting SetMachineConfigRights”
$FindMachineConfig = get-childitem -path C:\Windows\Microsoft.NET -Recurse -Filter “Machine.Config”
$FindMachineConfig = $FindMachineConfig.Fullname
For ($i=0; $i -lt $FindMachineConfig.length ; $i++)
{
LogAction ” Setting ACL for “$FindMachineConfig[$i]
icacls $FindMachineConfig[$i] /grant “Domain Users:(M)”
}
LogAction ” Finished SetMachineConfigRights”
}
Function RemoveSpoolFiles
{
LogAction “Cleaning obsolete files from the spooler directory”
$SpoolFolder = Get-ItemProperty HKLM:\SYSTEM\CurrentControlSet\Control\Print\Printers | select “DefaultSpoolDirectory”
[int]$SpoolFileCount = 0
Get-ChildItem -Path $SpoolFolder.DefaultSpoolDirectory | ForEach-Object {$SpoolFileCount++}
If ($SpoolFileCount -gt 0)
{
LogAction ” Removing $SpoolFileCount spool files”
Get-ChildItem $SpoolFolder.DefaultSpoolDirectory | foreach ($_) {remove-item $_.fullname}
}
Else
{
LogAction ” No obsolete spool files found”
}
}
Function KillService {
Param([string]$a, [string]$b) # the two parameters.
[string]$ServiceName = $a
[string]$ServiceDescription = $b
[int]$n = 3 # second to wait
LogAction “Attempting to abort $b”
If (Get-Process $ServiceName -ErrorAction SilentlyContinue)
{
Stop-Process -processname $ServiceName -Force
Start-Sleep -Seconds $n
If (Get-Process $ServiceName -ErrorAction SilentlyContinue)
{
LogAction ” ***** FAILED *****”
}
Else
{
LogAction ” $ServiceDescription abortion confirmed”
}
}
Else
{
LogAction ” * $ServiceDescription not running *”
}
Function StartService {
Param([string]$a) # Service description.
[string]$ServiceDescription =$a
[int]$n = 3 # second to wait
LogAction “Starting $a after $n seconds”
Start-Sleep -Seconds $n
Start-Service $a
Get-Service “Print Spooler” | ForEach-Object {
if ($_.status -eq “running”)
{LogAction ” Service – $a – running”}
else
{
LogAction ” ***** Service -$a- not running *****”
}
}
}
Function RebootServer {
LogAction ” ***** Initiating Reboot *****”
. c:\s4\Framework\Core\S4-Preload.ps1;S4-PreLoad;S4\Invoke-Systemreboot
LogAction ” ***** Reboot intiated *****”
}
###
###
### Start of Main Routine
###
###
################## PREREQUISITES ##################
################## PREREQUISITES ##################
################## PREREQUISITES ##################
[string]$SystemDrive = Get-Content ENV:SystemDrive
[string]$SystemRoot = Get-Content ENV:SystemRoot
[string]$CitrixServer = Get-Content ENV:COMPUTERNAME
[string]$UserDomain = Get-Content ENV:USERDOMAIN
[string]$LogFolder = $SystemDrive+”\Logs\”
[string]$LogFile = “_Reboot_log.txt”
[string]$LogFileDate = get-date -format “dd-MM-yyyy”
[string]$LogFileName = $LogFolder + $LogFileDate + $LogFile
### Do house keeping on the logfiles by rotating over $DaysToKeep
LogRotate 90 #DaysToKeep
### User log off
LogOffCitrixUsers
### Killing the Citrix Print Manager
KillService cpsvc “Citrix Print Manager Service”
### Kill Microsoft Print Spooler Service
KillService spoolsv “Print Spooler”
### Cleaning up the obsolote spool files from the spooler directory
RemoveSpoolFiles
### Starting Microsoft Print Spooler Service
StartService “Print Spooler”
### Starting Citrix Print Manager Service
StartService “Citrix Print Manager Service”
### Start process Apply Patches (without reboot!)
### email the results on failure to address mentioned in first argument
alert@bogus.tld
### Change the ACL for the MACHINE.CONFIG files in the various Microsoft .NET folders
SetMachineConfigRights
### Starting Citrix Print Manager Service
RebootServer
###
###
### End of Main Routine
###
###