Updated powerCLI function for setting HA Admission control policy in percent with number of hosts

I got the question from a colleague if i could add a parameter in my function, no problem, just some dividing..

So you can either set percent CPU/Memory or number of hosts and from that get a percent on the policy. I have not taken care of the case if you have more than 100 hosts in your cluster (as this is not possible, at least not yet 😉 )

function Set-HAAdmissionControlPolicy{
<#
.SYNOPSIS
Set the Percentage HA Admission Control Policy
 
.DESCRIPTION
Percentage of cluster resources reserved as failover spare capacity
 
.PARAMETER  Cluster
The Cluster object that is going to be configurered 

.PARAMETER numberHosts
When this parameter is set the percentage is set based on number of hosts in cluster
 
.PARAMETER percentCPU
The percent reservation of CPU Cluster resources
 
.PARAMETER percentMem
The percent reservation of Memory Cluster resources
 
.EXAMPLE
PS C:\> Set-HAAdmissionControlPolicy -Cluster $CL -percentCPU 50 -percentMem 50
 
.EXAMPLE
PS C:\> Get-Cluster | Set-HAAdmissionControlPolicy -percentCPU 50 -percentMem 50

.EXAMPLE
PS C:\> Set-HAAdmissionControlPolicy -Cluster $CL -numberHosts 5
 
.NOTES
Author: Niklas Akerlund / RTS
Date: 2012-01-25
#>
   param (
   [Parameter(Position=0,Mandatory=$true,HelpMessage="This need to be a clusterobject",
    ValueFromPipeline=$True)]
    $Cluster,
	[int]$numberHosts = 0,
    [int]$percentCPU = 25,
    [int]$percentMem = 25
    )
 
    if(Get-Cluster $Cluster){
 
        $spec = New-Object VMware.Vim.ClusterConfigSpecEx
        $spec.dasConfig = New-Object VMware.Vim.ClusterDasConfigInfo
        $spec.dasConfig.admissionControlPolicy = New-Object VMware.Vim.ClusterFailoverResourcesAdmissionControlPolicy
		if($numberHosts -eq 0){
        	$spec.dasConfig.admissionControlPolicy.cpuFailoverResourcesPercent = $percentCPU
        	$spec.dasConfig.admissionControlPolicy.memoryFailoverResourcesPercent = $percentMem
 		}else{
			$spec.dasConfig.admissionControlPolicy.cpuFailoverResourcesPercent = 100/$numberHosts
        	$spec.dasConfig.admissionControlPolicy.memoryFailoverResourcesPercent = 100/$numberHosts
		}
        $Cluster = Get-View $Cluster
        $Cluster.ReconfigureComputeResource_Task($spec, $true)
    }
}

powerCLI function to set HA Admission Control Policy in percent

I am attending a VMware vSphere ICM 5 course this week, this because I am planning to become a VCI.

As I am a bit of PowerCLI fan i am trying to do all the labs in the course from the powerCLI console 🙂

In the HA laboration i found that the default implementation of the powerCLI does not allow you to set the HA Admission Control Policy Percentage, only the Host failure the cluster tolerates, here is a link to the powerCLI reference page for Set-Cluster. In the slides VMware recommends that you set percentage in a HA setup.

This led me to develop a powerCLI function that can configure this. The function has a default value for CPU and Memory that is 25 %, so if you only give the Cluster parameter the Capacity setting will be 25 %.

function Set-HAAdmissionControlPolicy{
<#
.SYNOPSIS
Set the Percentage HA Admission Control Policy

.DESCRIPTION
Percentage of cluster resources reserved as failover spare capacity

.PARAMETER  Cluster
The Cluster object that is going to be configurered 

.PARAMETER percentCPU
The percent reservation of CPU Cluster resources

.PARAMETER percentMem
The percent reservation of Memory Cluster resources

.EXAMPLE
PS C:\> Set-HAAdmissionControlPolicy -Cluster $CL -percentCPU 50 -percentMem 50

.EXAMPLE
PS C:\> Get-Cluster | Set-HAAdmissionControlPolicy -percentCPU 50 -percentMem 50

.NOTES
Author: Niklas Akerlund / RTS
Date: 2012-01-19
#>
   param (
   [Parameter(Position=0,Mandatory=$true,HelpMessage="This need to be a clusterobject",
    ValueFromPipeline=$True)]
    $Cluster,
    [int]$percentCPU = 25,
    [int]$percentMem = 25
    )
    
    if(Get-Cluster $Cluster){
    
        $spec = New-Object VMware.Vim.ClusterConfigSpecEx
        $spec.dasConfig = New-Object VMware.Vim.ClusterDasConfigInfo
        $spec.dasConfig.admissionControlPolicy = New-Object VMware.Vim.ClusterFailoverResourcesAdmissionControlPolicy
        $spec.dasConfig.admissionControlPolicy.cpuFailoverResourcesPercent = $percentCPU
        $spec.dasConfig.admissionControlPolicy.memoryFailoverResourcesPercent = $percentMem
    
        $Cluster = Get-View $Cluster
        $Cluster.ReconfigureComputeResource_Task($spec, $true)
    }
}

Here is a screenshot when running the function

Updated->Schedule PowerShell script in windows 2003 to clean any files

I have set up an scheduled task in a windows 2003 that run a PowerShell script, this script runs every week and the purpose is to clean out logs from IIS that otherwise fills the volume.

I used the script from Thomas Maurer to check a folder for files to delete and have customized it after excellent input from Jeffery Hicks, he suggested that i put in parameters instead to make the script more flexible and that way it can be run on any folder in the server with -Path and also set number of days to save -DaysBack, the last parameter has a default value of 30 days:

# Delete all Files in specifed parameter Path 
# and parameter older than 30 day(s) default or
# set by parameter DaysBack
#
# Parameter delyxe Niklas Akerlund / RTS
param(
	[Parameter(Mandatory=$true)][ValidateNotNullOrEmpty()]$Path,
	$DaysBack = 30)

$CurrentDate = Get-Date
$DatetoDelete = $CurrentDate.AddDays(-$Daysback) 

if($Path -ne ""){
	Get-ChildItem $Path | Where-Object { $_.LastWriteTime -lt $DatetoDelete } | Remove-Item
}

I saved it in C:\Scripts\Clean and you must set the execution policy in PowerShell console otherwise you will not be able to run any scripts,

Set-ExecutionPolicy -ExecutionPolicy Remotesigned

then i created the scheduled task, some screen shots follows with the way to set up this, first selesct PowerShell

then select interval that the script is going to be run

I have selected that the script is going to be executed every week at mondays 9 AM

Then set an account and password and click next, the magic comes when going into the advanced properties

As you can see i have added a -File C:\Scripts\Clean\clean.ps1 -Path “C:\windows\system32\LogFiles\W3SVC1” -DaysBack 20 to the PowerShell.exe in the run field, otherwise i will not run any scripts 😉 only the powershell, the -File was also a suggestion from Jeffery Hicks 🙂

C:\Windows\system32\WindowsPowerShell\v1.0\powershell.exe -File c:\Scripts\Clean\clean.ps1 -Path "C:\windows\system32\LogFiles\W3SVC1" -DaysBack 20

Quite simple but so powerful to not have to manually clean folders with logfiles that grows.

If you do not have PowerShell on your windows 2003 you have to install the Windows Management Framework first: kb968929

This script can also of course be run on xp, win7 and win 2008/2008 R2.

Populate and administer Active directory users with Powershell

Some days ago I have been working on some powershell scripts for a lab environment and now i have edited the handlescript to work better and with more functionality.

First i created a small script for populating some OU with student accounts.

# Script: Createusers.ps1
# Create users in AD
# Version: 0.1
# Niklas Akerlund /RTS

Import-Module Activedirectory

$OUs =  "OU1","OU2","OU3","OU4","OU5","OU6"

foreach ($OU in $OUs){
	$path = "OU=" + $OU + ",OU=lab,OU=Users,DC=demo,DC=local"
	for ($i=1;$i -le 10;$i++){
    	$SAMid = $OU + "Student0" + $i 
    	$Name = $OU + "Student0" + $i 
    	New-ADUser -SamAccountName $SAMid -Name $Name -AccountPassword (ConvertTo-SecureString -AsPlainText "S0meP@ssw0rd" -Force) -Enabled $true -Path $path
   
	}
}

 

Then i created with help from Jeffery Hicks post a script with a menu to enable or disable accounts in the different OU´s. As i described in a earlier post it is quite powerful to use Active Directory cmdlets and i have tried to take care of that by checking that when i enable/disable accounts i check that i really have something in my searchbase. Below are two screenshots of the script running. Update I have now updated the script with a check for the searchbase that actually works and also an extra menu option with the ability to set password on the accounts i enable!

 

Here is the script that creates this, i have not yet come up with a better and more dynamic way to create the switch, maybe someone can give me some help there..

# Script: handleusers.ps1
# Version: 0.1
# Disable or enable lab account users
# 
# Niklas Akerlund / RTS
# Menu code from Jeffery Hicks 

Import-Module ActiveDirectory
 
Function Show-Menu {

	Param(
		[Parameter(Position=0,Mandatory=$True,HelpMessage="Enter your menu text")]
		[ValidateNotNullOrEmpty()]
		[string]$Menu,
		[Parameter(Position=1)]
		[ValidateNotNullOrEmpty()]
		[string]$Title="Menu",
		[switch]$ClearScreen
	)

	if ($ClearScreen) {Clear-Host}

	#build the menu prompt
	$menuPrompt=$title
	#add a return
	$menuprompt+="<code>n"
	#add an underline
	$menuprompt+="-"*$title.Length
	$menuprompt+="</code>n"
	#add the menu
	$menuPrompt+=$menu

	Read-Host -Prompt $menuprompt

} #end function

$menu="<code>n"
$ListOU = Get-ADOrganizationalUnit -filter * -Searchbase "OU=lab,OU=Users,DC=demo,DC=local" | where {$_.Name -ne "lab"} | Sort-Object $_.Name

$i = 1
foreach ($OU in $ListOU){
	   $menu+= [string]$i + " " + $OU.Name + "</code>n"
      # write-host $menu
       $i = $i+1
     
}
$menu+= "Q Quit"
$menu+= "<code>n"

# Menu 2 
$menu2=@"
1 Disable accounts
2 Enable accounts
3 Set password and enable accounts
B Back to menu
"@
$menu2+= "</code>n"

#Keep looping and running the menu until the user selects Q (or q).
Do {
    #use a Switch construct to take action depending on what menu choice
    #is selected.
    Switch (Show-Menu $menu "Get OU to handle" -clear ) {
     "1" {
	 		if ($ListOU[0].DistinguishedName -ne $null){
		 		$menutext = "Handle " + $ListOU[0].Name + " users to disable/enable "
				$Users = Get-ADUser -filter * -searchbase $ListOU[0].DistinguishedName
		 		Switch (Show-Menu $menu2 $menutext -clear ) {
	     		"1" {
		 					$Users |  Set-ADUser -Enabled $false	
	         		} 
	     		"2" {
		 					$Users |  Set-ADUser -Enabled $true	
	          		}
	     		"3" {
							$newPassword = (Read-Host -Prompt "Provide New Password" -AsSecureString)
		 					$Users | Set-ADUser -Enabled $true	
							$Users | Set-ADAccountPassword -NewPassword $newPassword -Reset
	          		}
				"B" {
						Write-Host "Back to menu" -ForegroundColor Cyan
	        		}
				Default {Write-Warning "Invalid Choice. Try again."
	              sleep -milliseconds 750}
	         	}
			}
		 }
     "2"  {
	 		if ($ListOU[1].DistinguishedName -ne $null){
		 		$menutext = "Handle " + $ListOU[1].Name + " users to disable/enable " 
				$Users = Get-ADUser -filter * -searchbase $ListOU[1].DistinguishedName
		 		Switch (Show-Menu $menu2 $menutext -clear ) {
	     		"1" {
		 				
		 					$Users |  Set-ADUser -Enabled $false	
						
	         		} 
	     		"2" {
		 					$Users |  Set-ADUser -Enabled $true	
	          		}
				"3" {
							$newPassword = (Read-Host -Prompt "Provide New Password" -AsSecureString)
		 					$Users | Set-ADUser -Enabled $true	
							$Users | Set-ADAccountPassword -NewPassword $newPassword -Reset
	          		}
				"B" {
						Write-Host "Back to menu" -ForegroundColor Cyan
	        		}
				Default {Write-Warning "Invalid Choice. Try again."
	              sleep -milliseconds 750}
	         	} 
			}
		 }
     "3" {
	 		if ($ListOU[2].DistinguishedName -ne $null){
		 		$menutext = "Handle " + $ListOU[2].Name + " users to disable/enable " 
				$Users = Get-ADUser -filter * -searchbase $ListOU[2].DistinguishedName
		 		Switch (Show-Menu $menu2 $menutext -clear ) {
	     		"1" {
		 					$Users |  Set-ADUser -Enabled $false		
	         		} 
	     		"2" {
		 					$Users |  Set-ADUser -Enabled $true	
	          		}
				"3" {
							$newPassword = (Read-Host -Prompt "Provide New Password" -AsSecureString)
		 					$Users | Set-ADUser -Enabled $true	
							$Users | Set-ADAccountPassword -NewPassword $newPassword -Reset
	          		}
				"B" {
						Write-Host "Back to menu" -ForegroundColor Cyan
	        		}
				Default {Write-Warning "Invalid Choice. Try again."
	              sleep -milliseconds 750}
	         	} 
			}
		 }
	 "4" {
	 		if ($ListOU[3].DistinguishedName -ne $null){
		 		$menutext = "Handle " + $ListOU[3].Name + " users to disable/enable " 
				$Users = Get-ADUser -filter * -searchbase $ListOU[3].DistinguishedName
		 		Switch (Show-Menu $menu2 $menutext -clear ) {
	     		"1" {
		 					$Users |  Set-ADUser -Enabled $false		
	         		} 
	     		"2" {
		 					$Users |  Set-ADUser -Enabled $true	
	          		}
				"3" {
							$newPassword = (Read-Host -Prompt "Provide New Password" -AsSecureString)
		 					$Users | Set-ADUser -Enabled $true	
							$Users | Set-ADAccountPassword -NewPassword $newPassword -Reset
	          		}
				"B" {
						Write-Host "Back to menu" -ForegroundColor Cyan
	        		}
				Default {Write-Warning "Invalid Choice. Try again."
	              sleep -milliseconds 750}
	         	} 
			}
		 }
	 "5" {
	 		if ($ListOU[4].DistinguishedName -ne $null){
		 		$menutext = "Handle " + $ListOU[4].Name + " users to disable/enable " 
				$Users = Get-ADUser -filter * -searchbase $ListOU[4].DistinguishedName
		 		Switch (Show-Menu $menu2 $menutext -clear ) {
	     		"1" {
		 					$Users |  Set-ADUser -Enabled $false		
	         		} 
	     		"2" {
		 					$Users |  Set-ADUser -Enabled $true	
	          		}
				"3" {
							$newPassword = (Read-Host -Prompt "Provide New Password" -AsSecureString)
		 					$Users | Set-ADUser -Enabled $true	
							$Users | Set-ADAccountPassword -NewPassword $newPassword -Reset
	          		}
				"B" {
						Write-Host "Back to menu" -ForegroundColor Cyan
	        		}
				Default {Write-Warning "Invalid Choice. Try again."
	              sleep -milliseconds 750}
	         	} 
			}
		 }
	 "6" {
	 		if ($ListOU[5].DistinguishedName -ne $null){
		 		$menutext = "Handle " + $ListOU[5].Name + " users to disable/enable " 
				$Users = Get-ADUser -filter * -searchbase $ListOU[5].DistinguishedNam
		 		Switch (Show-Menu $menu2 $menutext -clear ) {
	     		"1" {
		 					$Users |  Set-ADUser -Enabled $false	
						
	         		} 
	     		"2" {
		 					$Users |  Set-ADUser -Enabled $true	
	          		}
				"3" {
							$newPassword = (Read-Host -Prompt "Provide New Password" -AsSecureString)
		 					$Users | Set-ADUser -Enabled $true	
							$Users | Set-ADAccountPassword -NewPassword $newPassword -Reset
					}          	
				"B" {
						Write-Host "Back to menu" -ForegroundColor Cyan
	        		}
				Default {Write-Warning "Invalid Choice. Try again."
	              sleep -milliseconds 750}
	         	} 
			}
		 }
     "Q" {Write-Host "Goodbye" -ForegroundColor Cyan
         Return
         }
     Default {Write-Warning "Invalid Choice. Try again."
              sleep -milliseconds 750}
    } #switch
} While ($True)