Public/Search-History.ps1
|
function Search-History { <# .SYNOPSIS Search saved-point history for a specific text. .DESCRIPTION Search-History finds every saved point in the active project that added or removed the text you give it. Useful for forensic questions like "when did the connection string change?" or "when was that function name dropped?" By default, Search-History returns structured objects (one per matching saved point), so you can pipe and filter. With -Patch, it includes the actual change text alongside each result. .PARAMETER Pattern The text to search for in the saved-point history. Plain text, not a regular expression. .PARAMETER Count The maximum number of matching saved points to return. Defaults to 50. Validated to the range 1-500. .PARAMETER Patch Include the change text (the lines that were added or removed) for each matching saved point. .EXAMPLE Search-History -Pattern 'DROP TABLE' .EXAMPLE Search-History -Pattern 'connection string' -Count 10 .EXAMPLE Search-History -Pattern 'old-function-name' -Patch .NOTES Search-History looks at every saved point in history, not just recent ones, so it can be slow on very large projects. Use -Count to limit how many results to return. .LINK Show-History .LINK Find-CodeChange .LINK Save-Work #> [CmdletBinding()] [OutputType([System.Object[]])] param( [Parameter(Mandatory, Position = 0)] [string]$Pattern, [ValidateRange(1, 500)] [int]$Count = 50, [switch]$Patch ) $root = Get-GERepoRoot $delim = '<<<GE-SEARCH-DELIM>>>' # Local list named to avoid shadowing the $args automatic variable. $logArgs = @('log', "-S$Pattern", "--max-count=$Count", '--date=short', "--pretty=format:$delim%h%x09%ad%x09%an%x09%s") if ($Patch) { $logArgs += '--patch' } $r = Invoke-GEGit -ArgumentList $logArgs -WorkingDirectory $root -AllowFailure if ($r.ExitCode -ne 0) { return @() } $output = ($r.Output -join "`n") $chunks = $output -split [regex]::Escape($delim) $results = New-Object System.Collections.Generic.List[object] foreach ($chunk in $chunks) { if ([string]::IsNullOrWhiteSpace($chunk)) { continue } $lines = @($chunk -split "`n") $headerLine = $lines[0] $parts = @($headerLine -split "`t", 4) if ($parts.Count -lt 4) { continue } $entry = [PSCustomObject]@{ Repository = $root Id = $parts[0].Trim() Date = $parts[1].Trim() Author = $parts[2].Trim() Message = $parts[3].Trim() } if ($Patch -and $lines.Count -gt 1) { $patchText = ($lines[1..($lines.Count - 1)] -join "`n").Trim() Add-Member -InputObject $entry -NotePropertyName 'Change' -NotePropertyValue $patchText } $results.Add($entry) } return $results.ToArray() } |