web-dev-qa-db-ja.com

Hadoop MapReduceは、ネストされたディレクトリをジョブ入力として提供します

複数のレベルのファイルを含む、ネストされたディレクトリ構造を処理するジョブに取り組んでいます。

_one/
├── three/
│   └── four/
│       ├── baz.txt
│       ├── bleh.txt
│       └── foo.txt
└── two/
    ├── bar.txt
    └── gaa.txt
_

入力パスとして_one/_を追加すると、ルートレベルですぐに使用できるファイルがないため、ファイルは処理されません。

job.addInputPathRecursively(..)について読みましたが、これは最近のリリースでは非推奨になっているようです(hadoop 1.0.2を使用しています)。フォルダをウォークし、job.addInputPath(dir)を使用して各ディレクトリを追加するコードをいくつか作成しました。これは、ディレクトリを入力ファイルとして処理しようとしたときにジョブがクラッシュするまで機能しました。 -fs.open(split.getPath())がディレクトリの場合、split.getPath()を試行します(これは_LineRecordReader.Java_内で発生します)。

ネストされたディレクトリ構造でジョブを提供するためのより簡単な方法が必要であると自分自身に確信させようとしています。何か案は?

[〜#〜] edit [〜#〜]-これには 未解決のバグ があるようです。

22
sa125

これに関するドキュメントは見つかりませんでしたが、*/*動作します。っていうことは -input 'path/*/*'

14
Cheng

import org.Apache.hadoop.mapreduce.lib.input.FileInputFormat;

FileInputFormat.setInputDirRecursive(job、true);

いいえ、雷鋒と呼んでください。

7
backingwu

distcpなどからのログファイルが残っている可能性があるため、データを再帰的に処理することは危険である可能性があります。別の方法を提案させてください。

コマンドラインで再帰的にウォークを実行してから、スペースで区切られたパラメーターのパスをMapReduceプログラムに渡します。 argvからリストを取得します。

$ hadoop jar blah.jar "`hadoop fs -lsr recursivepath | awk '{print $8}' | grep '/data.*\.txt' | tr '\n' ' '`"

長いバッシュで申し訳ありませんが、それは仕事を成し遂げます。物事をbashスクリプトでラップして、物事を変数に分割することができます。

私は個人的にmapreduceジョブを作成するためのpass-in-filepathアプローチが好きなので、コード自体にハードコードされたパスがなく、より複雑なファイルのリストに対して実行するように設定するのは比較的簡単です。

4
Donald Miner

それでも関連性があるかどうかはわかりませんが、少なくともhadoop 2.4.0では、プロパティmapreduce.input.fileinputformat.input.dir.recursivetrueに設定できます。あなたの問題。

2
Eitan Illuz