This project has moved. For the latest updates, please go here.

IQueryableSearch

Jul 4, 2016 at 4:54 PM
Hello,

Your work looks great and i wish to use IQueryableSearch in a project but i have a problem :
I'm french (that's not my problem) and in my language we use "accents" : é, è, ê, ù, etc.
Google, for example, don't take care of it : a "é" is interpreted like a normal "e".
To illustrate, if i search a word like "prométhée" it gives "promethee" or "prométhée" or any combination with accents.
The opposite is true as well : "promethee" gives "prométhée", etc.

But IQueryableSearch seems to search the exact word in columns.
Could you help me?

Sorry for my english,
Julien
Coordinator
Jul 5, 2016 at 9:28 PM
You would need do go in and add some fuzzy search logic as e does not equal é. You could do this in many ways as simple as "alike" sets or some other method. I don't have the resources right now to add in something like this, but it shouldn't be too hard, good luck!
Jul 7, 2016 at 8:59 AM
Hello,

Thanks for your response.
In fact, that's not as easy as it seems : i use Linq with entity and it changes some parameters.

First of all, i've found this method to remove diacritics (accents) without a dictionnary of characters :
(it extends the String type to add this method)
public static string RemoveDiacritics(this string text)
{
    var normalizedString = text.Normalize(NormalizationForm.FormD);
    var stringBuilder = new StringBuilder();

    foreach (var c in normalizedString)
    {
        var unicodeCategory = CharUnicodeInfo.GetUnicodeCategory(c);
        if (unicodeCategory != UnicodeCategory.NonSpacingMark)
        {
            stringBuilder.Append(c);
        }
    }

    return stringBuilder.ToString().Normalize(NormalizationForm.FormC);
}
1st attempt : IQueryableSearch native and extension of entity generated class
My first though was to extend the object class generated by entity to add a "search" property.
I code the "get" accessor to concat all the porperties i want to search in (with a blank space) and lower the characters and remove diacritics.
And then, i call your search method with this "search" property in the string array[] "properties_to_search" and a keywords string array with lowered characters and diacritics removed.

But it doesn't work.
Linq with entity request work only on properties who came from the database, not the added ones.

2nd attempt : Modify your code
At this point, i download your code to change it.
I added the "RemoveDiacritics" method in your StringConversions class as it fit well there.
And then i added the call of this method there :
public static IQueryable Search(this IQueryable list_to_search, Dictionary<string, Type> properties_to_search, object[] keywords, StringSearchType string_search_type)
(...)
if (column.Value == typeof(string))
                            where_expression += column.Key + ".RemoveDiacritics()." + (string_search_type == StringSearchType.Equals ? "Equals" : "Contains") + "(@0) || ";
(...)
But it doesn't work too.
In fact, Linq transform queries to SQL and it cannot do this for my custom method.
For information, it stops exactly here :
        private static IQueryable SearchInitial(this IQueryable list_to_search, string where_expression, object keyword)
        {
*           return list_to_search.Where(where_expression, keyword);
        }
With this values :
where_expression : "TITRE.RemoveDiacritics().Contains(@0) || PROBLEME.RemoveDiacritics().Contains(@0)"
keyword : "param" (my research keyword)
and this error : {"No applicable method 'RemoveDiacritics' exists in type 'String'"} (source : System.Linq.Dynamic)

3rd attempt : Keep it simple
Here i'm am.
Now i want to make it simple.
Then my plan is to add in the database a column dedicated to research.
With a trigger on update i will fill this column with a concateced string of my scope of research without diacritics and lowered characters (coded in PL/SQL in my case).
Then i could use your dll without any modification.
I'm confident (but i was confident too before ;)


This is a long post, but maybe it could helps someone.
Or maybe i'm wrong and you could have an idea to make things differently.

Thank you anyway,
Julien.