Where 節

この記事には、以下のトピックが含まれています。
casm173
この記事には、以下のトピックが含まれています。
doSelect() や doQuery() など、一部の Web サービス メソッドでは、CA SDM やナレッジ管理を使用した検索時に
Where 節
が必要となります。 Where 節とは、SQL ステートメントの中で、「WHERE」というキーワードの後にくる文字列のことです。 たとえば、姓を使用して連絡先(「cnt」オブジェクト)を検索する Where 節は以下のようになります。
last_name = 'Jones'
または
last_name LIKE 'Jone%'
最初の例では「Jones」のみを検索しますが、2 つ目の例では名前が「Jone」で始まる連絡先をすべて検索します。
CA SDM がサポートする Where 節は、標準 SQL パラメータのサブセットのみです。以下がサブセットのリストです。
  • 論理演算子 AND、OR、および NOT
  • LIKE および IS
  • NULL
  • IN
  • ワイルドカード文字「%」および「_」(文字列の検索に使用)
  • すべての比較演算子(<, >, <=, >=, !=, <>)
グループ化する場合は丸かっこを使用します。 CA SDM では、明示的な結合、EXISTS、および GROUP BY エレメントはサポートされません。 文字列の値は引用符で囲む必要があります。たとえば、「‘Jones’」とします。
列名はオブジェクトの属性名を示しています。 CA SDM の日付や期間などのデータ タイプは整数として扱われます。 以下に例を示します。
creation_date > 38473489389
属性名はオブジェクト レベルで使用する必要があります。 実際の DBMS 列名を使用しないでください。
SREL (外部キー)タイプを検索する場合は、Where 節にドット表記を使用できます。 たとえば、リクエスト(「cr」)オブジェクトに対するクエリでは、次の例のように、連絡先に特定の姓が割り当てられたすべてのリクエストが返されます。
assignee.last_name like 'Martin%'
ドット表記は Where 節を作成するには非常に便利ですが、クエリが有効であることを確認する必要があります。 連絡先の last_name 属性のインデックスが DBMS で作成されていない場合は、例に挙げられているクエリ(
assignee.last_name like 'Martin%
)は有効ではない場合があります。 SREL を使用して検索するときに必ずインデックスを使用するには、CA SDM オブジェクトの ID 属性を使用します。 CA SDM のどのテーブルでも、ID 属性に対してインデックスが作成されています。
オブジェクトの ID 属性はオブジェクトのハンドルから簡単に取得することができます。 オブジェクトのハンドルは「
: 」形式の文字列で
。ここで
は、 すべての CA
SDM オ
ブジェクトにある ID 属性の値です。 ID 部分を抽出して、Where 節に「 .id」を使用します。
オブジェクトの ID は整数または UUID のどちらかです。 整数の場合、以下のように使用します。 たとえば、
rootcause
が根本原因オブジェクト(ハンドル「
rc:1234
」)を指しているリクエストを検索するには、Where 節は以下のようになります。
rootcause.id = 1234
オブジェクトの ID が UUID タイプの場合は、以下のようにフォーマットする必要があります。
U'<uuid>'
UUID の文字列は一重引用符で囲み、大文字の「U」を先頭に付けます。 この文字列はオブジェクト ハンドルの 部分です。 たとえば、特定の連絡先のハンドルが「cnt:913B485771E1B347968E530276916387」であるとわかっている場合、以下の例に示すように、クエリを作成できます。
assignee.id = U'913B485771E1B347968E530276916387'
以下の例のように、「persistent_id」属性のクエリを行う Where 節は作成しないでください。
rootcause.persistent_id = 'rc:1234'
ハンドルの詳細については、「デフォルトのハンドル」を参照してください。
IN 節
IN 節には特別な説明が必要です。 2 つの構文形式を以下に示します。
SREL_attr_name.subq_WHERE_attr[.attr] IN ( value1 [, value2 [,...]] ) SREL_attr_name.[subq_SELECT_attr]LIST_name.subq_WHERE_attr IN (value1, [,value2 [,...]] )
IN 節の左側は、クエリ対象のテーブルの SREL タイプの属性で始める必要があり、上記の例では
SREL_attr_name
となっています。
subq_WHERE_attr
は外部オブジェクトの属性で、それ自体が別の SREL ポインタである場合があります。
たとえば、リクエスト(「cr」)オブジェクトに対するクエリは以下のようにコード化できます。
category.sym IN ('Soft%', 'Email')
これは擬似 SQL で表すと以下のようになります。
SELECT ... FROM cr WHERE cr.category IN (SELECT persistent_id FROM pcat WHERE sym LIKE 'Soft%' OR sym = 'Email')
前述のサブクエリでは、「pcat」は cr.category が指すオブジェクト名です。
IN 節の 2 つ目の形式は、BREL リストを検索できます。 たとえば、特定のグループのアナリストに割り当てられたすべてのリクエストを検索する場合は、以下のようになります。
assignee.[member]group_list.group IN (U'913B485771E1B347968E530276916387')
IN 節の最初の部分(assignee)は、cr オブジェクトの SREL(外部キー)であり、cnt オブジェクトを指しています。 次の group_list は cnt オブジェクトの属性で、連絡先が属しているグループを表す cnt オブジェクトのリストです。 最後の部分(group)は、IN サブクエリにおいて、Where 節の最初の部分を形成します。 ‘U’913B485771E1B347968E530276916387 は、group に一致する外部キーの値です。 サブクエリの戻り値は [member] によって指定されます。 これは擬似 SQL ステートメントで表すと以下のようになります。
SELECT ... FROM cr WHERE cr.assignee IN (SELECT member from grpmem WHERE group = U'913B485771E1B347968E530276916387')
複数のオブジェクトと一致する複数の外部キーを指定するには、以下のようにカンマ区切りリストを使用します。
assignee.[member]group_list.group IN (U'913B485771E1B347968E530276916387', U'913B485771E1B347968E530276916300')
このように IN 節を使用する場合に、ドット記法を拡張することはできません。たとえば、以下の指定は無効です。
assignee.[member]group_list.group.last_name IN ('Account Center')
INを使用する理由の1つは、直積を避けるためです。 たとえば、以下のようなクエリの結果は直積となり、効率が非常に悪くなります。
assignee.last_name LIKE 'MIS%' OR group.last_name LIKE 'MIS%'
IN を使用したクエリは以下のようにコード化できます。
assignee.last_name IN 'MIS%' OR group.last_name IN 'MIS%'
このクエリでは直積が作成されないどころか、結合さえも行われません。
IN の右側にある値のリストを囲むために通常使用するかっこは、リスト内の値が 1 つのみの場合は省略することができます。 同様に、クエリを変換して結合を避ける必要があります。
assignee.last_name LIKE 'Smith'
変換後
assignee = U'913B485771E1B347968E530276916387'
このようにすると、多少明確さに欠けますが、結合を避けることができます。IN を使用すれば、上記のクエリを以下のように記述できます。この場合、最初の例の明確さと、2 つ目の例の効率の良さを保つことができます。
assignee.last_name IN 'Smith'
「NOT」キーワードは、「NOT IN」のように、IN と組み合わせて使用することはできません。
リスト
一部の Web サービス メソッドでは、一意の整数型ハンドルで表される
リスト
が返されます。 リストは単に同じタイプのオブジェクトを集めたものです。 リストは多数のオブジェクトの集まり(システム内のすべての連絡先など)を扱うときに特に便利です。リスト内の複数の項目に関する情報を取得できるからです。 ただし、リスト ハンドルの取得、情報の取得、最終的なリスト ハンドルの解放のために、メソッドのコール回数が増えるという難点があります。 リストの行が少ないと思われる場合は、リスト ハンドルが関係しない doSelect() などのメソッドを使用します。
リストの詳細は以下のとおりです。
  • リストは均質である
    リストに含まれるのは、連絡先リストや組織リストなど、単一タイプのオブジェクトのみです。
  • リストは静的である
    たとえば、すべての連絡先用のリスト オブジェクトを取得した後に、別の連絡先がシステムに追加された場合、連絡先の追加による更新はリストに反映されません。 最新のデータを取得するには、別のリスト ハンドルを取得する必要があります。
  • リスト ハンドル
    リストをリクエストすると、同じタイプのオブジェクトのリストを表す整数ハンドルが返されます。 クライアントにその他の情報は送信されません。 クライアントはリストをクエリして、リスト内の行に含まれる特定の情報を取得できます。 クライアントはリストを使用した後、freeListHandles() を使用してハンドルを解放する必要があります。 CA SDM サーバがリストを保持しているため、システムのリソースが消費されます。 したがって、リストを解放することは重要です。 オブジェクト ハンドルとは違って、リスト ハンドルはセッション間で固定されていません。
  • 整数インデックス
    いくつかのメソッドでは、整数インデックスをリストに含める必要があります。 リストはゼロベースのため、最初のエレメントのインデックスは 0 になります。
前述のとおり、リスト ハンドルは何回もクエリされる可能性のある大きなデータに使用すると便利です。 ただし、操作の種類によっては、リストが大きくなることがあります。 メソッドもいくつか用意されており、代表的なものは doSelect() です。リスト ハンドルのオーバーヘッドなしで、データ セットに関するリクエストされた情報が返されます。
リスト ハンドルとメソッド(doSelect() など)のどちらを使用するかは、パフォーマンスと利便性のどちらを重視するかで決まります。 たとえば、アプリケーションがシステム内の15,000個すべての連絡先を処理するとします。 doSelect() メソッドでは、1 回のコールですべての連絡先データを取得することができます。しかし、応答は遅くなり、非常に大きなデータ セットを収集して返す間、システム全体のパフォーマンスは悪くなります。 この場合、doQuery() メソッドでは、リスト参照が非常に迅速に返されます。 リストから特定のデータ範囲をクエリすれば、サーバの応答時間を短縮することができます。 目安として、データ セットのアイテムが 250 個を超える場合にリスト参照を使用することをお勧めします。
リスト ハンドルを使用する意味がない場合もあります。 たとえば、案件にはアクティビティ ログのリストがあります。 インストール形態によって、ログの数が数個から数十個の範囲で違いがあります。 リスト参照をリクエストしてデータをクエリし、リストを解放するよりも、一度にすべてのデータをリクエストする方が早いと考えられます。
リスト参照の代わりにデータ セットを返すメソッドの例は以下のとおりです。
  • doSelect()
  • getRelatedListValues()
  • getLrelValues()
  • getTaskListValues()
  • getValidTaskTransitions()
前述のとおり、多くの行を返すクエリはサーバのパフォーマンスに深刻な影響を及ぼします。 これに対処するため、CA SDM では返される行数を 250 に制限しています。 これは、以下のものを含め、オブジェクトのリストを返すすべての CA SDM Web サービス メソッドに影響を与えます。
  • doSelect()
  • doSelectKD()
  • getGroupMemberListValues()
  • getListValues()
  • getPropertyInfoForCategory()
  • getRelatedListValues()
  • getTaskListValues()
  • getValidTaskTransitions()
これらのメソッドで 250 を超える行を取得するようリクエストした場合でも、制限は適用されます。
多数の行を取得するには、結果リストに対するハンドルを取得し、getListValues() を使用して、250 行以下のデータ セットを複数取得します。 この方法によって、大容量のデータの処理中にサーバの動作が遅くなることを防ぎます。