5 Oracle XQuery for Apache Hadoopの使用
この章では、Oracle XQuery for Apache Hadoop (Oracle XQuery for Hadoop)を使用して大量の半構造化データを抽出および変換する方法について説明します。内容は次のとおりです。
Oracle XQuery for Hadoopとは
Oracle XQuery for Hadoopは、半構造化されたビッグ・データの変換エンジンです。Oracle XQuery for Hadoopでは、XQuery言語で表された変換を一連のMapReduceジョブに解釈して実行します(これらのジョブはApache Hadoopクラスタ上で並列で実行されます)。ユーザーは、スケーラビリティやパフォーマンスを犠牲にせずに、JavaおよびMapReduceの複雑性に取り組むのではなくデータ移動および変換ロジックに集中できます。
入力データは、Hadoop Distributed File System (HDFS)など、Hadoopのファイル・システムAPIを介してアクセス可能なファイル・システムに配置するか、Oracle NoSQL Databaseに格納できます。Oracle XQuery for Hadoopでは、変換結果をHadoopファイル、Oracle NoSQL DatabaseまたはOracle Databaseに書き込むことができます。
また、Oracle XQuery for Hadoopには、大規模なXMLファイルをサポートするためにApache Hiveに対する拡張が用意されています。
Oracle XQuery for Hadoopは、XPath、XQueryおよびXQuery Update Facilityなどの円熟した業界標準に基づいています。他のOracle製品と完全に統合されているため、Oracle XQuery for Hadoopを使用すると、次のことが可能です。
-
Oracle Loader for Hadoopを使用してデータをOracle Databaseに効率的にロードすること。
-
Oracle NoSQL Databaseに読取り/書込みサポートを提供すること。
次の図に、Oracle XQuery for Hadoopを使用したデータ・フローの概要を示します。
Oracle XQuery for Hadoopを使用する前に
Oracle XQuery for HadoopはXQuery開発者が使用するように設計されています。XQueryをよく理解している場合はすぐに開始できます。XQuery初心者は、最初に言語の基本を習得する必要があります。この情報については、このガイドには記載されていません。
例: Hello World!
次のステップに従って、Oracle XQuery for Hadoopを使用して単純な問合せを作成し、実行します。
-
Hello
の行を含むhello.txt
というテキスト・ファイルを現在のディレクトリに作成します。$ echo "Hello" > hello.txt
-
ファイルをHDFSにコピーします。
$ hdfs dfs -copyFromLocal hello.txt
-
次の内容で
hello.xq
という問合せファイルを現在のディレクトリに作成します。import module "oxh:text"; for $line in text:collection("hello.txt") return text:put($line || " World!")
-
問合せを実行します。
$ hadoop jar $OXH_HOME/lib/oxh.jar hello.xq -output ./myout -print 13/11/21 02:41:57 INFO hadoop.xquery: OXH: Oracle XQuery for Hadoop 4.2.0 ((build 4.2.0-cdh5.0.0-mr1 @mr2). Copyright (c) 2014, Oracle. All rights reserved. 13/11/21 02:42:01 INFO hadoop.xquery: Submitting map-reduce job "oxh:hello.xq#0" id="3593921f-c50c-4bb8-88c0-6b63b439572b.0", inputs=[hdfs://bigdatalite.localdomain:8020/user/oracle/hello.txt], output=myout . . .
-
出力ファイルを確認します。
$ hdfs dfs -cat ./myout/part-m-00000 Hello World!
Oracle XQuery for Hadoopの関数について
Oracle XQuery for Hadoopは、ビッグ・データセットに対してcollectionおよびput関数を使用して読取りおよび書込みを実行します。
-
collection関数は、HadoopファイルまたはOracle NoSQL Databaseからデータを項目のコレクションとして読み取ります。Hadoopファイルは、Hadoopのファイル・システムAPIを介してアクセスできるファイルです。Oracle Big Data Applianceおよび大半のHadoopクラスタでは、このファイル・システムはHadoop Distributed File System (HDFS)です。
-
put関数は、Oracle Database、Oracle NoSQL DatabaseまたはHadoopファイルに格納されたデータセットに対して単一の項目を追加します。
次の例は、項目をソースから読み取って別の場所に書き込むOracle XQuery for Hadoopの単純な問合せです。
for $x in collection(...) return put($x)
Oracle XQuery for Hadoopには、特定の形式およびソースについてputおよびcollection関数を定義する際に使用できる一連のアダプタが付属しています。各アダプタには2つのコンポーネントがあります。
-
利便性を考慮して事前定義された一連の組込みputおよびcollection関数。
-
カスタムputおよびcollection関数の定義に使用できる一連のXQuery関数の注釈。
他の共通して使用する関数もOracle XQuery for Hadoopに含まれています。
アダプタについて
次に、Oracle XQuery for Hadoopアダプタについて簡単に説明します。
- Avroファイル・アダプタ
-
Avroファイル・アダプタは、HDFSに格納されたAvroコンテナ・ファイルへのアクセスを提供します。Avroコンテナ・ファイルに対して読取り/書込みを行うcollectionおよびput関数が含まれています。
- JSONファイル・アダプタ
-
JSONファイル・アダプタは、HDFSに格納されたJSONファイルへのアクセスを提供します。JSONファイルを読み取るためのcollection関数とJSONデータを直接解析するための一連のhelper関数が含まれています。出力を書き込むには、別のアダプタを使用する必要があります。
- Oracle Databaseアダプタ
-
Oracle Databaseアダプタは、データをOracle Databaseにロードします。このアダプタは、JDBCまたはOCIを使用してOracleデータベースの表に出力先を指定するためのカスタムput関数をサポートしています。データベースへのライブ接続が使用可能でない場合、このアダプタはデータ・ポンプまたはHDFSのデリミタ付きテキスト・ファイルへの出力もサポートします。ファイルは、SQL*Loaderなどの異なるユーティリティで、または外部表を使用してOracleデータベースにロードできます。このアダプタはデータをデータベースから移動しないため、collection関数やget関数はありません。
サポートされるOracle Databaseのバージョンについては、ソフトウェア要件を参照してください。
- Oracle NoSQL Databaseアダプタ
-
Oracle NoSQL Databaseアダプタは、Oracle NoSQL Databaseに格納されたデータへのアクセスを提供します。データは表、Avro、XML、バイナリXMLまたはテキストとして読取りまたは書込みできます。このアダプタにはcollection、getおよびput関数が含まれています。
- 順序ファイル・アダプタ
-
順序ファイル・アダプタは、Hadoop順序ファイルへのアクセスを提供します。順序ファイルは、キーと値のペアで構成されるHadoop形式です。
このアダプタには、テキスト、XMLまたはバイナリXMLを格納するHDFS順序ファイルに対して読取り/書込みを行うcollectionおよびput関数が含まれています。
- Solrアダプタ
-
Solrアダプタは、フルテキスト索引を作成し、Apache Solrサーバーにロードする機能を提供します。
- テキスト・ファイル・アダプタ
-
テキスト・ファイル・アダプタは、CSVファイルなどのテキスト・ファイルへのアクセスを提供します。テキスト・ファイルに対して読取り/書込みを行うcollectionおよびput関数が含まれています。
JSONファイル・アダプタは、テキスト・ファイルに格納されたJSONオブジェクトに対するサポートを拡張します。
- XMLファイル・アダプタ
-
XMLファイル・アダプタは、HDFSに格納されたXMLファイルへのアクセスを提供します。大規模なXMLファイルを読み取るためのcollection関数が含まれています。出力を書き込むには、別のアダプタを使用する必要があります。
XQuery変換の作成
この章では、Oracle XQuery for Hadoopを使用してXQuery変換を作成する方法について説明します。この項の内容は次のとおりです。
XQuery変換の要件
Oracle XQuery for Hadoopの変換は、次の追加要件に従う必要があることを除き、他のXQuery変換と同様の方法で作成します。
-
主要なXQuery式(問合せ本文)は、次のいずれかの形式で指定する必要があります。
FLWOR1
または
(FLWOR1, FLWOR2,... , FLWORN)
この構文で、FLWORはXQuery FLWOR式のトップレベルのFLWOR (For、Let、Where、Order by、Returnの頭文字)式です。
-
トップレベルの各FLWOR式には、Oracle XQuery for Hadoopの
collection
関数全体を反復するfor
句が必要です。このfor
句には位置指定変数を使用できません。collection
関数については、「Oracle XQuery for Apache Hadoopリファレンス」を参照してください。 -
トップレベルの各FLWOR式には、オプションの
let
、where
およびgroup by
句を使用できます。order by
、count
、window
句など、その他のタイプの句は無効です。 -
トップレベルの各FLWOR式では、Oracle XQuery for Hadoopの
put
関数の呼出しで1つ以上の結果を返す必要があります。put
関数については、「Oracle XQuery for Apache Hadoopリファレンス」を参照してください。 -
問合せ本文は更新式である必要があります。
put
関数はすべて更新関数として分類されるため、Oracle XQuery for Hadoopのすべての問合せは更新問合せとなります。Oracle XQuery for Hadoopでは、
%*:put
注釈は、関数が更新であることを示します。この場合、%updating
注釈またはupdating
キーワードは不要です。関連項目:
-
XQuery 3.1: An XML Query LanguageのFLWOR式に関する項
-
式の更新に関する詳細は、W3C XQuery Update Facility 1.0のXQuery 1.0に対する拡張に関する項
-
XQuery言語のサポートについて
Oracle XQuery for HadoopはW3C XQuery 3.1をサポートしています。ただし次のものを除きます。
-
FLWOR式のwindow句
-
FLWOR式のcount句
-
namespaceコンストラクタ
-
fn:parse-ietf-date
-
fn:transform
-
XQueryの高階関数
言語については、W3CのXQuery 3.1: An XML Query Languageを参照してください。
関数については、W3CのXPath and XQuery Functions and Operatorsを参照してください。
Hadoop分散キャッシュのデータへのアクセス
Hadoop分散キャッシュ機能を使用して補助ジョブ・データにアクセスできます。このメカニズムは、一方が比較的小さいファイルである場合の結合問合せに役立ちます。分散キャッシュからアクセスされるファイルが小さいほど、問合せは高速になります。
ファイルを分散キャッシュに配置するには、Oracle XQuery for Hadoopを呼び出すときに-files
Hadoopコマンドライン・オプションを使用します。分散キャッシュからファイルを読み取る問合せで、XMLの場合はfn:doc
関数を、テキスト・ファイルの場合はfn:unparsed-text
またはfn:unparsed-text-lines
のいずれかを呼び出す必要があります。例5-7を参照してください。
XQueryからのカスタムJava関数の呼出し
Oracle XQuery for Hadoopは、Java言語でカスタム外部関数を実装して拡張できます。Java実装は、パラメータを備えた静的メソッドで、XQuery API for Java (XQJ)仕様に定義されているタイプを返す必要があります。
カスタムJava関数バインディングは、%ora-java:binding
注釈を使用して外部関数定義に注釈を指定することで、Oracle XQuery for Hadoopに定義されます。この注釈の構文は、次のとおりです。
%ora-java:binding("java.class.name[#method]")
%ora-java:binding
の例については、例5-8を参照してください。
カスタムJava関数が格納されているJARファイルはすべて-libjars
コマンドライン・オプションに指定する必要があります。次に例を示します。
hadoop jar $OXH_HOME/lib/oxh.jar -libjars myfunctions.jar query.xq
ユーザー定義のXQueryライブラリ・モジュールおよびXMLスキーマのアクセス
-
Oracle XQuery for Hadoopを呼び出すメインの問合せが存在するクライアント上の同じディレクトリに、ライブラリ・モジュールまたはXMLスキーマ・ファイルを配置します。
-
import module
またはimport schema
文のロケーションURIパラメータを使用してメインの問合せからライブラリ・モジュールまたはXMLスキーマをインポートします。 -
Oracle XQuery for Hadoopを呼び出す場合は、ライブラリ・モジュールまたはXMLスキーマ・ファイルを
-files
コマンドライン・オプションに指定します。
ユーザー定義のXQueryライブラリ・モジュールおよびXMLスキーマの使用例は、例5-9を参照してください。
関連項目:
XQuery 3.1: An XML Query Language のロケーションURIに関する項
XQuery変換の例
これらの例では、HDFSに次のテキスト・ファイルがあります。ファイルには、異なるWebページへのアクセス・ログが格納されます。各行はWebページへのアクセスを表し、時間、ユーザー名、アクセスしたページ、およびステータス・コードが格納されます。
mydata/visits1.log 2013-10-28T06:00:00, john, index.html, 200 2013-10-28T08:30:02, kelly, index.html, 200 2013-10-28T08:32:50, kelly, about.html, 200 2013-10-30T10:00:10, mike, index.html, 401 mydata/visits2.log 2013-10-30T10:00:01, john, index.html, 200 2013-10-30T10:05:20, john, about.html, 200 2013-11-01T08:00:08, laura, index.html, 200 2013-11-04T06:12:51, kelly, index.html, 200 2013-11-04T06:12:40, kelly, contact.html, 200
例5-1 基本的なフィルタ
この問合せは、ユーザーkelly
がアクセスしたページをフィルタ処理し、そのファイルをテキスト・ファイルに書き込みます。
import module "oxh:text"; for $line in text:collection("mydata/visits*.log") let $split := fn:tokenize($line, "\s*,\s*") where $split[2] eq "kelly" return text:put($line)
この問合せは、次の行を含むテキスト・ファイルを出力ディレクトリに作成します。
2013-11-04T06:12:51, kelly, index.html, 200 2013-11-04T06:12:40, kelly, contact.html, 200 2013-10-28T08:30:02, kelly, index.html, 200 2013-10-28T08:32:50, kelly, about.html, 200
例5-2 分類と集計
次の問合せは、ページに対する1日当たりのアクセス数を計算します。
import module "oxh:text"; for $line in text:collection("mydata/visits*.log") let $split := fn:tokenize($line, "\s*,\s*") let $time := xs:dateTime($split[1]) let $day := xs:date($time) group by $day return text:put($day || " => " || fn:count($line))
この問合せは、次の行を含むテキスト・ファイルを作成します。
2013-10-28 => 3 2013-10-30 => 3 2013-11-01 => 1 2013-11-04 => 2
例5-3 内部結合
この例は、他のファイルに加え、HDFSの次のテキスト・ファイルを問い合せます。このファイルには、ユーザーID、姓名、年齢などのユーザー・プロファイル情報がコロン(:)区切りで格納されています。
mydata/users.txt john:John Doe:45 kelly:Kelly Johnson:32 laura:Laura Smith: phil:Phil Johnson:27
次の問合せは、users.txt
とログ・ファイルの結合を実行します。30歳を超えるユーザーが各ページにアクセスした回数を計算します。
import module "oxh:text"; for $userLine in text:collection("mydata/users.txt") let $userSplit := fn:tokenize($userLine, "\s*:\s*") let $userId := $userSplit[1] let $userAge := xs:integer($userSplit[3][. castable as xs:integer]) for $visitLine in text:collection("mydata/visits*.log") let $visitSplit := fn:tokenize($visitLine, "\s*,\s*") let $visitUserId := $visitSplit[2] where $userId eq $visitUserId and $userAge gt 30 group by $page := $visitSplit[3] return text:put($page || " " || fn:count($userLine))
この問合せは、次の行を含むテキスト・ファイルを作成します。
about.html 2 contact.html 1 index.html 4
次の問合せは、任意のページにアクセスした各ユーザーのアクセス数を計算します。ページにアクセスしたことがないユーザーは除外されます。
import module "oxh:text"; for $userLine in text:collection("mydata/users.txt") let $userSplit := fn:tokenize($userLine, "\s*:\s*") let $userId := $userSplit[1] for $visitLine in text:collection("mydata/visits*.log") [$userId eq fn:tokenize(., "\s*,\s*")[2]] group by $userId return text:put($userId || " " || fn:count($visitLine))
この問合せは、次の行を含むテキスト・ファイルを作成します。
john 3 kelly 4 laura 1
ノート:
2つのcollection関数の結果を結合する場合は、等価結合のみがサポートされます。ソースの一方または両方がcollection
関数からのソースでない場合は、任意の結合条件が許可されます。
例5-4 左外部結合
この例は例5-3の2番目の問合せと類似していますが、ページにアクセスしなかったユーザーもカウントします。
import module "oxh:text"; for $userLine in text:collection("mydata/users.txt") let $userSplit := fn:tokenize($userLine, "\s*:\s*") let $userId := $userSplit[1] for $visitLine allowing empty in text:collection("mydata/visits*.log") [$userId eq fn:tokenize(., "\s*,\s*")[2]] group by $userId return text:put($userId || " " || fn:count($visitLine))
この問合せは、次の行を含むテキスト・ファイルを作成します。
john 3 kelly 4 laura 1 phil 0
例5-5 セミ結合
次の問合せは、ページにアクセスしたユーザーを検出します。
import module "oxh:text"; for $userLine in text:collection("mydata/users.txt") let $userId := fn:tokenize($userLine, "\s*:\s*")[1] where some $visitLine in text:collection("mydata/visits*.log") satisfies $userId eq fn:tokenize($visitLine, "\s*,\s*")[2] return text:put($userId)
この問合せは、次の行を含むテキスト・ファイルを作成します。
john kelly laura
例5-6 複数の出力
次の問合せは、コードが401のWebページ・アクセスを検索し、XQueryのtext:trace()
関数を使用してtrace*
ファイルに書き込みます。残りのアクセス・レコードはデフォルトの出力ファイルに書き込みます。
import module "oxh:text"; for $visitLine in text:collection("mydata/visits*.log") let $visitCode := xs:integer(fn:tokenize($visitLine, "\s*,\s*")[4]) return if ($visitCode eq 401) then text:trace($visitLine) else text:put($visitLine)
この問合せは、次の行を含むtrace*
テキスト・ファイルを生成します。
2013-10-30T10:00:10, mike, index.html, 401
この問合せは、次の行を含むデフォルトの出力ファイルも生成します。
2013-10-30T10:00:01, john, index.html, 200 2013-10-30T10:05:20, john, about.html, 200 2013-11-01T08:00:08, laura, index.html, 200 2013-11-04T06:12:51, kelly, index.html, 200 2013-11-04T06:12:40, kelly, contact.html, 200 2013-10-28T06:00:00, john, index.html, 200 2013-10-28T08:30:02, kelly, index.html, 200 2013-10-28T08:32:50, kelly, about.html, 200
例5-7 補助入力データのアクセス
次の問合せは例5-3の2番目の問合せの代替バージョンですが、fn:unparsed-text-lines
関数を使用してHadoop分散キャッシュのファイルにアクセスします。
import module "oxh:text"; for $visitLine in text:collection("mydata/visits*.log") let $visitUserId := fn:tokenize($visitLine, "\s*,\s*")[2] for $userLine in fn:unparsed-text-lines("users.txt") let $userSplit := fn:tokenize($userLine, "\s*:\s*") let $userId := $userSplit[1] where $userId eq $visitUserId group by $userId return text:put($userId || " " || fn:count($visitLine))
問合せを実行するhadoop
コマンドには、Hadoopの-files
オプションを使用する必要があります。「Hadoop分散キャッシュのデータへのアクセス」を参照してください。
hadoop jar $OXH_HOME/lib/oxh.jar -files users.txt query.xq
この問合せは、次の行を含むテキスト・ファイルを作成します。
john 3 kelly 4 laura 1
例5-8 XQueryからのカスタムJava関数の呼出し
次の問合せは、java.lang.String#format
メソッドを使用して入力データを書式設定します。
import module "oxh:text"; declare %ora-java:binding("java.lang.String#format") function local:string-format($pattern as xs:string, $data as xs:anyAtomicType*) as xs:string external; for $line in text:collection("mydata/users*.txt") let $split := fn:tokenize($line, "\s*:\s*") return text:put(local:string-format("%s,%s,%s", $split))
この問合せは、次の行を含むテキスト・ファイルを作成します。
john,John Doe,45 kelly,Kelly Johnson,32 laura,Laura Smith, phil,Phil Johnson,27
関連項目:
クラス文字列については、Java Platform Standard Edition 7 API Specification。
例5-9 ユーザー定義のXQueryライブラリ・モジュールおよびXMLスキーマの使用
この例では、mytools.xq
というライブラリ・モジュールを使用します。
module namespace mytools = "urn:mytools"; declare %ora-java:binding("java.lang.String#format") function mytools:string-format($pattern as xs:string, $data as xs:anyAtomicType*) as xs:string external;
次の問合せは前の例と同等ですが、string-format関数をmytools.xq
ライブラリ・モジュールから呼び出します。
import module namespace mytools = "urn:mytools" at "mytools.xq"; import module "oxh:text"; for $line in text:collection("mydata/users*.txt") let $split := fn:tokenize($line, "\s*:\s*") return text:put(mytools:string-format("%s,%s,%s", $split))
この問合せは、次の行を含むテキスト・ファイルを作成します。
john,John Doe,45 kelly,Kelly Johnson,32 laura,Laura Smith, phil,Phil Johnson,27
例5-10 Try/Catch式を使用したダーティ・データのフィルタリング
XQueryのtry/catch式は、入力データが予期しない形式である、破損しているあるいは失われている場合に広く対応するために使用できます。 次の問合せでは、ユーザー名とユーザーの年齢が含まれた入力ファイルages.txtを読み込みます。
USER AGE
------------------
john 45
kelly
laura 36
phil OLD!
ファイルの最初の2行にヘッダー・テキストが含まれ、Kellyの年齢のエントリがなく、Philの年齢のエントリがダーティな値であることに注目してください。 この問合せは、ファイルにある各ユーザーについて、ユーザー名とそのユーザーが40歳以上かどうかを書き出します。
import module "oxh:text";
for $line in text:collection("ages.txt")
let $split := fn:tokenize($line, "\s+")
return
try {
let $user := $split[1]
let $age := $split[2] cast as xs:integer
return
if ($age gt 40) then
text:put($user || " is over 40")
else
text:put($user || " is not over 40")
} catch * {
text:trace($err:code || " : " || $line)
}
この問合せは、次の行を含むテキスト出力ファイルを生成します。
john is over 40
laura is not over 40
この問合せは、次の行を含むtrace*ファイルも作成します。
err:FORG0001 : USER AGE
err:XPTY0004 : ------------------
err:XPTY0004 : kelly
err:FORG0001 : phil OLD!
問合せの実行
問合せを実行するには、hadoop jar
コマンドを使用してoxh
ユーティリティを呼び出します。基本的な構文は次のとおりです。
hadoop jar $OXH_HOME/lib/oxh.jar [generic options] query.xq -output directory [-clean] [-ls] [-print] [-sharelib
hdfs_dir][-skiperrors] [-version]
Oracle XQuery for Hadoopのオプション
- query.xq
-
XQueryファイルを識別します。「XQuery変換の作成」を参照してください。
- -clean
-
問合せの実行前に、出力ディレクトリからすべてのファイルを削除します。デフォルト・ディレクトリを使用する場合、Oracle XQuery for Hadoopはこのオプションが省略されている場合でも常にディレクトリを空にします。
- -exportliboozie directory
-
Oracle XQuery for Hadoopの依存関係を指定されたディレクトリにコピーします。このオプションは、Oracle XQuery for HadoopをHadoop分散キャッシュおよびOozie共有ライブラリに追加する場合に使用します。外部依存関係もコピーされるため、
KVHOME
、OLH_HOME
およびOXH_SOLR_MR_HOME
などの環境変数が関連アダプタ(Oracle NoSQL Database、Oracle DatabaseおよびSolr)で使用するように設定されていることを確認します。 - -ls
-
問合せ実行後に、出力ディレクトリの内容をリスト表示します。
- -output directory
-
問合せの出力ディレクトリを指定します。ファイル・アダプタのput関数によって、このディレクトリにファイルが作成されます。書き込まれた値は、1つ以上のファイルに展開されます。作成されるファイル数は、問合せがどのように複数のタスクに分散されているかによって異なります。デフォルトの出力ディレクトリは
/tmp/oxh-
user_name
/output
です。put関数の説明は、「Oracle XQuery for Hadoopの関数について」を参照してください。
-
出力ディレクトリ内の全ファイルの内容を標準出力(画面)に印刷します。Avroファイルの印刷時は、各レコードがJSONテキストとして印刷されます。
- -sharelib hdfs_dir
-
Oracle XQuery for Hadoopおよびサードパーティ・ライブラリが含まれているHDFSフォルダの場所を指定します。
- -skiperrors
-
エラーで処理が停止しないように、エラー・リカバリをオンに切り替えます。
問合せ処理中に発生したすべてのエラーがカウントされ、問合せ終了時に合計がログに記録されます。また、タスクごとに最初の20件のエラーのエラー・メッセージがログに記録されます。次の構成プロパティを参照してください。
- -version
-
Oracle XQuery for Hadoopのバージョンを表示し、問合せを実行せずに終了します。
汎用オプション
任意の汎用的なhadoop
コマンドライン・オプションを指定できます。Oracle XQuery for Hadoopは、org.apache.hadoop.util.Tool
インタフェースを実装し、MapReduceアプリケーションを構築する標準的なHadoopの方法に従います。
Oracle XQuery for Hadoopでは、次の汎用オプションが一般的に使用されます。
- -conf job_config.xml
-
ジョブ構成ファイルを識別します。「Oracle XQuery for Hadoopの構成プロパティ」を参照してください。
Oracle DatabaseまたはOracle NoSQL Databaseのアダプタを使用している場合は、このファイルに様々なジョブ・プロパティを設定できます。「Oracle Loader for Hadoop構成プロパティおよび対応する%oracle-property注釈」および「Oracle NoSQL Databaseアダプタの構成プロパティ」を参照してください。
- -D property=value
-
構成プロパティを識別します。「Oracle XQuery for Hadoopの構成プロパティ」を参照してください。
- -files
-
分散キャッシュに追加するファイルのカンマ区切りリストを指定します。「Hadoop分散キャッシュのデータへのアクセス」を参照してください。
関連項目:
汎用オプションの詳細は、次のサイトを参照してください。
ローカルでの問合せの実行について
問合せの開発では、問合せをクラスタに送信する前に、ローカルで実行できます。ローカル実行を使用することで、小さいデータセットで問合せが動作する様子を確認し、潜在的な問題を迅速に診断できます。
ローカル・モードでは、HDFSではなくローカル・ファイル・システムに対して相対的なURIで解決し、問合せをシングル・プロセスで実行します。
問合せをローカル・モードで実行するには、次の手順を実行します。
-
Hadoopの
-jt
および-fs
汎用引数をlocal
に設定します。この例では、「例: Hello World!」に記載されている問合せをローカル・モードで実行します。$ hadoop jar $OXH_HOME/lib/oxh.jar -jt local -fs local ./hello.xq -output ./myoutput -print
-
問合せのローカル出力ディレクトリ内の結果ファイルを、この例のようにして確認します。
$ cat ./myoutput/part-m-00000 Hello World!
Apache Oozieからの問合せの実行
Apache Oozieは、複数のMapReduceジョブを指定した順番に(およびオプションで予定された時間に)実行するワークフロー・ツールです。Oracle XQuery for Hadoopは、OozieワークフローからのOracle XQuery for Hadoopの問合せの実行に使用できるOozieアクション・ノードを提供します。
サポートされているXML要素
Oracle XQuery for Hadoopアクションにより、OozieのJavaアクションが拡張されます。このアクションでは、Javaアクションと同じ構文およびセマンティクスを持つ次のオプションの子XML要素がサポートされます。
-
archive
-
configuration
-
file
-
job-tracker
-
job-xml
-
name-node
-
prepare
関連項目:
Javaアクションは、次のサイトのOozie仕様で説明されています。
https://oozie.apache.org/docs/4.0.0/WorkflowFunctionalSpec.html#a3.2.7_Java_Action
さらに、Oracle XQuery for Hadoopアクションでは、次の要素がサポートされています。
-
script
: Oracle XQuery for Hadoop問合せファイルの場所。必須。問合せファイルはワークフロー・アプリケーション・ディレクトリに置く必要があります。相対パスはアプリケーション・ディレクトリに対して解決されます。
例:
<script>myquery.xq</script>
-
output
: 問合せの出力ディレクトリ。必須。output
要素にはオプションのclean
属性があります。この属性をtrue
に設定し、出力ディレクトリを削除してから問合せを実行します。出力ディレクトリがすでに存在し、clean
属性が設定されていないかfalse
に設定されている場合、エラーが発生します。ジョブを実行しているときは出力ディレクトリは存在できません。例:
<output clean="true">/user/jdoe/myoutput</output>
問合せ句の実行時に発生したあらゆるエラーによって、Oozieではそのアクションに対するエラー遷移が実行されます。
例: Hello World
この例では、次のファイルを使用します。
-
workflow.xml
:hello.xq
にある問合せの2つの構成値(HDFSファイルおよび文字列World!
)を設定するOozieアクションの情報を表示します。HDFS入力ファイルは
/user/jdoe/data/hello.txt
で、次の文字列が含まれています。Hello
例5-11を参照してください。
-
hello.xq
: Oracle XQuery for Hadoopを使用して問合せを実行します。例5-12を参照してください。
-
job.properties
: Oozieのジョブ・プロパティをリストします。例5-13を参照してください。
例を実行するには、このコマンドを使用します。
oozie job -oozie http://example.com:11000/oozie -config job.properties -run
ジョブを実行した後、/user/jdoe/myoutput
出力ディレクトリには、テキスト"Hello World!"を含むファイルが置かれます。
例5-11 Hello Worldのworkflow.xmlファイル
このファイルは/user/jdoe/hello-oozie-oxh/workflow.xml
という名前です。job.properties
ファイルに定義された変数を使用します。
<workflow-app xmlns="uri:oozie:workflow:0.4" name="oxh-helloworld-wf"> <start to="hello-node"/> <action name="hello-node"> <oxh xmlns="oxh:oozie-action:v1"> <job-tracker>${jobTracker}</job-tracker> <name-node>${nameNode}</name-node> <!-- The configuration can be used to parameterize the query. --> <configuration> <property> <name>myinput</name> <value>${nameNode}/user/jdoe/data/src.txt</value> </property> <property> <name>mysuffix</name> <value> World!</value> </property> </configuration> <script>hello.xq</script> <output clean="true">${nameNode}/user/jdoe/myoutput</output> </oxh> <ok to="end"/> <error to="fail"/> </action> <kill name="fail"> <message>OXH failed: [${wf:errorMessage(wf:lastErrorNode())}]</message> </kill> <end name="end"/> </workflow-app>
例5-12 Hello Worldのhello.xq ファイル
このファイルは/user/jdoe/hello-oozie-oxh/hello.xq
という名前です。
import module "oxh:text"; declare variable $input := oxh:property("myinput"); declare variable $suffix := oxh:property("mysuffix"); for $line in text:collection($input) return text:put($line || $suffix)
例5-13 Hello Worldのjob.propertiesファイル
oozie.wf.application.path=hdfs://example.com:8020/user/jdoe/hello-oozie-oxh nameNode=hdfs://example.com:8020 jobTracker=hdfs://example.com:8032 oozie.use.system.libpath=true
Oracle XQuery for Hadoopの構成プロパティ
Oracle XQuery for Hadoopでは、構成プロパティを指定する汎用メソッドをhadoop
コマンドで使用します。構成ファイルを指定する場合は-conf
オプションを使用し、個別のプロパティを指定する場合は-D
オプションを使用します。「問合せの実行」を参照してください。
プロパティ | 説明 | ||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
oracle.hadoop.xquery.lib.share |
型: String デフォルト値: 定義されていません。 説明: Oracle XQuery for Hadoopのライブラリおよびサードパーティ・ソフトウェアを含むHDFSディレクトリを特定します。次に例を示します。 http://path/to/shared/folder すべてのHDFSファイルは同じディレクトリに置く必要があります。 または、コマンドラインで パターン一致: ディレクトリ名にパターン一致文字を使用できます。複数のディレクトリのパターンが一致した場合、変更のタイムスタンプが最新のディレクトリが使用されます。 ディレクトリ名を指定するには、英数字を使用し、オプションで次のパターン一致の特殊文字を使用します。
Oozieライブラリ: 値 |
||||||||||||||||||
oracle.hadoop.xquery.output |
型: String デフォルト値: 説明: 問合せの出力ディレクトリを設定します。このプロパティは、 |
||||||||||||||||||
oracle.hadoop.xquery.scratch |
型: String デフォルト値: 説明: 一時ファイルを格納するために、Oracle XQuery for HadoopのHDFS一時ディレクトリを設定します。 |
||||||||||||||||||
oracle.hadoop.xquery.timezone |
型: String デフォルト値: クライアント・システムのタイムゾーン 説明: XQueryの暗黙的なタイムゾーンで、date、timeまたはdatetime値にタイムゾーンがない場合に、比較または算術の操作に使用されます。値はJava
|
||||||||||||||||||
oracle.hadoop.xquery.skiperrors |
型: Boolean デフォルト値: 説明: エラー・リカバリをオンにする場合は |
||||||||||||||||||
oracle.hadoop.xquery.skiperrors.counters |
型: Boolean デフォルト値: 説明: エラー・コード別にエラーを分類する場合は |
||||||||||||||||||
oracle.hadoop.xquery.skiperrors.max |
型: Integer デフォルト値: Unlimited 説明: 単一のMapReduceタスクがリカバリできるエラーの最大数を設定します。 |
||||||||||||||||||
oracle.hadoop.xquery.skiperrors.log.max |
型: Integer デフォルト値: 20 説明: 単一のMapReduceタスクでログに記録するエラーの最大数を設定します。 |
||||||||||||||||||
log4j.logger.oracle.hadoop.xquery |
型: String デフォルト値: 定義されていません。 説明: 指定のしきい値レベルでタスクごとに |