Search with whitespace

78 views
Skip to first unread message

Nguyễn Huy

unread,
Jul 21, 2015, 2:17:38 AM7/21/15
to rav...@googlegroups.com
Hi all,

I have search class and query below . But it is not work with the whitespace: For example : when search with Product 1 it will display the result with all Product 2 , Product 3 .......

 public class Product_Search : AbstractIndexCreationTask<ProductModel, Product_Search.Result>
    {

        public class Result
        {
            public string Query;
            public ProductModel ProductModel;
        }

        public Product_Search()
            {
                Map = products => from product in products
                    select new
                    {
                        Query = new object[] { product.Name, product.Status, product.Att.Select(x => x.Name) },
                        product.ProductionDate
                       
                    };
                Index(x => x.Query, FieldIndexing.Analyzed);

            }
        }
    }

My Query

Session.Query<Product_Search.Result, Product_Search>().Search(x => x.Query, searchString.GetQueryProduct(searchString),
                    escapeQueryOptions: EscapeQueryOptions.AllowAllWildcards, options: SearchOptions.And).As<ProductModel>().ToList();

And function getQueryproduct :

  public static string GetQueryProduct(this string wildquery, string query)
        {
            if (query == null) query = "";
            return string.Format("*{0}*", QueryParser.Escape(query));
        }

Is anything to improve to search the exactly match the result ?

Oren Eini (Ayende Rahien)

unread,
Jul 21, 2015, 5:17:20 AM7/21/15
to ravendb
You explicitly asked to break apart the term to allow full text search on it when you asked for analyzed.

Hibernating Rhinos Ltd  

Oren Eini l CEO Mobile: + 972-52-548-6969

Office: +972-4-622-7811 l Fax: +972-153-4-622-7811

 


--
You received this message because you are subscribed to the Google Groups "RavenDB - 2nd generation document database" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ravendb+u...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Nguyễn Huy

unread,
Jul 21, 2015, 8:50:26 AM7/21/15
to rav...@googlegroups.com
Could you eleborate for me Oren?

--
You received this message because you are subscribed to a topic in the Google Groups "RavenDB - 2nd generation document database" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/ravendb/OVnVyNsndOs/unsubscribe.
To unsubscribe from this group and all its topics, send an email to ravendb+u...@googlegroups.com.

Oren Eini (Ayende Rahien)

unread,
Jul 21, 2015, 9:06:31 AM7/21/15
to ravendb

Nguyễn Huy

unread,
Jul 21, 2015, 9:14:10 AM7/21/15
to rav...@googlegroups.com
Hi ,

I try all with the analyzer but it still not worked .First I did not add    Index(x => x.Query, FieldIndexing.Analyzed) . So the query with the string :Product 1 .It is return 0 record when I add that    Index(x => x.Query, FieldIndexing.Analyzed); It display the lists as I mention in the first comment 

Nguyễn Huy

unread,
Jul 21, 2015, 9:58:05 PM7/21/15
to rav...@googlegroups.com
Hi all,

Can anyone help me ?

Kijana Woodard

unread,
Jul 21, 2015, 10:37:45 PM7/21/15
to rav...@googlegroups.com
Are you saying you are getting *more* results than you expect?

That's because the results are coming back ordered by lucene score.
You won't get *only* exact matches when doing analyzed [full text] searches. You'll get the "best match" [according to lucene and the employed analyzer] first and then lesser matches after.

Think about an ecommerce search. If I search for "bears", I might see
Bears in the Wild
Bear and Pear
Bear T-Shirt

If I wanted exactly "bears", I would use a plain Where == instead of Search.

Nguyễn Huy

unread,
Jul 21, 2015, 10:43:35 PM7/21/15
to rav...@googlegroups.com
It is clear now .it mean we do not any work around to search exactly match ?

Kijana Woodard

unread,
Jul 21, 2015, 11:40:21 PM7/21/15
to rav...@googlegroups.com
.Where(x => x.Name == "Product 1")

Nguyễn Huy

unread,
Jul 22, 2015, 1:01:01 AM7/22/15
to rav...@googlegroups.com
Hi ,
I try with the below query but it thrown exception . Can you help ?

 return Session.Query<Product_Search.Result, Product_Search>().Search(x => x.Query, searchString.GetQueryProduct(searchString),
                    escapeQueryOptions: EscapeQueryOptions.AllowAllWildcards, options: SearchOptions.And).As<ProductModel>()
                    .Where(x => x.ProductionDate >= fromDate && x.ProductionDate <= toDate && x.Name == searchString).ToList();

searchString has value but it got exception 

{"Url: \"/databases/CyberDyne/indexes/Product/Search?&query=%20Query%3A%28%2AProduct%202%2A%29%20AND%20%28%20ProductionDate%3A%5B2015-07-22T00%3A00%3A00.0000000%20TO%202015-08-22T00%3A00%3A00.0000000%5D%20AND%20Name%3A%22Product%202%22%29&pageSize=128&SortHint-ProductionDate=String\"\r\n\r\nSystem.ArgumentException: The field 'Name' is not indexed, cannot query on fields that are not indexed\r\n   at Raven.Database.Indexing.Index.AssertQueryDoesNotContainFieldsThatAreNotIndexed(IndexQuery indexQuery, AbstractViewGenerator viewGenerator)\r\n   at Raven.Database.Indexing.Index.IndexQueryOperation.<Query>d__5d.MoveNext()\r\n   at Raven.Database.Util.ActiveEnumerable`1..ctor(IEnumerable`1 enumerable)\r\n   at Raven.Database.Actions.QueryActions.DatabaseQueryOperation.Init()\r\n   at Raven.Database.Actions.QueryActions.<>c__DisplayClasse.<Query>b__a(IStorageActionsAccessor accessor)\r\n   at Raven.Storage.Esent.TransactionalStorage.ExecuteBatch(Action`1 action, EsentTransactionContext transactionContext)\r\n   at Raven.Storage.Esent.TransactionalStorage.Batch(Action`1 action)\r\n   at Raven.Database.Actions.QueryActions.Query(String index, IndexQuery query, CancellationToken externalCancellationToken)\r\n   at Raven.Database.Server.Controllers.IndexController.PerformQueryAgainstExistingIndex(String index, IndexQuery indexQuery, Etag& indexEtag, HttpResponseMessage msg, CancellationToken token)\r\n   at Raven.Database.Server.Controllers.IndexController.ExecuteQuery(String index, Etag& indexEtag, HttpResponseMessage msg, CancellationToken token)\r\n   at Raven.Database.Server.Controllers.IndexController.GetIndexQueryResult(String index, CancellationToken token)\r\n   at Raven.Database.Server.Controllers.IndexController.IndexGet(String id)\r\n   at lambda_method(Closure , Object , Object[] )\r\n   at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ActionExecutor.<>c__DisplayClass10.<GetExecutor>b__9(Object instance, Object[] methodParameters)\r\n   at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ExecuteAsync(HttpControllerContext controllerContext, IDictionary`2 arguments, CancellationToken cancellationToken)\r\n--- End of stack trace from previous location where exception was thrown ---\r\n   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)\r\n   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)\r\n   at System.Runtime.CompilerServices.TaskAwaiter`1.GetResult()\r\n   at System.Web.Http.Controllers.ApiControllerActionInvoker.<InvokeActionAsyncCore>d__0.MoveNext()\r\n--- End of stack trace from previous location where exception was thrown ---\r\n   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)\r\n   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)\r\n   at System.Runtime.CompilerServices.TaskAwaiter`1.GetResult()\r\n   at System.Web.Http.Controllers.ActionFilterResult.<ExecuteAsync>d__2.MoveNext()\r\n--- End of stack trace from previous location where exception was thrown ---\r\n   at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)\r\n   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)\r\n   at System.Runtime.CompilerServices.TaskAwaiter`1.GetResult()\r\n   at System.Web.Http.Controllers.ExceptionFilterResult.<ExecuteAsync>d__0.MoveNext()"}

Nguyễn Huy

unread,
Jul 22, 2015, 1:37:36 AM7/22/15
to rav...@googlegroups.com
I know the root cause but when I add this to the map so I can not query by productName, productStatus ,Attachment Name. BTW thank Kijana

Oren Eini (Ayende Rahien)

unread,
Jul 22, 2015, 2:08:30 AM7/22/15
to ravendb
Add those fields directly to the index

Nguyễn Huy

unread,
Jul 22, 2015, 2:46:07 AM7/22/15
to rav...@googlegroups.com
Hi 

I add the index for the query already :

 public class Product_Search : AbstractIndexCreationTask<ProductModel, Product_Search.Result>
    {

        public class Result
        {
            public string Query;
            public ProductModel ProductModel;
        }

        public Product_Search()
            {
                Map = products => from product in products
                    select new
                    {
                        Query = new object[] { product.Name, product.Status, product.Att.Select(x => x.Name) },
                        product.ProductionDate
                       
                    };
                Index(x => x.Query, FieldIndexing.Analyzed);

            }
        }
    }

What need to add in that class ? can you explain >

Oren Eini (Ayende Rahien)

unread,
Jul 22, 2015, 3:10:08 AM7/22/15
to ravendb
You added that to the _query_ field.
Add the name directly:

  Map = products => from product in products
                    select new
                    {
                        Query = new object[] { product.Name, product.Status, product.Att.Select(x => x.Name) },
                        product.ProductionDate,
                        product.Name
                       
                    };

Nguyễn Huy

unread,
Jul 22, 2015, 10:26:51 AM7/22/15
to rav...@googlegroups.com
Hi Oren,

When I added to that index so the   Query = new object[] { product.Name, product.Status, product.Att.Select(x => x.Name) },

product.Name in that query is not worked anymore . Is there anyway to work 

Oren Eini (Ayende Rahien)

unread,
Jul 22, 2015, 10:28:30 AM7/22/15
to ravendb
You need it as a top level field.

Nguyễn Huy

unread,
Jul 22, 2015, 10:31:09 AM7/22/15
to RavenDB - 2nd generation document database
It mean .Right ?

  Map = products => from product in products
                    select new
                    {
                        product.ProductionDate,
                        product.Name,
                        Query = new object[] { product.Name, product.Status, product.Att.Select(x => x.Name) }
                    
                       
                    };

Vào 21:28:30 UTC+7 Thứ Tư, ngày 22 tháng 7 năm 2015, Oren Eini đã viết:

Oren Eini (Ayende Rahien)

unread,
Jul 22, 2015, 10:33:22 AM7/22/15
to ravendb
Yes

Nguyễn Huy

unread,
Jul 22, 2015, 10:40:48 AM7/22/15
to RavenDB - 2nd generation document database
I will try tomorrow and let you know the result .Thank Oren

Vào 21:33:22 UTC+7 Thứ Tư, ngày 22 tháng 7 năm 2015, Oren Eini đã viết:

Nguyễn Huy

unread,
Jul 22, 2015, 10:16:38 PM7/22/15
to RavenDB - 2nd generation document database, fridayth...@gmail.com
Hi Oren. The result is the same when I move product.Name in the top of the map

Vào 21:40:48 UTC+7 Thứ Tư, ngày 22 tháng 7 năm 2015, Nguyễn Huy đã viết:

Nguyễn Huy

unread,
Jul 28, 2015, 4:43:00 AM7/28/15
to rav...@googlegroups.com
Can you help me in this case ? I can not do as your advise

Grisha Kotler

unread,
Jul 28, 2015, 4:44:38 AM7/28/15
to rav...@googlegroups.com
How does your query and index look like now?

Hibernating Rhinos Ltd  cid:image001.png@01CF95E2.8ED1B7D0

Grisha Kotler l RavenDB Core Team Developer Mobile: +972-54-586-8647

RavenDB paving the way to "Data Made Simplehttp://ravendb.net/

Nguyễn Huy

unread,
Jul 28, 2015, 4:49:33 AM7/28/15
to rav...@googlegroups.com
As suggest from Oren this is my index :

 public class Product_Search : AbstractIndexCreationTask<ProductModel, Product_Search.Result>
    {

        public class Result
        {
            public string Query;
            public ProductModel ProductModel;
        }

        public Product_Search()
        {
            Map = products => from product in products
                              select new
                              {
                                  product.Name
                                  Query = new object[] { product.Name, product.Status, product.Att.Select(x => x.Name) },
                                  product.ProductionDate

                              };
            Index(x => x.Query, FieldIndexing.Analyzed);

        }
    }

And my myquery here 
  results = Session.Query<Product_Search.Result, Product_Search>().Search(x => x.Query, searchString.GetQueryProduct(searchString),
                        escapeQueryOptions: EscapeQueryOptions.AllowAllWildcards, options: SearchOptions.And).Statistics(out stats).As<ProductModel>()
                        .Where(x => x.ProductionDate >= fromDate && x.ProductionDate <= toDate&&x.Name==searcString).Skip((page - 1) * limit).Take(limit).ToList();


if I add x.Name==searcString . I can search full text base on that string . But it will destroy search by Status and AttachmentName. Is anyway to fix it ?



Grisha Kotler

unread,
Jul 28, 2015, 5:04:11 AM7/28/15
to rav...@googlegroups.com
How does searchString.GetQueryProduct look like?

Hibernating Rhinos Ltd  cid:image001.png@01CF95E2.8ED1B7D0

Grisha Kotler l RavenDB Core Team Developer Mobile: +972-54-586-8647

Office: +972-4-622-7811 l Fax: +972-153-4-622-7811

RavenDB paving the way to "Data Made Simplehttp://ravendb.net/


Nguyễn Huy

unread,
Jul 28, 2015, 5:12:40 AM7/28/15
to rav...@googlegroups.com

Nguyễn Huy

unread,
Jul 28, 2015, 10:48:27 AM7/28/15
to RavenDB - 2nd generation document database, gri...@hibernatingrhinos.com
Can you pls check ?

Vào 16:04:11 UTC+7 Thứ Ba, ngày 28 tháng 7 năm 2015, Grisha Kotler đã viết:
...

Kijana Woodard

unread,
Jul 28, 2015, 10:54:25 AM7/28/15
to rav...@googlegroups.com
You would do a full text search and and exact match on the same field at the same time. It doesn't make much sense.

You should setup a full failing test with data so we can see what you're trying to do and execute.

Nguyễn Huy

unread,
Jul 28, 2015, 10:59:28 AM7/28/15
to rav...@googlegroups.com
Ok . I will explain here. with the original I did not put the product.name in the top of the map . So I can query with the name,status and the name of the child of product object. But when I put the product.name so I can query with the full name for example :Product 1. But we can not search with the status and child's name anymore .I know the reason becasue this is below my query I use & so I can not query the other fields. Is there any way to query with my requirement

And my myquery here 
  results = Session.Query<Product_Search.Result, Product_Search>().Search(x => x.Query, searchString.GetQueryProduct(searchString),
                        escapeQueryOptions: EscapeQueryOptions.AllowAllWildcards, options: SearchOptions.And).Statistics(out stats).As<ProductModel>()
                        .Where(x => x.ProductionDate >= fromDate && x.ProductionDate <= toDate&&x.Name==searcString).Skip((page - 1) * limit).Take(limit).ToList();


if I add x.Name==searcString . I can search full text base on that string . But it will destroy search by Status and AttachmentName. Is anyway to fix it ?

Oren Eini (Ayende Rahien)

unread,
Jul 28, 2015, 11:01:49 AM7/28/15
to ravendb
Please see the following document with regards to how to send a full functional failing unit test.

Nguyễn Huy

unread,
Jul 28, 2015, 11:04:40 AM7/28/15
to rav...@googlegroups.com
thank
Reply all
Reply to author
Forward
0 new messages