Tag Archives: Validation

Friday Fun: Get Day of the Year with PowerShell

calendarEarlier this week I was having some fun with @EnergizedTech on Twitter, playing around with dates in PowerShell. I’m not even sure where we started but the experience got me thinking and it’s Friday so let’s have some fun.

While I can easily find out what the day of the year is for a given date:

there’s no method to convert an integer to a day of the year. But it really isn’t that hard. Here’s a simple function.

The stuff around the command is longer than the command itself. But I don’t mind. The function takes an integer value between 1 and 366, the most possible days in a year. You can also specify a year, but it defaults to the current year. The function then loops using a While loop which keeps adding one day to until the day of the year matches the target day of the year. I used a While loop because it is possible that the expression will be True immediately and there’s no need to process the scriptblock. Copy and paste the code and try for yourself!

UPDATE: I knew as soon as I posted that someone would show me a better way. And they did. I was clearly overthinking the problem. I’ve updated the code to show the smart way to do this. And now the solution is so short, you probably don’t even need the function.

Variable Validation

In PowerShell v3 there is a new feature you might not be aware of that could save you pain and headaches. This is something you could use in scripting as well as the console. In fact, I think using it in the console is an especially smart idea.

In PowerShell v2 scripts and functions we had the ability to add validation tags to parameters. These tags could perform different validation tests on a parameter value. If the value failed, the script or function would throw an exception. I’d rather have the command fail to start than to fail halfway through. Now in PowerShell v3 we can use these same tags on variables in our scripts and even the console. I’ve written about a number of these validation tags in the past on my blog. Here’s an example of what we can do in v3.


PS C:\> [validateRange(1,10)]$i=5

In this example I’ve added a validation test to verify that any value for $i is between 1 and 10. I can use the variable as I normally would. Even change the value.


PS C:\> $i*2
10
PS C:\> $i+=1
PS C:\> $i*2
12

But watch what happens when I try to use a value outside of the accepted range:


PS C:\> $i=30
The variable cannot be validated because the value 30 is not a valid value for the i variable.
At line:1 char:1
+ $i=30
+ ~~~~~
+ CategoryInfo : MetadataError: (:) [], ValidationMetadataException
+ FullyQualifiedErrorId : ValidateSetFailure

I get an exception. This is much better than setting a value that will cause another error later. The sooner you can detect potential problems the better.

Perhaps this example isn’t compelling. But there are other validation tests you might want to take advantage of. Maybe a regular expression pattern.


PS C:\> [validatepattern({\\\\\w+\\\w+})]$unc="\\server01\share"

If I later decide to change the value, the validation will help me catch typos.


PS C:\> $unc="\server02\data"
The variable cannot be validated because the value \server02\data is not a valid value for the unc variable.
At line:1 char:1
+ $unc="\server02\data"
+ ~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : MetadataError: (:) [], ValidationMetadataException
+ FullyQualifiedErrorId : ValidateSetFailure

The bottom line is that if your variable values will change, using a validation tag will ensure new values will work. If you don’t want to sift through the blog learning more about the validation tags, take a look at my Scripting Help module.

PowerShell Scripting with [ValidateNotNullorEmpty]

I’ve been writing about the different parameter validation attributes that you can use in your PowerShell scripting. One that I use in practically every script is [ValidateNotNullorEmpty()]. This validation will ensure that something is passed as a parameter value. I’m not talking about making a parameter mandatory; only that if the user decides to use the parameter that something is passed. Let’s look at my demo.


#requires -version 2.0

Param (
[Parameter(Position=0,Mandatory=$True,HelpMessage="Enter a process name like lsass")]
[ValidateNotNullorEmpty()]
[string]$Name,
[Parameter(Position=1)]
[ValidateNotNullorEmpty()]
[string]$Computername=$env:computername

)

Try {
Get-Process -Name $name -ComputerName $computername -errorAction "Stop" | Select *,
@{Name="Runtime";Expression={(Get-Date)-$_.StartTime}}
}

Catch {
Write-Warning $_.Exception.Message
}

I’ve used the attribute on both parameters. The first parameter I’ve also made mandatory which makes it more likely that something will be entered. But if not, then the script will fail.

I would get a similar message if the user forgot to complete the command.

Even though I’m using a default value for Computername, as soon as the parameter is detected PowerShell assumes I’m going to use a different value.

Validation should work for missing values, a variable that might be null, or in general anything that is meaningless. However, it won’t prevent something quirky like this:


PS S:\> $p=" "
PS S:\> .\demo-ValidateNotNull.ps1 -name $p
WARNING: Cannot find a process with the name " ". Verify the process name and
call the cmdlet again.

The variable, while semantically meaningless to us, is not null or empty but a string of 1 space. If there’s the chance you might run into this situation then you can add additional validation checks to the parameter.

If you’d like, feel free to download Demo-ValidateNotNull and see for yourself.