From 5b344fb53cad6fee62612680aebff55907fb3aed Mon Sep 17 00:00:00 2001 From: Jack251970 <1160210343@qq.com> Date: Mon, 9 Dec 2024 13:23:28 +0800 Subject: [PATCH] Improve windows index search with special character --- .../Search/WindowsIndex/QueryConstructor.cs | 37 ++++++++++++++++++- 1 file changed, 36 insertions(+), 1 deletion(-) diff --git a/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/QueryConstructor.cs b/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/QueryConstructor.cs index a35bad274d3..9e3707fbeab 100644 --- a/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/QueryConstructor.cs +++ b/Plugins/Flow.Launcher.Plugin.Explorer/Search/WindowsIndex/QueryConstructor.cs @@ -1,10 +1,14 @@ using System; +using System.Text.RegularExpressions; using Microsoft.Search.Interop; namespace Flow.Launcher.Plugin.Explorer.Search.WindowsIndex { public class QueryConstructor { + private static Regex _specialCharacterMatcher = new(@"[\@\@\#\#\&\&*_;,\%\|\!\(\)\{\}\[\]\^\~\?\\""\/\:\=\-]+", RegexOptions.Compiled); + private static Regex _multiWhiteSpacesMatcher = new(@"\s+", RegexOptions.Compiled); + private Settings settings { get; } private const string SystemIndex = "SystemIndex"; @@ -76,8 +80,39 @@ public string FilesAndFolders(ReadOnlySpan userSearchString) if (userSearchString.IsWhiteSpace()) userSearchString = "*"; + // Remove any special characters that might cause issues with the query + var replacedSearchString = ReplaceSpecialCharacterWithTwoSideWhiteSpace(userSearchString); + // Generate SQL from constructed parameters, converting the userSearchString from AQS->WHERE clause - return $"{CreateBaseQuery().GenerateSQLFromUserQuery(userSearchString.ToString())} AND {RestrictionsForAllFilesAndFoldersSearch} ORDER BY {FileName}"; + return $"{CreateBaseQuery().GenerateSQLFromUserQuery(replacedSearchString)} AND {RestrictionsForAllFilesAndFoldersSearch} ORDER BY {FileName}"; + } + + /// + /// If one special character have white space on one side, replace it with one white space. + /// So command will not have "[special character]+*" which will cause OLEDB exception. + /// + private static string ReplaceSpecialCharacterWithTwoSideWhiteSpace(ReadOnlySpan input) + { + const string whiteSpace = " "; + + var inputString = input.ToString(); + + // Use regex to match special characters with whitespace on one side + // and replace them with a single space + var result = _specialCharacterMatcher.Replace(inputString, match => + { + // Check if the match has whitespace on one side + bool hasLeadingWhitespace = match.Index > 0 && char.IsWhiteSpace(inputString[match.Index - 1]); + bool hasTrailingWhitespace = match.Index + match.Length < inputString.Length && char.IsWhiteSpace(inputString[match.Index + match.Length]); + if (hasLeadingWhitespace || hasTrailingWhitespace) + { + return whiteSpace; + } + return match.Value; + }); + + // Remove any extra spaces that might have been introduced + return _multiWhiteSpacesMatcher.Replace(result, whiteSpace).Trim(); } ///