Put PowerShell scripts to sleep with Progress Bar

Cover

All of you know very well the embedded PowerShell cmdlet Start-Sleep, which able to put a script to the sleep for a certain period measured in seconds or milliseconds. This is great, but not enough.

Start-SleepProgress

  • The Start-SleepProgress function from my PowerShell MS-Module module has some enhancements compared to the usual Start-Sleep cmdlet.
Import-Module MS-Module
Get-Command -Module MS-Module
Get-Alias -Definition Start-SleepProgress
  • First of all a sleep period visualized by Write-Progress cmdlet. In addition to the progress, you will see elapsed and left time.

01.Start-SleepProgress_Second

  • The sleep period may be specified either in seconds (-Second/-s), minutes (-Minute/-m) or hours (-Hour/-h). The milliseconds are out of scope Emoj.

  • The minutes and hours can be decimal values. The –Minute 1.5 is the same as –Second 90.

  • The maximum sleep period is twenty-four hours. Not enough?

Start-SleepProgress –s 90
Start-SleepProgress –m 1.5

02.Start-SleepProgress_Minute

  • Sleep for one hour and fifteen minutes. The 0.25 from 60 min is 15 min Emoj.
Start-SleepProgress –h 1.25
Start-SleepProgress –m 75

03.Start-SleepProgress_Hour

  • The default units are seconds.
Start-SleepProgress –s 10
Start-SleepProgress 10

04.Start-SleepProgress_Default

-Until parameter

  • The more interesting parameter is –Until.

  • This parameter allows specifying a point in time (timestamp) and Start-SleepProgress will sleep until that time. Cool?

Start-SleepProgress –u 17:00
Start-SleepProgress -Until '1:30:45 PM'
  • All what can be considered as [datetime] value are suitable for -Until parameter.
[datetime]'1:30 PM'
[datetime]’bullshit’

05.Start-SleepProgress_Until

  • If the timestamp, specified by -Until is less (earlier) than your current time (returned by Get-Date), it is possible to specify –Force parameter to shift the timestamp to tomorrow.
Start-SleepProgress -Until (Get-Date).AddHours(-1)
Start-SleepProgress -Until (Get-Date).AddHours(-1) -Force

06.Start-SleepProgress_Force

–ScriptBlock parameter

  • For those of you, who will execute the Start-SleepProgress interactively in the PowerShell console, but not within scripts, there is –ScriptBlock parameter.

  • The piece of code specified here –ScriptBlock { } will be executed right after the sleep will have finished.

  • This example is a «proof of concept» only with no much sense.

07.Start-SleepProgress_ScriptBlockPOC

There are many use cases for this functionality. Generally, this is PowerShell based task scheduler! Let me show you some examples.

  • Get snapshot of running services at the designated time.
Start-SleepProgress -Until '8:00PM' -ScriptBlock {Get-Service | ? {$_.Status -eq 'running'} | epcsv -notype .\Svc.csv}

08.Start-SleepProgress_ScriptBlockExample1

  • Schedule file system monitoring. This one-liner will execute hundred times 1..100 | % every ten seconds Start-SleepProgress -s 10 the script block that returns the last modified temp file -match ‘\.tmp$’ within Windows temp directory, usually C:\WINDOWS\Temp.
1..100 | % {Start-SleepProgress -s 10 -ScriptBlock {dir "$env:windir\Temp" | sort LastWriteTime -desc | ? {$_.Name -match '\.tmp$'} | select –f 1}}

09.Start-SleepProgress_ScriptBlockExample2

Start-SleepProgress for VMware Admins

  • Especially for VMware Admins, VI operations. Schedule VM(s) restart at midnight.
Start-SleepProgress -Until 0:00AM -Force -ScriptBlock {Get-VM VM01 | Restart-VMGuest -Confirm:$false}

10.Start-SleepProgress_ScriptBlockExample3

  • Schedule VM snapshot operations tonight.
Start-SleepProgress -Until 2:00AM -Force -ScriptBlock {Get-VM VM01, VM02 | Get-Snapshot | Remove-Snapshot -RunAsync -Confirm:$false}

11.Start-SleepProgress_ScriptBlockExample4

  • As you can see, your imagination is a limit. You are able to schedule anything now.

Precision of Start-SleepProgress

  • Few words about the precision of the time calculation.

  • Every second the function goes to sleep for 980 milliseconds (Start-Sleep -Milliseconds 980) and not for one second (Start-Sleep –Seconds 1)! Why? The answer is to keep maximum possible accuracy.

  • I measured and found that all the code within For( ) { } loop takes on average 20 milliseconds.

12.Start-SleepProgress_Measure

13.Start-SleepProgress_Average20ms

  • The above screenshot show you function executions for 15 minutes sleep period. As you can see, the deviation is less than one percent (about 0.8-0.9%)! For the NASA, it may not be acceptable, but for IT purposes, it is good enough Emoj.

  • Try it yourself, only change the $testtimemin variable to your liking.

$testtimemin = 15   ### the test duration (min)
$start = Get-Date -f 'HH:mm:ss'; $end = Start-SleepProgress -m $testtimemin -ScriptBlock { Get-Date -f 'HH:mm:ss' }
Write-Host "$start - $end" -ForegroundColor Yellow
[math]::Round(((New-TimeSpan -Start $start -End $end).TotalSeconds/$testtimemin/60*100), 3)-100
  • The result will be deviation measured in percent.

14.Start-SleepProgress_Precision

  • The good news. While using the –Until parameter, the precision is absolute (100%).

  • For more details about the function, please take a look at the content based help and examples.

Get-Alias -Definition Start-SleepProgress
Get-Help Start-SleepProgress -Full
Get-Help Start-SleepProgress -Examples
Get-Help Start-SleepProgress -Parameter until

You may also like:

New-PercentageBar – Create colored and adjustable Percentage Bar in the PowerShell
Write-Menu – Create interactive dynamic Menu in PowerShell

2 thoughts on “Put PowerShell scripts to sleep with Progress Bar

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s