Skip to content

Instantly share code, notes, and snippets.

@crmckenzie
Last active August 18, 2017 23:01
Show Gist options
  • Save crmckenzie/6225a6f94771576363161a932b21dea1 to your computer and use it in GitHub Desktop.
Save crmckenzie/6225a6f94771576363161a932b21dea1 to your computer and use it in GitHub Desktop.
Pester-Watch
param([switch] $Start)
function New-FileSystemWatcher(
[Parameter(Mandatory)][ValidateNotNullOrEmpty()] [string] $TargetFile,
[Parameter(Mandatory)][ValidateNotNull()] [ScriptBlock] $Action
) {
$fullPath = Resolve-Path $TargetFile
$fsw= New-Object System.IO.FileSystemWatcher
$fsw.Path = (Split-Path $fullPath -Parent)
$fsw.Filter = (SPlit-Path $FullPath -Leaf)
$fsw.NotifyFilter = [IO.NotifyFilters]::LastWrite
Register-ObjectEvent -InputObject $fsw `
-EventName Changed `
-Action $Action | Out-Null
return $fsw
}
function Find-AssociatedTestFile (
[Alias("FullName")]
[Parameter(Mandatory, ValueFromPipeline, ValueFromPipelineByPropertyName)]
[ValidateNotNullOrEmpty()]
[string] $FullPath) {
$fileInfo = New-Object IO.FileInfo $FullPath
$TestFileName = "$($FileInfo.BaseName).Tests.ps1"
gci -path "./module/tests" -filter $TestFileName -recurse
}
function New-WatchList() {
gci -path "./Module/Functions" -filter *.ps1 -recurse `
| %{
return [PsCustomObject] @{
"SourceFile" = $_.FullName;
"TestFile" = ($_ | Find-AssociatedTestFile).FullName
}
} `
| ?{ $_.SourceFile -and $_.TestFile };
}
function Save-WatchList([Parameter(Mandatory)][ValidateNotNull()][array] $Array) {
[System.AppDomain]::Currentdomain.SetData("Posh-Watch:WatchList", $Array)
}
function Get-WatchList() {
[System.AppDomain]::Currentdomain.GetData("Posh-Watch:WatchList")
}
$OnSourceFileChanged = {
param($sender, $e)
#
# It is necessary to reproduce this function here as the parent closure will
# not be available during the event.
#
function Find-AssociatedTestFile (
[string] $FullPath) {
$fileInfo = New-Object IO.FileInfo $FullPath
$TestFileName = "$($FileInfo.BaseName).Tests.ps1"
gci -path "./module/tests" -filter $TestFileName -recurse
}
$TestFile = Find-AssociatedTestFIle -FullPath $e.FullPath
Invoke-Pester -Script $TestFile.FullName
}
$OnTestFileChanged = {
param($sender, $e)
Invoke-Pester -Script $e.FullPath
}
function Start-Watch() {
$watchers = @()
Save-WatchList (New-WatchList) | Out-Null
Get-WatchList | %{
$Watchers += New-FileSystemWatcher -TargetFile $_.SourceFile -Action $OnSourceFileChanged
$Watchers += New-FileSystemWatcher -TargetFile $_.TestFile -Action $OnTestFileChanged
}
write-host "Monitoring $($Watchers.Count) files..."
try {
while ($true) {
# infinite loop to wait
}
} finally {
write-host "Ending monitoring."
Get-EventSubscriber | Unregister-Event
}
}
if ($Start) {
Start-Watch
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment