検索インデックス・フィルターの構文

DataStax Enterpriseは、DSE SearchノードにおけるCQL Solrクエリーの実稼働レベルの実装をサポートしています。Solr固有のAPIを使用せずに全文検索できる、CQLを中核としたアプリケーションを開発します。

DataStax Enterpriseは、DSE SearchにおけるCQL Solrクエリーの実稼働レベルの実装をサポートしています。Apache Solr™固有のAPIを使用せずに全文検索できる、CQLを中核としたアプリケーションを開発できます。全文検索クエリーのみがサポートされています。

制約事項:
  • CQL Solrクエリーはデフォルトで同等のLIMIT 10に設定されます。
  • ページネーションはデフォルトでオフになっています。dse.yamlのcql_solr_query_pagingオプションは、どのような場合にページネーション(カーソルとも呼ばれる)を使用するかを指定します
  • Solrの制限事項ページネーションに適用されます。
  • クエリーの結果セットが小さいほど、ページングをオフにした状態のパフォーマンスが向上します。
  • 制限事項と既知のApache Solrの問題がDSE Searchクエリーに適用されます。たとえば、トークン化された文字列フィールドのソート結果が正しくないなどの問題です。
  • カラム別名は、solr_queryクエリーでサポートされていません。

検索インデックス・クエリーの構文

SELECT文のWHERE句のsolr_queryオプションを使用して、インデックス・カラムに対するクエリーを実行します。

構文

SELECT selectors FROM table
 WHERE solr_query = 'search_expression' [LIMIT n]
以下の2種類の検索インデックス式があります。
注: 検索インデックス・フィールドでフィルター処理するには、solr_queryオプションを使用します。例を次に示します。
SELECT * from users WHERE solr_query = 'irc:jdoe';
検索インデックスではクエリーを直接実行できません。たとえば、以下の構文は失敗します。
SELECT * FROM users WHERE irc = 'jdoe';

基本的なインデックス・クエリーの作成

CQLクエリー式では、Solrのqパラメーターによってサポートされている構文を使用します。 CQLで、文字列リテラル内に単一引用符を使用するには、単一引用符を使用してエスケープする必要があります(つまり、単一引用符を二重にする必要があります)。CQLの「文字のエスケープ」を参照してください。 例を次に示します。
SELECT * FROM keyspace.table WHERE solr_query='name: cat name: dog -name:fish'
特定のカラムを指定すると、DSE Searchは、指定されたカラムだけを取得し、それらのカラムを結果行の一部として返します。DSE Searchは、select式として射影(SELECT a, b, c…)のみをサポートし、関数はサポートしていません。以下の例では指定カラムのみを取得します。
SELECT name FROM keyspace.table WHERE solr_query='name:cat name:dog -name:fish'
LIMIT句を使用して、返す行の数を指定します。以下の例では1行のみを取得します。
SELECT * FROM keyspace.table WHERE solr_query='name:cat name:dog -name:fish' LIMIT 1
CQL SolrクエリーでCount()関数を使用すると、Solrクエリーを満たす行数が返されます。
SELECT count(*) FROM table WHERE solr_query = '...';

count()をLIMITまたはファセットと組み合わせて使用すると、エラーが発生します。

ドライバーのすべての応答クエリーにカスタム・ペイロードがあり、検出されたドキュメントの総数が返されます。この値は、DSESearch.numFoundとして入力されます。

高度なsolr_query式の作成

DSE Searchは、JSONベースの式を含む高度なSolr検索を使用したCQLクエリーのフィルター処理をサポートしています。

DSE Searchは、JSONベースの式を含む高度なSolr検索を使用したCQLクエリーのフィルター処理をサポートしています。

このページに含まれる内容:

検索クエリーのデフォルトのTimeZone(UTC)のオーバーライド」も参照してください。

JSONクエリー構文

JSONクエリー式の構文は、JSON文字列です。JSONベースのクエリー式は、以下のパラメーターに加えてローカル・パラメーターをサポートしています。
{
  "q": query_expression (string), 
  "fq": filter_query_expression(s) (string_or_array_of_strings, ...),  
  "facet": facet_query_expression (object) 
  "sort": sort_expression (string), 
  "start": start_index(number),
  "tz": zoneID),   //  Any valid zone ID in java TimeZone class                            
  "paging": "driver" (string),
  "distrib.singlePass": true|false (boolean),
  "shards.failover": true|false (boolean),    // Default: true
  "shards.tolerant": true|false (boolean),    // Default: false
  "commit": true|false (boolean),
  "route.partition": partition_routing_expression (array_of_strings), 
  "route.range": range_routing_expression (array_of_strings), 
  "query.name": query_name (string),
}
例を次に示します。
SELECT id FROM nhanes_ks.nhanes WHERE solr_query=' {"q":"ethnicity:Asian"}';
SELECT id FROM nhanes_ks.nhanes WHERE solr_query='{"q":"ethnicity:Mexi*", "sort":"id asc"}' LIMIT 3;
SELECT * FROM mykeyspace.mytable WHERE solr_query='{"q" : "{!edismax}quotes:yearning or kills"}';
注: Apache Solr™ Extended DisMaxクエリー・パーサー(eDisMax)をsolr_queryとともに使用するには、defaultSearchFieldをスキーマに含める必要があります。

分散クエリーをシャード障害耐性にする

分散クエリーは多くのシャードにアクセスするため、クエリーのシャード障害耐性を向上させることで、クエリー実行の成功率が高まります。shards.failoverパラメーターとshards.tolerantパラメーターを使用して、JSONクエリー中に発生するクエリーのフェイルオーバーとシャード障害耐性を定義します。
有効な構成 説明
"shards.failover": true,
"shards.tolerant": false,
このデフォルトの構成を使用すると、クエリー・フェイルオーバーが有効になり、フォールト・トレランスが無効になります。エラーから復旧の見込みが妥当と判断される場合は、失敗したシャード要求をリトライしてください。クエリーが完了する前に分散したノード(シャード)のいずれかが失敗する場合は、レプリカに対してシャード・クエリーをリトライします。
"shards.failover": false,
"shards.tolerant": true,
クエリー・フェイルオーバーが無効になります。フォールト・トレランスが有効になります。クエリーが部分的にしか正常に完了せず、すべてのノードに対して正常に完了しなかった場合でも、クエリーを正常な完了とします。
"shards.failover": false,
"shards.tolerant": false,
クエリー・フェイルオーバーが無効になります。フォールト・トレランスも無効になります。
フェイルオーバーと部分的な結果のトレランスは同じクエリーに共存できません。クエリーは、単一のパラメーターのみに対するトレランスの有効化をサポートしています。

その他のフォールト・トレランスの構成オプションには、dse.yamlnetty_client_request_timeoutと、cassandra.yamlread_request_timeout_in_msがあります。

Apache Solr™/Apache Lucene®特殊文字であるリテラル文字を使用したJSONクエリー

Luceneは、クエリー構文に使用されている特殊文字のエスケープをサポートしています。特殊文字には、+、-、&&、||、!、(、)、"、~、*、?、:があります。solr_queryとともにJSONを使用する場合は、Lucene特殊文字であるリテラル文字の追加の構文が必要です。

単純な検索文字列の構文:
単純な検索文字列 mytestuser1?
Solrクエリー name:mytestuser1\?
CQL Solrクエリー solr_query='{"q":"name:mytestuser1\\?"}'
複雑な検索文字列の構文:
複雑な検索文字列 (1+1):2
Solrクエリー e:\(1\+1\)\:2
CQL Solrクエリー solr_query='{"q":"e:\\(1\\+1\\)\\:2"}'

JSONクエリーによるフィールド、クエリー、および範囲のファセット化

ファセットJSONオブジェクト内のファセット・パラメーターを指定して、Solrクエリー内のフィールド、クエリー、および範囲のファセット化を実行します。分散されたピボットのファセット化がサポートされています。ファセットを指定するためのクエリー構文を簡潔にするには、以下を行います。
  • HTTP APIで要求されるファセット・プレフィックスを使用せずに各ファセット・パラメーターを指定する。
  • 複数のファセット・フィールドとクエリーをJSON配列内で表現する。
ファセット化された検索の例
SELECT * FROM solr WHERE solr_query='{"q":"id:*","facet":{"field":"type"}}';
クエリー・ファセットの例
SELECT * FROM solr WHERE solr_query='{"q":"id:*","facet":{"query":"type:0"}}';
複数のクエリーの例
SELECT * FROM solr WHERE solr_query='{"q":"id:*","facet":{"query":["type:0","type:1"]}}';
分散されたピボットのファセット化の例
SELECT id FROM table WHERE solr_query='{"q":"id:*","facet":{"pivot":"type,value","limit":"-1"}}'
範囲ファセットの例
SELECT * FROM solr WHERE solr_query='{"q":"id:*","facet":{"range":"type", "f.type.range.start":-10, "f.type.range.end":10, "range.gap":1}}}';
返される結果は、各カラムがファセットの出力(フィールド、クエリー、または範囲)に対応した単一行の形式で出力されます。ファセット結果は複雑でネストされている場合があるため、値はJSON BLOBとして表されます。例を次に示します。
facet_fields           | facet_queries
------------------------+-------------------------
 {"type":{"0":2,"1":1}} | {"type:0":2,"type:1":1}
日付別範囲ファセットの例
SELECT * FROM solr WHERE solr_query='{"q":"business_date:*","facet":{"range":"business_date", "f.business_date.range.start":"2015-01-01T00:00:00Z", "f.business_date.range.end":"2015-08-01T00:00:00Z", "f.business_date.range.gap":"+1MONTH"}}';
警告: Solrの範囲ファセットの先頭、末尾、および中間で、マルチノード・クラスターについて不正確で整合性の低い結果が返される場合があります。SOLR-6187およびSOLR-6375を参照してください。
間隔ファセットの例
SELECT * FROM solr WHERE solr_query='{"q":"id:*","facet":{"interval":"id", "interval.set":"[*,500]"}';

分散クエリーのトレース

分散クエリーの実行時、トークン範囲セットの処理は各ノードが行います。シャードは、ノードと範囲の組み合わせです。シャード・トークン範囲は以下の場所で報告されます。
  • HTTPクエリーのshards.info応答内。
  • cassandra.trace=trueを指定するHTTPクエリーと、ドライバー・レベルのトレースを有効にするCQL Solrクエリーのsystem_traces.eventsテーブル内。

JSONシングルパス分散クエリー

CQL Solrクエリーではシングルパス分散クエリーがサポートされています。

標準の2パス・クエリーの代わりにシングルパス分散クエリーを使用するには、JSONクエリー式でdistrib.singlePassブーリアン・パラメーターを指定します。
SELECT * FROM ks.cf WHERE solr_query = '{"q" : "*:*", "distrib.singlePass" : true}'
シングルパス分散クエリーを使用すると、ディスクとネットワークのオーバーヘットが増える可能性があるため、運用コストがかかります。シングルパス・クエリーでは、各ノードはクエリーを満たす行をすべて読み取り、コーディネーター・ノードに返します。シングルパス分散クエリーは高度な機能であるため、クエリーが実行された行の取得中に1回のネットワーク往復の転送が保存されます。通常の分散クエリーではネットワークを2回往復します。1回目はクエリーを満たすIDをDSE Searchから取得し、2回目は最初のステップで取得したIDに基づいて、クエリーを満たす行のみをデータベースから取得します。シングルパス分散クエリーは、検出されたドキュメントのほとんどが検索結果に表示される場合に最も効果的です。これらのドキュメントのほとんどがコーディネーター・ノードに返されない場合は効果はありません。

たとえば、コーディネーター・ノードから単一ノードに分けるだけの分散クエリーは、シングルパス・クエリーとしては最も効果的です。

CQLのシングルパス分散クエリーは、追加のdistrib.singlePassブーリアン・パラメーターがJSONクエリーに含まれている場合にサポートされています。

シングルパス・クエリーでは、検索スキーマで定義されているドキュメント・フィールドのみがクエリー結果として返されるという制約があります。この制約は、動的フィールド・マッピングに従っていないマップ・エントリーにも適用されます。

JSONクエリーのnameオプション

以下の構文を使用して、パフォーマンス・オブジェクトのメトリクスと監視をサポートするようにクエリーに名前を付けます。クエリーに名前を付けると、タグ付けやJMX操作などに役立ちます。
SELECT id FROM nhanes_ks.nhanes WHERE solr_query=' {"query.name":"Asian subjects", "q":"ethnicity:Asia*"}' LIMIT 50;

JSONクエリーのcommitオプション

ドキュメントを一括で読み込んだ後にカスタム・クエリーを実行し、自動ソフト・コミットが無効になっているか、頻度が極端に低い値に構成されている場合、クエリーが最新データを取得できるようにするには、JSONクエリーのcommitオプションを使用して、すへての保留中の更新がソフト・コミットされていることを確認してからクエリーを実行します。デフォルトでは、commitオプションはfalseに設定されています。

例を次に示します。
SELECT id FROM nhanes_ks.nhanes WHERE solr_query='{"q":"ethnicity:Asia*", "commit":true}' LIMIT 50;
警告: 実稼働クラスターに対する稼働中の操作にJSONのcommitオプションを使用しないでください。DataStaxでは、Solr HTTPインターフェイスを介してコミットを強制的に発行するように求められた場合にのみ、JSONのcommitオプションを使用することを推奨します。commitオプションは、通常の自動ソフト・コミット・プロセスに置き換わるものではありません。

ページングを動的に有効にするためのクエリー

dse.yamlcql_solr_query_paging: offの場合にページネーションを動的に有効にするには、"paging":"driver"パラメーターを使用します。
select id from wiki.solr where solr_query='{"q":"*", "sort":"id asc", "paging":"driver"}';

solr_queryの文字のエスケープ

基本または高度なsolr_query式の特殊文字をエスケープする方法。

Solrクエリーでは、クエリー構文に含まれている特殊文字をエスケープする必要があります。特殊文字には、+、-、&&、||、!、(、)、"、~、*、?、:があります。 これらの文字をエスケープするには、エスケープする文字の前にスラッシュ(\)を含めます。たとえば、リテラル二重引用符(")文字を検索するには、\"としてSolrの"をエスケープします。

solr_queryを使用する場合、以下の2つの形式で特殊文字をエスケープできます。
CQL Solr
...WHERE solr_query='field:value'
JSON
WHERE solr_query='{ "q": "field:value"}'

また、JSONエンコード・クエリーでは、その値が特殊文字をJSON形式でエスケープしたものである必要があります。

二重引用符を含むクエリーでは、3つのスラッシュ\\\を使用します。
  • クエリー構文の場合:"をエスケープするには1つのスラッシュ\を使用します。
  • JSON文字列構文の場合:\をエスケープするには2つのスラッシュ\\を使用します。

    \"の両方の文字をエスケープするには3つのスラッシュ\\\を使用して、\\(エスケープ文字のエスケープ)と\"(二重引用符のエスケープ)を生成します。

単一引用符のエスケープ

  • 単一引用符(')を二重にする
    CQL
    ...WHERE solr_query='name:Walter''s'
    JSON
    ...WHERE solr_query='{ "q": "Walter''s"}'
  • 文字列定数にはドル記号引用符を使用する
    CQL
    ...WHERE solr_query=$$name:Walter's$$
    JSON
    ...WHERE solr_query=$${ "q": "Walter's"}$$

クエリーで二重引用符をエスケープする例

CQL
Solrのエスケープの場合は単一引用符(')を二重にしてバックスラッシュ(\)を追加する
...WHERE solr_query='name:Walter\''s'
JSON
JSONの場合は\"の両方の文字をエスケープするために\\\"にする
...WHERE solr_query='{ "q": "Walter\\\"s"}'

完全一致クエリーとあいまい一致クエリーの例

完全一致の句クエリー
以下のように、二重引用符を含んでいる電子メール・アドレス(greenr"q@example.com)を含む行の場合:
INSERT INTO users(id, email) VALUES(1, 'greenr"q@example.com')"
二重引用符で囲まれている電子メール・アドレスを検索するには、句クエリーを実行します。
SELECT * FROM users where solr_query = ' { "q": "*:*", "fq": "email:\"greenr\\\"q@example.com\""} ';
あいまい一致クエリー
以下のように、二重引用符を含んでいる同じ電子メール・アドレス(greenr"q@example.com)を含む行の場合:
select * from test.users where solr_query='{"q":"email:r\\\"q@example"}' ; id | email | solr_query ------+-------+------------------------------ 1 | greenr"q@example.com | null (1 rows)
r"q@exampleを含むすべての電子メール・アドレスを検出する単語クエリー(あいまい検索)では、二重引用符を削除しますが、電子メール・アドレスに含まれている二重引用符をエスケープするための三重の引用符は保持します。
SELECT * FROM users where solr_query = ' { "q": "*:*", "fq": "email:r\\\"q@example"} ';

solr_queryとともにJSONを使用する場合は、Lucene特殊文字であるリテラル文字の追加の構文が必要です。Solr特殊文字であるリテラル文字を使用したJSONクエリー」を参照してください。