Files
winutil/pester/search-filter.Tests.ps1
T
Malin FossumandChris Titus b8b81edcdb Show preset JSON key in app, tweak, and feature tooltips (#4995)
* Add Get-WinUtilEntryToolTip helper for preset-key tooltips

* Show preset JSON key in app and tweak tooltips

* Match apps search against preset key for consistency with tweaks

* Limit preset-key tooltips to preset-representable controls

Comboboxes and package-manager radio buttons cannot appear in a preset
file. Update-WinUtilSelections routes a flat list of keys by the
WPFInstall/WPFTweaks/WPFToggle/WPFFeature/WPFAppx prefixes, so a preset
can carry neither a combobox selected value nor a radio group choice;
WingetRadioButton and ChocoRadioButton do not even carry a WPF prefix.
Advertising those control names as preset keys invited users to add keys
that fall through the switch and abort the whole import.

Revert the combobox label and radio button tooltips to the plain
description, and add tests that fail if the key is reattached to a
control the preset importer cannot accept.

* fix: address preset key review feedback

* docs: clarify preset key search scope

---------

Co-authored-by: Chris Titus <contact@christitus.com>
2026-08-19 16:26:11 -05:00

556 lines
21 KiB
PowerShell

#===========================================================================
# Tests - Search and Filter Helpers
#===========================================================================
BeforeAll {
$script:repoRoot = (Resolve-Path (Join-Path $PSScriptRoot "..")).Path
if (-not ("Windows.Visibility" -as [type])) {
Add-Type @"
namespace Windows
{
public enum Visibility
{
Visible,
Collapsed
}
}
"@
}
if (-not ("System.Windows.Controls.CheckBox" -as [type])) {
Add-Type @"
namespace System.Windows.Controls
{
public class CheckBox
{
public bool? IsChecked { get; set; }
}
public class Label
{
public object Content { get; set; }
}
public class WrapPanel
{
public object Visibility { get; set; }
}
public class StackPanel
{
public System.Collections.ArrayList Children { get; private set; }
public StackPanel()
{
Children = new System.Collections.ArrayList();
}
}
}
"@
}
if (-not ("Windows.Controls.Border" -as [type])) {
Add-Type @"
namespace Windows.Controls
{
public class Border
{
public object Child { get; set; }
public object Visibility { get; set; }
}
public class DockPanel
{
public System.Collections.ArrayList Children { get; private set; }
public object Visibility { get; set; }
public DockPanel()
{
Children = new System.Collections.ArrayList();
}
}
public class StackPanel
{
public System.Collections.ArrayList Children { get; private set; }
public object Visibility { get; set; }
public StackPanel()
{
Children = new System.Collections.ArrayList();
}
}
public class ItemsControl
{
public System.Collections.ArrayList Items { get; private set; }
public object Visibility { get; set; }
public ItemsControl()
{
Items = new System.Collections.ArrayList();
}
}
public class Label
{
public object Content { get; set; }
public object ToolTip { get; set; }
public object Visibility { get; set; }
}
public class CheckBox
{
public object Content { get; set; }
public object ToolTip { get; set; }
public object Visibility { get; set; }
}
}
"@
}
. (Join-Path $script:repoRoot "functions\private\Find-AppsByNameOrDescription.ps1")
. (Join-Path $script:repoRoot "functions\private\Find-TweaksByNameOrDescription.ps1")
function script:New-WinUtilSearchCollection {
return ,[System.Collections.ArrayList]::new()
}
function script:New-WinUtilAppSearchItem {
param([string]$Tag)
[pscustomobject]@{
Tag = $Tag
Visibility = [Windows.Visibility]::Visible
}
}
function script:New-WinUtilAppCategory {
param(
[string]$Label,
[object[]]$Items
)
$labelControl = [pscustomobject]@{
Content = $Label
Visibility = [Windows.Visibility]::Visible
}
$wrapPanel = [pscustomobject]@{
Children = New-WinUtilSearchCollection
Visibility = [Windows.Visibility]::Visible
}
foreach ($item in $Items) {
$null = $wrapPanel.Children.Add($item)
}
$children = New-WinUtilSearchCollection
$null = $children.Add($labelControl)
$null = $children.Add($wrapPanel)
[pscustomobject]@{
Children = $children
Visibility = [Windows.Visibility]::Visible
}
}
function script:New-WinUtilAppSearchContext {
param([object[]]$Categories)
$items = New-WinUtilSearchCollection
foreach ($category in $Categories) {
$null = $items.Add($category)
}
$script:sync = [Hashtable]::Synchronized(@{
ItemsControl = [pscustomobject]@{
Items = $items
}
configs = @{
applicationsHashtable = @{
WPFInstallBrowser = [pscustomobject]@{
Content = "Firefox"
Description = "Fast private browser"
Category = "Browsers"
}
WPFInstallMedia = [pscustomobject]@{
Content = "VLC"
Description = "Media player"
Category = "Multimedia Tools"
}
WPFInstallLiteral = [pscustomobject]@{
Content = "Tool [abc]"
Description = "Literal wildcard sample"
Category = "Utilities"
}
WPFInstallEditor = [pscustomobject]@{
Content = "Code Editor"
Description = "Text editing"
Category = "Development"
}
WPFInstallPowerToys = [pscustomobject]@{
Content = "PowerToys"
Description = "A collection of system utilities"
Category = "Microsoft Tools"
}
}
}
})
$global:sync = $script:sync
}
function script:New-WinUtilFakeSearchForm {
param(
$TweaksPanel,
$AppxPanel
)
$form = [pscustomobject]@{
tweakspanel = $TweaksPanel
appxpanel = $AppxPanel
}
$form | Add-Member -MemberType ScriptMethod -Name FindName -Value {
param($name)
return $this.$name
}
$form
}
function script:New-WinUtilTweakLabelItem {
param(
[string]$Content,
[string]$ToolTip = ""
)
$item = [Windows.Controls.DockPanel]::new()
$checkbox = [Windows.Controls.CheckBox]::new()
$label = [Windows.Controls.Label]::new()
$label.Content = $Content
$label.ToolTip = $ToolTip
$null = $item.Children.Add($checkbox)
$null = $item.Children.Add($label)
$item.Visibility = [Windows.Visibility]::Visible
$item
}
function script:New-WinUtilTweakCheckboxItem {
param(
[string]$Content,
[string]$ToolTip = ""
)
$item = [Windows.Controls.StackPanel]::new()
$checkbox = [Windows.Controls.CheckBox]::new()
$checkbox.Content = $Content
$checkbox.ToolTip = $ToolTip
$null = $item.Children.Add($checkbox)
$item.Visibility = [Windows.Visibility]::Visible
$item
}
function script:New-WinUtilTweakCategory {
param(
[string]$Label,
[object[]]$Items
)
$categoryLabel = [Windows.Controls.Label]::new()
$categoryLabel.Content = $Label
$categoryLabel.Visibility = [Windows.Visibility]::Visible
$itemsControl = [Windows.Controls.ItemsControl]::new()
$null = $itemsControl.Items.Add($categoryLabel)
foreach ($item in $Items) {
$null = $itemsControl.Items.Add($item)
}
$dockPanel = [Windows.Controls.DockPanel]::new()
$null = $dockPanel.Children.Add($itemsControl)
$border = [Windows.Controls.Border]::new()
$border.Child = $dockPanel
$border.Visibility = [Windows.Visibility]::Visible
[pscustomobject]@{
Border = $border
Label = $categoryLabel
ItemsControl = $itemsControl
}
}
function script:New-WinUtilTweakPanel {
param([object[]]$Categories)
$panel = [pscustomobject]@{
Children = New-WinUtilSearchCollection
}
foreach ($category in $Categories) {
$null = $panel.Children.Add($category.Border)
}
$panel
}
function script:New-WinUtilTweakSearchContext {
param(
$TweaksPanel,
$AppxPanel = $null,
[string]$CurrentTab = "Tweaks"
)
$script:sync = [Hashtable]::Synchronized(@{
currentTab = $CurrentTab
Form = New-WinUtilFakeSearchForm -TweaksPanel $TweaksPanel -AppxPanel $AppxPanel
})
$global:sync = $script:sync
}
function script:Remove-WinUtilSearchGlobals {
Remove-Variable -Name sync -Scope Global -ErrorAction SilentlyContinue
}
}
Describe "Find-AppsByNameOrDescription" {
AfterEach {
Remove-WinUtilSearchGlobals
}
It "restores app visibility and respects collapsed category state for empty search" {
$browserItem = New-WinUtilAppSearchItem -Tag "WPFInstallBrowser"
$mediaItem = New-WinUtilAppSearchItem -Tag "WPFInstallMedia"
$browserItem.Visibility = [Windows.Visibility]::Collapsed
$mediaItem.Visibility = [Windows.Visibility]::Collapsed
$collapsedCategory = New-WinUtilAppCategory -Label "+ Browsers" -Items @($browserItem)
$expandedCategory = New-WinUtilAppCategory -Label "- Media" -Items @($mediaItem)
$collapsedCategory.Children[1].Visibility = [Windows.Visibility]::Collapsed
$expandedCategory.Children[1].Visibility = [Windows.Visibility]::Collapsed
New-WinUtilAppSearchContext -Categories @($collapsedCategory, $expandedCategory)
Find-AppsByNameOrDescription -SearchString ""
$collapsedCategory.Visibility | Should -Be ([Windows.Visibility]::Visible)
$collapsedCategory.Children[0].Visibility | Should -Be ([Windows.Visibility]::Visible)
$collapsedCategory.Children[1].Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$browserItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$expandedCategory.Children[1].Visibility | Should -Be ([Windows.Visibility]::Visible)
$mediaItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
}
It "shows matching apps by description and hides categories without matches" {
$browserItem = New-WinUtilAppSearchItem -Tag "WPFInstallBrowser"
$mediaItem = New-WinUtilAppSearchItem -Tag "WPFInstallMedia"
$editorItem = New-WinUtilAppSearchItem -Tag "WPFInstallEditor"
$browserCategory = New-WinUtilAppCategory -Label "+ Browsers" -Items @($browserItem, $mediaItem)
$editorCategory = New-WinUtilAppCategory -Label "- Editors" -Items @($editorItem)
New-WinUtilAppSearchContext -Categories @($browserCategory, $editorCategory)
Find-AppsByNameOrDescription -SearchString "private"
$browserCategory.Visibility | Should -Be ([Windows.Visibility]::Visible)
$browserCategory.Children[0].Content | Should -Be "- Browsers"
$browserCategory.Children[1].Visibility | Should -Be ([Windows.Visibility]::Visible)
$browserItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$mediaItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$editorCategory.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$editorItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
}
It "matches apps by preset key" {
$browserItem = New-WinUtilAppSearchItem -Tag "WPFInstallBrowser"
$mediaItem = New-WinUtilAppSearchItem -Tag "WPFInstallMedia"
$category = New-WinUtilAppCategory -Label "- Browsers" -Items @($browserItem, $mediaItem)
New-WinUtilAppSearchContext -Categories @($category)
Find-AppsByNameOrDescription -SearchString "WPFInstallBrowser"
$browserItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$mediaItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$category.Visibility | Should -Be ([Windows.Visibility]::Visible)
}
It "treats wildcard characters as literal app search text" {
$literalItem = New-WinUtilAppSearchItem -Tag "WPFInstallLiteral"
$mediaItem = New-WinUtilAppSearchItem -Tag "WPFInstallMedia"
$category = New-WinUtilAppCategory -Label "- Tools" -Items @($literalItem, $mediaItem)
New-WinUtilAppSearchContext -Categories @($category)
Find-AppsByNameOrDescription -SearchString "[abc]"
$literalItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$mediaItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$category.Visibility | Should -Be ([Windows.Visibility]::Visible)
}
It "filters category chips by exact application category" {
$utilityItem = New-WinUtilAppSearchItem -Tag "WPFInstallLiteral"
$powerToysItem = New-WinUtilAppSearchItem -Tag "WPFInstallPowerToys"
$category = New-WinUtilAppCategory -Label "- Tools" -Items @($utilityItem, $powerToysItem)
New-WinUtilAppSearchContext -Categories @($category)
Find-AppsByNameOrDescription -Categories @("Utilities")
$utilityItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$powerToysItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$category.Visibility | Should -Be ([Windows.Visibility]::Visible)
}
It "shows apps from every selected category when several chips are active" {
$utilityItem = New-WinUtilAppSearchItem -Tag "WPFInstallLiteral"
$powerToysItem = New-WinUtilAppSearchItem -Tag "WPFInstallPowerToys"
$browserItem = New-WinUtilAppSearchItem -Tag "WPFInstallBrowser"
$category = New-WinUtilAppCategory -Label "- Tools" -Items @($utilityItem, $powerToysItem, $browserItem)
New-WinUtilAppSearchContext -Categories @($category)
Find-AppsByNameOrDescription -Categories @("Utilities", "Microsoft Tools")
$utilityItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$powerToysItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$browserItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
}
It "applies the search text and the category filter together" {
$powerToysItem = New-WinUtilAppSearchItem -Tag "WPFInstallPowerToys"
$literalItem = New-WinUtilAppSearchItem -Tag "WPFInstallLiteral"
$category = New-WinUtilAppCategory -Label "- Tools" -Items @($powerToysItem, $literalItem)
New-WinUtilAppSearchContext -Categories @($category)
Find-AppsByNameOrDescription -SearchString "PowerToys" -Categories @("Microsoft Tools")
$powerToysItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$literalItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
}
It "hides a category when the search text matches nothing inside the selected categories" {
$powerToysItem = New-WinUtilAppSearchItem -Tag "WPFInstallPowerToys"
$category = New-WinUtilAppCategory -Label "- Tools" -Items @($powerToysItem)
New-WinUtilAppSearchContext -Categories @($category)
Find-AppsByNameOrDescription -SearchString "Firefox" -Categories @("Microsoft Tools")
$powerToysItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$category.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
}
It "expands a collapsed category that has matches for the selected filter" {
$powerToysItem = New-WinUtilAppSearchItem -Tag "WPFInstallPowerToys"
$category = New-WinUtilAppCategory -Label "+ Tools" -Items @($powerToysItem)
New-WinUtilAppSearchContext -Categories @($category)
Find-AppsByNameOrDescription -Categories @("Microsoft Tools")
$category.Children[0].Content | Should -Be "- Tools"
$category.Children[1].Visibility | Should -Be ([Windows.Visibility]::Visible)
}
It "re-collapses a category it expanded once the filter is cleared" {
$powerToysItem = New-WinUtilAppSearchItem -Tag "WPFInstallPowerToys"
$category = New-WinUtilAppCategory -Label "+ Tools" -Items @($powerToysItem)
New-WinUtilAppSearchContext -Categories @($category)
Find-AppsByNameOrDescription -Categories @("Microsoft Tools")
$category.Children[0].Content | Should -Be "- Tools"
Find-AppsByNameOrDescription -SearchString ""
$category.Children[0].Content | Should -Be "+ Tools"
$category.Children[1].Visibility | Should -Be ([Windows.Visibility]::Collapsed)
}
It "leaves a category the user had expanded alone when the filter is cleared" {
$powerToysItem = New-WinUtilAppSearchItem -Tag "WPFInstallPowerToys"
$category = New-WinUtilAppCategory -Label "- Tools" -Items @($powerToysItem)
New-WinUtilAppSearchContext -Categories @($category)
Find-AppsByNameOrDescription -Categories @("Microsoft Tools")
Find-AppsByNameOrDescription -SearchString ""
$category.Children[0].Content | Should -Be "- Tools"
$category.Children[1].Visibility | Should -Be ([Windows.Visibility]::Visible)
}
}
Describe "Find-TweaksByNameOrDescription" {
AfterEach {
Remove-WinUtilSearchGlobals
}
It "restores category labels and tweak item visibility for empty search" {
$labelItem = New-WinUtilTweakLabelItem -Content "Disable Telemetry" -ToolTip "Stop tracking"
$stackItem = New-WinUtilTweakCheckboxItem -Content "Show Extensions" -ToolTip "File extension display"
$category = New-WinUtilTweakCategory -Label "+ Privacy" -Items @($labelItem, $stackItem)
$labelItem.Visibility = [Windows.Visibility]::Collapsed
$stackItem.Visibility = [Windows.Visibility]::Collapsed
$category.Label.Visibility = [Windows.Visibility]::Collapsed
$category.Border.Visibility = [Windows.Visibility]::Collapsed
$panel = New-WinUtilTweakPanel -Categories @($category)
New-WinUtilTweakSearchContext -TweaksPanel $panel
Find-TweaksByNameOrDescription -SearchString ""
$category.Border.Visibility | Should -Be ([Windows.Visibility]::Visible)
$category.Label.Visibility | Should -Be ([Windows.Visibility]::Visible)
$labelItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$stackItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
}
It "shows tweak matches by label tooltip and checkbox content" {
$telemetryItem = New-WinUtilTweakLabelItem -Content "Disable Telemetry" -ToolTip "Stop tracking"
$extensionsItem = New-WinUtilTweakCheckboxItem -Content "Show Extensions" -ToolTip "File extension display"
$nonMatchItem = New-WinUtilTweakLabelItem -Content "Enable NumLock" -ToolTip "Keyboard setting"
$category = New-WinUtilTweakCategory -Label "+ Privacy" -Items @($telemetryItem, $extensionsItem, $nonMatchItem)
$panel = New-WinUtilTweakPanel -Categories @($category)
New-WinUtilTweakSearchContext -TweaksPanel $panel
Find-TweaksByNameOrDescription -SearchString "tracking"
$category.Border.Visibility | Should -Be ([Windows.Visibility]::Visible)
$category.Label.Visibility | Should -Be ([Windows.Visibility]::Visible)
$category.Label.Content | Should -Be "- Privacy"
$telemetryItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$extensionsItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$nonMatchItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
Find-TweaksByNameOrDescription -SearchString "Show Extensions"
$telemetryItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$extensionsItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$nonMatchItem.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
}
It "hides tweak category panels when no items match" {
$item = New-WinUtilTweakLabelItem -Content "Disable Telemetry" -ToolTip "Stop tracking"
$category = New-WinUtilTweakCategory -Label "- Privacy" -Items @($item)
$panel = New-WinUtilTweakPanel -Categories @($category)
New-WinUtilTweakSearchContext -TweaksPanel $panel
Find-TweaksByNameOrDescription -SearchString "not-present"
$category.Border.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$category.Label.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
$item.Visibility | Should -Be ([Windows.Visibility]::Collapsed)
}
It "searches the AppX panel when AppX is the current tab" {
$tweakItem = New-WinUtilTweakLabelItem -Content "Disable Telemetry" -ToolTip "Stop tracking"
$appxItem = New-WinUtilTweakCheckboxItem -Content "Xbox Overlay" -ToolTip "Gaming overlay package"
$tweakCategory = New-WinUtilTweakCategory -Label "- Privacy" -Items @($tweakItem)
$appxCategory = New-WinUtilTweakCategory -Label "+ AppX" -Items @($appxItem)
$tweakPanel = New-WinUtilTweakPanel -Categories @($tweakCategory)
$appxPanel = New-WinUtilTweakPanel -Categories @($appxCategory)
New-WinUtilTweakSearchContext -TweaksPanel $tweakPanel -AppxPanel $appxPanel -CurrentTab "AppX"
Find-TweaksByNameOrDescription -SearchString "overlay"
$appxCategory.Border.Visibility | Should -Be ([Windows.Visibility]::Visible)
$appxCategory.Label.Content | Should -Be "- AppX"
$appxItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
$tweakCategory.Border.Visibility | Should -Be ([Windows.Visibility]::Visible)
$tweakItem.Visibility | Should -Be ([Windows.Visibility]::Visible)
}
}