4

my question is very simple. I want to combine two filters one filter_bool and one filter_range in one query in Elastica. The code is

public function getAdvancedTweetsEs($keyword, $location, $datepicker, $datepicker1, $offset)
{
    $elasticaClient = new Elastica_Client();

    // Load index
    $elasticaIndex = $elasticaClient->getIndex('mongoindex3');

    // Define a Query. We want a string query.
    $elasticaQueryString = new Elastica_Query_QueryString();
    //$elasticaQueryString->setDefaultOperator('AND');
    $elasticaQueryString->setQuery($keyword);

    // Create the actual search object with some data.
    $elasticaQuery = new Elastica_Query();
    $elasticaQuery->setQuery($elasticaQueryString);
    $elasticaQuery->setFrom(0);
    $elasticaQuery->setLimit($offset);

    //Set a filter in text
    $elasticaFilterBool = new Elastica_Filter_Bool();                
    $filter1 = new Elastica_Filter_Term();
    $filter2 = new Elastica_Filter_Term();
    $filter1->setTerm('text', array(strtolower($keyword)));
    $filter2->setTerm('location', array(strtolower($location)));        
    $elasticaFilterBool->addMust($filter1);
    $elasticaFilterBool->addMust($filter2);
    $elasticaQuery->setFilter($elasticaFilterBool);

    $range = new Elastica_Query_Range();
    $range->addField('date', 
                        array(  'from' => $datepicker,
                                'to' => $datepicker1
                             ) 
                     );                 

    //Search on the index.
    $elasticaResultSet = $elasticaIndex->search($elasticaQuery);

    $elasticaResults = $elasticaResultSet->getResults();

    $results = array();

    foreach ($elasticaResults as $elasticaResult) 
    {   
        $results[] = $elasticaResult->getData();
    }

    return $results;
}

I can't put together two filters together in $elasticaQuery. Please I will appreciate any help!

thanks!

1 Answers1

4

Why don't you add the range filter as another must term in the bool filter:

$rangeFilter = new Elastica_Filter_Range();
$rangeFilter->addField('date', 
                    array(  'from' => $datepicker,
                            'to' => $datepicker1
                         ) 
                 ); 
$elasticaFilterBool->addMust($rangeFilter);
$elasticaQuery->setFilter($elasticaFilterBool);

You need to use filters, not queries, in a boolean filter. Note I have used Elastica_Filter_Range instead of the range query you were using.

Also, you know you are using an outdated version of Elastica, the new ones use namespaces!

ramseykhalaf
  • 3,371
  • 2
  • 17
  • 16
  • thanks! You have absolutely right! The building of query and its filters is totally correct, but still the date range I give isn't recognised. In my mapping date is a string. What can I do? Date in my datepicker is for example "09/06/13" and with the same format is stored into my database. – Dimitris Tsarouhas Sep 08 '13 at 11:49
  • You need to specify your date format in your mapping if you are not using the default format. If you use the default format elasticsearch will automatically map it as a date. Have a [look at this question/answer](http://stackoverflow.com/questions/17832217/store-date-format-in-elasticsearch/17832824#17832824), it should help you. – ramseykhalaf Sep 08 '13 at 20:07
  • I use MongoDB for my database, so the mapping was created automatically by elasticsearch-mongodb-river (https://github.com/richardwilly98/elasticsearch-river-mongodb). So the date was characterized as string automatically. Now I have to find a way to turn type into date.Thanks again! – Dimitris Tsarouhas Sep 08 '13 at 21:42
  • You can't change the mapping of a field that has been indexed already. If you can you need to use the `"put mapping API" to send the mapping before the river sends data and elsaticsearch tries to guess (wrongly) the mapping. – ramseykhalaf Sep 08 '13 at 23:12
  • Finally, i solved the case. So, what I have done. First of all, I use elasticsearch-head-master (https://github.com/mobz/elasticsearch-head), in order to have a look at my elasticsearch indexes and their condition. So, I deleted the previous index with the wrong mapping. I made a new index and with the right mapping and then I connected MongoDB with elasticsearch through the river. The new mapping was succeeded and my range filter is working fine at last! thanks again! – Dimitris Tsarouhas Sep 09 '13 at 15:58