2011-08-25 34 views
15

Tôi đã làm việc với ElasticSearch từ vài tháng trước, nhưng vẫn thấy nó phức tạp khi tôi phải vượt qua một truy vấn phức tạp.Làm cách nào để sử dụng thông số truy vấn ElasticSearch Query (truy vấn DSL) cho nhiều loại?

Tôi muốn chạy các truy vấn mà sẽ phải tìm kiếm nhiều "loại" và từng loại phải được tìm kiếm với "bộ lọc" của riêng mình, nhưng cần phải có kết hợp "đã tìm kiếm kết quả"

Ví dụ:

Tôi cần tìm kiếm tài liệu "loại người dùng" là bạn bè của tôi và đồng thời tôi phải tìm kiếm tài liệu "loại đối tượng" mà tôi thích, theo từ khóa được cung cấp.

HOẶC

Truy vấn có cả "AND" và "KHÔNG" khoản

truy vấn Ví dụ:

$options['query'] = array(
     'query' => array(
      'filtered' => array(
       'query' => array(
        'query_string' => array(
         'default_field' => 'name', 
         'query' => $this->search_term . '*', 
        ), 
       ), 
       'filter' => array(
        'and' => array(
         array(
          'term' => array(
           'access_id' => 2, 
          ), 
         ), 
        ), 

        'not' => array(
         array(
          'term' => array(
           'follower' => 32, 
          ), 
         ), 

         array(
          'term' => array(
           'fan' => 36, 
          ), 
         ), 
        ), 
       ), 
      ), 
     ), 
    ); 

như truy vấn này có nghĩa là để tìm kiếm cho người dùng access_id = 2 , nhưng không được có người theo dõi id 32 và người hâm mộ của id 36

nhưng điều này không hoạt động ..

Edit: truy vấn Modified

{ 
    "query": { 
    "filtered": { 
     "filter": { 
     "and": [ 
      { 
      "not": { 
       "filter": { 
       "and": [ 
        { 
        "query": { 
         "query_string": { 
         "default_field": "fan", 
         "query": "*510*" 
         } 
        } 
        }, 
        { 
        "query": { 
         "query_string": { 
         "default_field": "follower", 
         "query": "*510*" 
         } 
        } 
        } 
       ] 
       } 
      } 
      }, 
      { 
      "term": { 
       "access_id": 2 
      } 
      } 
     ] 
     }, 
     "query": { 
     "field": { 
      "name": "xyz*" 
     } 
     } 
    } 
    } 
} 

bây giờ sau khi chạy truy vấn này, tôi đang nhận hai kết quả, một với theo: "34.518" & fan: "510" và thứ hai với người hâm mộ: "34", nhưng nó không phải là kết quả thứ hai trong kết quả.

Bất kỳ ý tưởng nào?

Trả lời

14

Bạn có thể muốn nhìn vào slide của một bài thuyết trình mà tôi đã trong tháng này, điều này giải thích những điều cơ bản về cách thức DSL truy vấn hoạt động:

Terms of endearment - the ElasticSearch Query DSL explained

Vấn đề với truy vấn của bạn là bộ lọc của bạn được lồng nhau không chính xác. Các andnot bộ lọc chỉ ở mức tương tự, nhưng các bộ lọc not nên dưới and:

curl -XGET 'http://127.0.0.1:9200/_all/_search?pretty=1' -d ' 
{ 
    "query" : { 
     "filtered" : { 
     "filter" : { 
      "and" : [ 
       { 
        "not" : { 
        "filter" : { 
         "and" : [ 
          { 
           "term" : { 
           "fan" : 36 
           } 
          }, 
          { 
           "term" : { 
           "follower" : 32 
           } 
          } 
         ] 
        } 
        } 
       }, 
       { 
        "term" : { 
        "access_id" : 2 
        } 
       } 
      ] 
     }, 
     "query" : { 
      "field" : { 
       "name" : "keywords to search" 
      } 
     } 
     } 
    } 
} 
' 
+0

Bộ lọc "không" luôn có trong bộ lọc "và" hay chỉ trong trường hợp này là –

+0

Xin chào @DrTech, tôi vừa chỉnh sửa câu hỏi, vui lòng kiểm tra. –

+1

Câu hỏi đã chỉnh sửa của bạn giới thiệu các sự cố khác. Tôi khuyên bạn nên xem qua bản trình bày mà tôi đã liên kết đến - nó giải thích sự khác biệt giữa các điều khoản và văn bản cũng như loại truy vấn hoặc bộ lọc để sử dụng ở đâu. – DrTech

3

Tôi chỉ cố gắng nó với "BOOL"

{ 
    "query": { 
    "bool": { 
     "must": [ 
     { 
      "term": { 
      "access_id": 2 
      } 
     }, 
     { 
      "wildcard": { 
      "name": "xyz*" 
      } 
     } 
     ], 
     "must_not": [ 
     { 
      "wildcard": { 
      "follower": "*510*" 
      } 
     }, 
     { 
      "wildcard": { 
      "fan": "*510*" 
      } 
     } 
     ] 
    } 
    } 
} 

Nó cung cấp cho câu trả lời đúng.

nhưng tôi không chắc nó nên được sử dụng như thế này?

+2

Điều này sẽ hiệu quả, nhưng cực kỳ kém hiệu quả. Các mệnh đề ký tự đại diện phải tải tất cả các cụm từ, tìm tất cả các cụm từ phù hợp, sau đó viết lại truy vấn để bao gồm tất cả các cụm từ đó. Điều đó thực sự có thể nổ tung. Tốt hơn hết là phân tích dữ liệu của bạn một cách chính xác vào thời gian chỉ mục, để bạn có thể chia nhỏ các giá trị của mình thành các thuật ngữ riêng biệt, mà bạn có thể đối sánh riêng lẻ. Bạn có thể cần phải xem xét bằng cách sử dụng phân tích ngram, nhưng nó thực sự phụ thuộc vào dữ liệu của bạn. Hãy xem chủ đề này để biết ví dụ về http://elasticsearch-users.115913.n3.nabble.com/help-needed-with-the-query-tt3177477.html#a3178856 – DrTech

+1

Cảm ơn @DrTech, nó được giải thích rất rõ . +1. Và tôi thực sự sẽ nói rằng bạn nên viết một hướng dẫn đầy đủ về ElasticSearch, bởi vì chưa có ai thực hiện nó :) Cảm ơn –

Các vấn đề liên quan