SHOEISHA iD

※旧SEメンバーシップ会員の方は、同じ登録情報(メールアドレス&パスワード)でログインいただけます

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

初めてのHBase

HBaseを使って簡易ブログサービスを作ってみよう

初めてのHBase 第3回


  • X ポスト
  • このエントリーをはてなブックマークに追加

Get

 次はGetです。GetはHBaseからRow単位のデータを取得するAPIです。以下が、Getのコードになります。

byte[] fam = Bytes.toBytes("fam");
byte[] row = Bytes.toBytes("row");
byte[] col1 = Bytes.toBytes("col1");
byte[] col2 = Bytes.toBytes("col2");

// Getオブジェクトを生成する際にRowKeyを指定
Get get = new Get(row);

// データをGetする
Result result = table.get(get);

System.out.println(Bytes.toString(result.getValue(fam, col1))); // val1
System.out.println(Bytes.toString(result.getValue(fam, col2))); // val2

 ResultオブジェクトはRow単位の結果です。getValueでValueを取得しています。今回は省略しますが、ResultはgetValue以外にもさまざまなデータの取得メソッドが用意されています。

 以下のようにColumnFamilyを限定することで、I/Oの切り分けが可能になります。

// ColumnFamilyを限定
get.addFamily(fam);

 取得するColumnを限定したい場合は、以下のようにします。

// Columnを限定
get.addColumn(fam, col1);

 複数バージョンを取得したい場合は、以下のようにします。デフォルトは1なので最新バージョンのみ取得します。

// 3バージョン取得
get.setMaxVersions(3);

 また、以下のメソッドを用いることで、特定のTimestampやその範囲を指定して取得できます。

// Timestamp指定
get.setTimeStamp(ts);

// Timestampの範囲を指定
get.setTimeRange(minTs, maxTs);

Delete

 次はDeleteです。

byte[] row = Bytes.toBytes("row");

Delete delete = new Delete(row);
table.delete(delete);

 上記のコードでは、RowKeyが"row"のRowをまるごと削除しています。削除の範囲を特定のColumnFamilyに絞りたい場合は、以下のようにします。

delete.deleteFamily(fam);

 次に、削除の範囲を特定のColumnに絞りたい場合は、以下のようにします。

delete.deleteColumns(fam, col1);

 削除の範囲を特定のColumnで最新のバージョンに絞りたい場合は、以下のようにします。

delete.deleteColumn(fam, col1);

batchとRowMutations

 複数の処理を一度に行いたい場合に、batchとRowMutationsがあります。batchは複数Rowに対する操作を、RowMutationsは単一Rowに対する操作を一度に行うことができます。

 batchの例は以下のようになります。PutとDeleteを一度に行っています。

byte[] row1 = Bytes.toBytes("row1");
byte[] row2 = Bytes.toBytes("row2");
byte[] fam = Bytes.toBytes("fam");
byte[] col1 = Bytes.toBytes("col1");
byte[] val1 = Bytes.toBytes("val1");
byte[] row3 = Bytes.toBytes("row3");

Put put1 = new Put(row1);
put.add(fam, col1, val1);

Put put2 = new Put(row2);
put.add(fam, col1, val1);
    
Delete delete = new Delete(row3);

List<Row> actions = new ArrayList<Row>();
actions.add(put1);
actions.add(put2);
actions.add(delete);

// バッチ処理
table.batch(actions);

 また、以下のように、複数のGetもbatchによって一度に行うことができます。

byte[] row1 = Bytes.toBytes("row1");
byte[] row2 = Bytes.toBytes("row2");
byte[] fam = Bytes.toBytes("fam");
byte[] col = Bytes.toBytes("col");

Get get1 = new Get(row1);
Get get2 = new Get(row2);

List<Row> actions = new ArrayList<Row>();
actions.add(get1);
actions.add(get2);

// バッチ処理
Object[] results = table.batch(actions);

System.out.println(((Result) results[0]).getValue(fam, col)); // get1の結果
System.out.println(((Result) results[1]).getValue(fam, col)); // get2の結果

 batchの結果としてObjectの配列が返ってきますが、actionsに指定した操作の結果が入っています。Getの結果としてはResultオブジェクトが返ってくるので、キャストして使用することができます。

 RowMutationsの例は以下のようになります。この処理はアトミックに行われます。

byte[] fam = Bytes.toBytes("fam");
byte[] row = Bytes.toBytes("row");

byte[] col1 = Bytes.toBytes("col1");
byte[] val1 = Bytes.toBytes("val1");

byte[] col2 = Bytes.toBytes("col2");

RowMutations rm = new RowMutations(row);

Put put = new Put(row);
put.add(fam, col1, val1);
rm.add(put);

Delete delete = new Delete(row);
delete.deleteColumns(fam, col2);
rm.add(delete);

// バッチ処理(アトミックに処理される)
table.mutateRow(rm);

 上記のコードでは、PutとDeleteがアトミックに行われます。

Scan

 Scanは複数Rowにまたがったデータを取得するAPIで、カーソルのような操作を行うことができます。

byte[] fam = Bytes.toBytes("fam");
byte[] col = Bytes.toBytes("col");
byte[] startRow = Bytes.toBytes("row1");
byte[] stopRow = Bytes.toBytes("row5");

Scan scan = new Scan();
scan.setStartRow(startRow);
scan.setStopRow(stopRow);

// ResultScannerを取得
ResultScanner scanner = table.getScanner(scan);

for (Result result : scanner) {
  // 各RowのValueを取得
  byte[] value = result.getValue(fam, col);
}

// 最後にclose
scanner.close();

 Scanオブジェクトを生成し、ScanしたいRowのstartRowとstopRowを指定しています。stopRowはScanする対象に含まれないので注意してください。

 生成したScanオブジェクトをHTableのgetScannerに渡すことで、ResultScannerオブジェクトが返ってきます。

 ResultScannerはIterableを実装しているので拡張forに渡すことができ、結果のResultオブジェクトを受け取ることができます。

 scannerは使い終わったらcloseします。

 ScanはResultScannerを取得した時点のデータが取れることが保証されています。

 つまり、ResultScannerを取得した後にデータが変更されても、変更前のデータが取得できます。

 ScanもGetと同様、ColumnFamilyやColumnを限定したり、バージョン数やTimestampの指定やその範囲の指定ができます。

// ColumnFamilyを限定
scan.addFamily(fam);

// Columnを限定
scan.addColumn(fam, col1);

// 3バージョン取得
scan.setMaxVersions(3);

// Timestamp指定
scan.setTimeStamp(ts);

// Timestampの範囲を指定
scan.setTimeRange(minTs, maxTs);

次のページ
Filter

修正履歴

この記事は参考になりましたか?

  • X ポスト
  • このエントリーをはてなブックマークに追加
初めてのHBase連載記事一覧

もっと読む

この記事の著者

鈴木 俊裕(スズキ トシヒロ)

株式会社サイバーエージェント アメーバ事業本部 Ameba Technology Laboratory 2008年4月に株式会社サイバーエージェントに新卒で入社。基盤システムの開発・運用に従事する。 2010年4月にHadoop/Hiveを用いたログ解析基盤の開発・運用を担当する。 2011年4月に、ログ解析、レコメンド、検索エンジンなどを開発するAmeba Technology Laboratoryの立ち上げメンバーとなる。 2011年10月からHBaseを用...

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

この記事は参考になりましたか?

この記事をシェア

  • X ポスト
  • このエントリーをはてなブックマークに追加
CodeZine(コードジン)
https://codezine.jp/article/detail/7128 2013/09/24 19:02

おすすめ

アクセスランキング

アクセスランキング

イベント

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

新規会員登録無料のご案内

  • ・全ての過去記事が閲覧できます
  • ・会員限定メルマガを受信できます

メールバックナンバー

アクセスランキング

アクセスランキング