# XMLQUERY演算子

XMLQUERYはSQLにてXMLの値を問い合わせることができるSQL/XML演算子です。

XMLQUERY演算子には二つの引数があります。片方はXML問合せ式で、もう一つはDerbyXML値です。

#### 構文

    XMLQUERY ( xquery文字列リテラル
        PASSING BY REF xml値式
        [ RETURNING SEQUENCE [ BY REF ] ]
        EMPTY ON EMPTY
        )

`xquery文字列リテラル`
  文字列のリテラルが指定されなければなりません。もし引数にパラメータが与えられたり、リテラルではない式が与えられたり、文字列ではない(整数のような)リテラルが与えられた場合、Derbyはエラーを挙げます。 引数の`xquery文字列リテラル`は、Apache XalanがサポートするXPath式でなければなりません。DerbyはどのようなXML問合せ式を評価するでもApache Xalanを利用します。XalanはXQueryを完全にサポートしないので、Derbyも同様に完全にサポートしません。 もしXalanが問合せのコンパイルや実行を行えなかった場合、DerbyはXalanが挙げたエラーを補足して、SQLExceptionとして挙げなおします。 XPathおよびXQuery式の詳細については、次のWebサイトを参照してください。http://www.w3.org/TR/xpathとhttp://www.w3.org/TR/xquery/
`xml値式`
  これはXMLの値でなければならず、また整形式のSQL/XML文書でなければなりません。 `xml値式`はパラメータであってはなりません。 Derbyは暗黙の構文解析や、XML値への変換を行わないので、文字列やその他のデータ型を使うとエラーとなります。 もし引数がDerbyのXMLQUERY演算子により返る並びであった場合、もしその並びが一つの文書ノードであるノードからなる並びであれば、引数にとる事ができます。そうではなければ、Derbyはエラーを挙げます。
BY REF
  この省略可能なキーワードにより、Derbyにて可能な引数渡しの仕組みが記述されます。BY REFは規定の引数渡しの仕組みなので、このキーワードのあるなしにかかわらず、XMLQUERY演算子は同様に振舞います。引数渡しの仕組みについてのより詳細な情報は、SQL/XML仕様を参照してください。
RETURNING SEQUENCE
  省略可能なこのキーワードにより、DerbyのXMLQUERY演算子にて唯一返すことのできるXMLの種類を記述します。SEQUENCEは既定の返却値の種類なので、このキーワードのあるなしにかかわらず、XMLQUERY演算子は同様に振舞います。他のXML返却値の種類についてのより詳細な情報は、SQL/XML仕様を参照してください。
EMPTY ON EMPTY
  省略できないこのキーワードにより、XMLQUERY演算子の結果が空の並びであった時の振る舞いが記述されます。XMLQUERY演算子は空の並びをそのまま返します。XMLQUERY演算子はnull値に変換しません。空の並びは直列化されると空文字列になります。Derbyは、空の並びを整形式のXML文書としません。

XMLQUERY演算子の結果は、XML型の値です。 結果はXMLノードや値の並びを表します。文字列のような値は、結果の並びの一部となることができます。XMLQUERY演算子の結果は整形式のXML文書であることが保障されず、XML列にXMLQUERY演算子の結果を挿入できないことがあります。 XML列に結果を記録するためには、その結果は唯一つの項目を持つ並びで、その項目が整形式の文書ノードでなければなりません。 結果はXMLSERIALIZE 演算子によって直列化することによってのみ見られるようにできます。

#### 例

`x_table`表にて、`xcol`というXML列を検索して、age属性が20より大きいstudents要素を返すには次の文を書きます。

    SELECT ID,
        XMLSERIALIZE(
            XMLQUERY('//student[@age>20]' PASSING BY REF xcol EMPTY ON EMPTY)
        AS VARCHAR(50))
    FROM x_table

この問合せでは、XMLQUERY演算子が実際に結果を返すか否かにかかわらず、結果には`x_table`の全行毎に結果行があります。
`x_table`表にて`xcol`というXML列を検索して、BCという名前の生徒の年齢を返すには、次の文を書きます。

    SELECT ID,
        XMLSERIALIZE(
            XMLQUERY('string(//student[text() = "BC"]/@age)' PASSING BY REF xcol EMPTY ON EMPTY)
        AS VARCHAR(50))
    FROM x_table
    WHERE
        XMLEXISTS('//student[text() = "BC"]' PASSING BY REF xcol)

この問合せでは結果には、`x_table`中のBCという名前の生徒の行のみあります。

#### 利用上の覚書

DerbyはXMLの機能を動作させるために、Apache XercesのようなJAXP構文解析器とApache XalanがJavaのクラスパスに記述されている必要があります。JAXP構文解析器、Xalanの何れかがクラスパスに記述されていない場合に、XMLQUERY演算子を利用しようとするとエラーが発生します。

親トピック: 組み込み関数