tests/TestHelpers.psm1
|
<#
.SYNOPSIS Test helpers and utilities for HermesConsoleUI testing .DESCRIPTION Provides mock objects, assertion helpers and utilities for testing HermesConsoleUI components in isolation. #> #region Mock Console <# .SYNOPSIS Creates a mock console object for testing #> function New-MockConsole { [CmdletBinding()] param( [int]$Width = 120, [int]$Height = 30 ) return [PSCustomObject]@{ Output = [System.Collections.ArrayList]::new() Width = $Width Height = $Height CursorLeft = 0 CursorTop = 0 } } <# .SYNOPSIS Captures console output for testing #> function Start-OutputCapture { $script:CapturedOutput = [System.Collections.ArrayList]::new() $script:OriginalWriteHost = Get-Command Write-Host } function Stop-OutputCapture { return $script:CapturedOutput } function Get-CapturedOutput { return $script:CapturedOutput -join "`n" } #endregion #region ANSI Helpers <# .SYNOPSIS Validates ANSI escape codes in output #> function Assert-ANSIOutput { [CmdletBinding()] param( [Parameter(Mandatory)] [string]$Output, [Parameter(Mandatory)] [string]$ExpectedCode ) if ($Output -notmatch [regex]::Escape($ExpectedCode)) { throw "Expected ANSI code '$ExpectedCode' not found in output" } return $true } <# .SYNOPSIS Strips ANSI codes from text for comparison #> function Remove-ANSICodes { [CmdletBinding()] param( [Parameter(Mandatory, ValueFromPipeline)] [string]$Text ) process { return $Text -replace '\x1b\[[0-9;]*[a-zA-Z]', '' } } <# .SYNOPSIS Gets ANSI color code for a color name #> function Get-ANSIColorCode { [CmdletBinding()] param( [Parameter(Mandatory)] [ValidateSet('Black', 'Red', 'Green', 'Yellow', 'Blue', 'Magenta', 'Cyan', 'White')] [string]$Color, [switch]$Background ) $codes = @{ 'Black' = if ($Background) { 40 } else { 30 } 'Red' = if ($Background) { 41 } else { 31 } 'Green' = if ($Background) { 42 } else { 32 } 'Yellow' = if ($Background) { 43 } else { 33 } 'Blue' = if ($Background) { 44 } else { 34 } 'Magenta' = if ($Background) { 45 } else { 35 } 'Cyan' = if ($Background) { 46 } else { 36 } 'White' = if ($Background) { 47 } else { 37 } } return "`e[$($codes[$Color])m" } #endregion #region Test Data Generators <# .SYNOPSIS Generates test data for table rendering #> function New-TestTableData { [CmdletBinding()] param( [int]$RowCount = 10, [int]$ColumnCount = 3 ) $data = @() for ($i = 1; $i -le $RowCount; $i++) { $row = @{} for ($j = 1; $j -le $ColumnCount; $j++) { $row["Column$j"] = "Value_${i}_${j}" } $data += [PSCustomObject]$row } return $data } <# .SYNOPSIS Generates long string for edge case testing #> function New-LongString { [CmdletBinding()] param( [int]$Length = 1000, [char]$Character = 'A' ) return $Character.ToString() * $Length } <# .SYNOPSIS Generates string with special characters #> function New-SpecialCharString { return "Test`n`r`t`0Special" } #endregion #region Assertion Helpers <# .SYNOPSIS Asserts that output contains expected text (ignoring ANSI codes) #> function Assert-OutputContains { [CmdletBinding()] param( [Parameter(Mandatory)] [string]$Output, [Parameter(Mandatory)] [string]$Expected ) $cleanOutput = Remove-ANSICodes -Text $Output if ($cleanOutput -notmatch [regex]::Escape($Expected)) { throw "Expected text '$Expected' not found in output" } return $true } <# .SYNOPSIS Asserts that a scriptblock completes within time limit #> function Assert-CompletesWithin { [CmdletBinding()] param( [Parameter(Mandatory)] [scriptblock]$ScriptBlock, [Parameter(Mandatory)] [int]$Milliseconds ) $elapsed = Measure-Command { & $ScriptBlock } if ($elapsed.TotalMilliseconds -gt $Milliseconds) { throw "Script took $($elapsed.TotalMilliseconds)ms, expected <$Milliseconds ms" } return $true } #endregion #region Module Import Helper <# .SYNOPSIS Imports HermesConsoleUI module for testing #> function Import-HermesForTesting { [CmdletBinding()] param() $modulePath = Join-Path $PSScriptRoot ".." "HermesConsoleUI.psd1" if (-not (Test-Path $modulePath)) { throw "Module not found at: $modulePath" } Import-Module $modulePath -Force -Global } #endregion # Export functions Export-ModuleMember -Function @( 'New-MockConsole', 'Start-OutputCapture', 'Stop-OutputCapture', 'Get-CapturedOutput', 'Assert-ANSIOutput', 'Remove-ANSICodes', 'Get-ANSIColorCode', 'New-TestTableData', 'New-LongString', 'New-SpecialCharString', 'Assert-OutputContains', 'Assert-CompletesWithin', 'Import-HermesForTesting' ) |