From c3e89a5cc11dd02ae46a039fb0531740b2904904 Mon Sep 17 00:00:00 2001 From: VictoriousRaptor <10308169+VictoriousRaptor@users.noreply.github.com> Date: Tue, 30 Dec 2025 00:31:11 +0800 Subject: [PATCH] Implement file type filter for windows index --- .../Search/WindowsIndex/QueryConstructor.cs | 48 ++++++++++++++++++- .../WindowsIndex/WindowsIndexSearchManager.cs | 6 +-- 2 files changed, 49 insertions(+), 5 deletions(-) diff --git a/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/QueryConstructor.cs b/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/QueryConstructor.cs index 1d160983a..702741590 100644 --- a/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/QueryConstructor.cs +++ b/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/QueryConstructor.cs @@ -1,4 +1,6 @@ using System; +using System.Collections.Generic; +using System.Linq; using System.Text.RegularExpressions; using Microsoft.Search.Interop; @@ -74,7 +76,7 @@ namespace Flow.Launcher.Plugin.Explorer.Search.WindowsIndex /// /// Search will be performed on all folders and files based on user's search keywords. /// - public string FilesAndFolders(ReadOnlySpan userSearchString) + public string FilesAndFolders(ReadOnlySpan userSearchString, IEnumerable allowedResultTypes = null) { if (userSearchString.IsWhiteSpace()) userSearchString = "*"; @@ -82,8 +84,50 @@ namespace Flow.Launcher.Plugin.Explorer.Search.WindowsIndex // Remove any special characters that might cause issues with the query var replacedSearchString = ReplaceSpecialCharacterWithTwoSideWhiteSpace(userSearchString); + // Build the type filter constraint + var typeFilterConstraint = BuildTypeFilterConstraint(allowedResultTypes); + // Generate SQL from constructed parameters, converting the userSearchString from AQS->WHERE clause - return $"{CreateBaseQuery().GenerateSQLFromUserQuery(replacedSearchString)} AND {RestrictionsForAllFilesAndFoldersSearch} ORDER BY {OrderIdentifier}"; + var baseQuery = $"{CreateBaseQuery().GenerateSQLFromUserQuery(replacedSearchString)} AND {RestrictionsForAllFilesAndFoldersSearch}"; + + // Append type filter if present + if (!string.IsNullOrEmpty(typeFilterConstraint)) + baseQuery += $" AND {typeFilterConstraint}"; + + return $"{baseQuery} ORDER BY {OrderIdentifier}"; + } + + /// + /// Build WHERE clause constraint to filter by result types (File, Folder, Volume). + /// + /// + /// System.ItemType values: + /// - ".directory" for folders + /// - Specific file extensions (e.g., ".txt", ".pdf") for files + /// - Drive volumes are identified by their path structure + /// + private static string BuildTypeFilterConstraint(IEnumerable allowedResultTypes) + { + if (allowedResultTypes == null) + return null; + + var typesList = allowedResultTypes as IList ?? allowedResultTypes.ToList(); + + // No filtering needed if empty or all types are allowed + // TODO: what if more types are added in the future? + if (typesList.Count == 0 || typesList.Count == 3) + return null; + + var hasFile = typesList.Contains(ResultType.File); + var hasFolder = typesList.Contains(ResultType.Folder) || typesList.Contains(ResultType.Volume); // Folder and volume are merged in Folder action keyword so treat them as same + + if (hasFolder) + return "System.ItemType = '.directory'"; + + if (hasFile) + return "System.ItemType <> '.directory'"; + + return null; } /// diff --git a/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/WindowsIndexSearchManager.cs b/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/WindowsIndexSearchManager.cs index 0201fa3b7..98207275e 100644 --- a/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/WindowsIndexSearchManager.cs +++ b/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/WindowsIndexSearchManager.cs @@ -45,13 +45,14 @@ namespace Flow.Launcher.Plugin.Explorer.Search.WindowsIndex private IAsyncEnumerable WindowsIndexFilesAndFoldersSearchAsync( ReadOnlySpan querySearchString, + IEnumerable allowedResultTypes = null, CancellationToken token = default) { try { return WindowsIndex.WindowsIndexSearchAsync( QueryConstructor.CreateQueryHelper().ConnectionString, - QueryConstructor.FilesAndFolders(querySearchString), + QueryConstructor.FilesAndFolders(querySearchString, allowedResultTypes), token); } catch (COMException) @@ -85,8 +86,7 @@ namespace Flow.Launcher.Plugin.Explorer.Search.WindowsIndex public IAsyncEnumerable SearchAsync(string search, CancellationToken token, IEnumerable allowedResultTypes = null) { - // TODO: result type filter - return WindowsIndexFilesAndFoldersSearchAsync(search, token: token); + return WindowsIndexFilesAndFoldersSearchAsync(search, allowedResultTypes, token); } public IAsyncEnumerable ContentSearchAsync(string plainSearch, string contentSearch, CancellationToken token)