Google App Engineで1000件以上の大量データを取得する方法
Google App Engine for JAVAのBig Tableは
AppEngineの制約で1度のクエリーで1000件しか取ってこれない。
offset、limitをループでまわして取ってこようと思ったんだけど、
Datastore.query(meta).offset(30000).limit(1000).asList();
みたいな感じで大量データの中から1000件取る処理をすると内部では
31000件までを取得して30000件までのデータを破棄する・・・という
処理が行われているみたいなのでCancelledExceptionなるものが発生。
たぶんCPU使用時間オーバーとかでDataStoreへの
アクセスが強制終了したのかと。
色々探しても見つからなかったので、ゴリ押しで解決!
一度対象のKeyオブジェクトだけ全部取得して、
そこから分けてDataStoreにアクセス。
以下はSlim3での実装方法・・・。
# 職場で作ったのを思い出して書いたので
# 少し間違ってるかも。
# あとまだ検証途中なので取得対象が超膨大だと動かないかも。。。
// 取得したい件数
int getCount = 10000;
// DataStoreから1度に取得する件数
int base = 2500;
// DataStoreに問い合わせる回数
int loopCount = getCount / base;
// 対象のKEYを全部取得
ListkeyList = Datastore.query(meta).filter(filters).asKeyList();
// Keyを分割したリスト
Listint offset = 0;
boolean breakFlag = false;
for (int i = 0; i < loopCount; i++) {
int limit = (i + 1) * base;
if (keyList.size() <= limit) {
limit = keyList.size();
breakFlag = true;
}
readList.add(keyList.subList(offset, limit));
offset += base;
if (breakFlag) {break;}
}for (List
keySplitList : readList) {
resultItems.addAll(Datastore.get(Entity.class, keySplitList));
}
Google App Engineは色々トラブルがありすぎて嫌いになりそうだ。
>追記
このやり方だと大量データの場合ダメでした。。。
解決方法はこっちの記事を!