Amazon Web Services ブログ
Amazon EMR のサイズ変更とオートスケーリングのベストプラクティス
Amazon EMR で利用可能な動的なスケーリング機能を利用することで、費用を節約することができます。 クラスタ内のノード数を即座に増やしたり減らしたりスケールする機能は、Amazon EMR を弾力的にする主要な機能の1つです。 EMR のスケーリング機能を使うことで,負荷がほとんどまたはまったくない時にクラスターのサイズを小さく変更することができます。 また、ジョブが非常に遅くなった場合に処理能力を追加するために、クラスターのサイズを大きくすることもできます。 これによりあなたのジョブを少し余裕を持たせた上でカバーするのに必要十分なコストを使うことが出来ます。
この機能の背後にある複雑なロジックを知ることで、クラスタのコストを節約することができます。この記事では、EMR クラスターのサイズをどのように変更するかを詳しく説明し、この機能を使用してあなたのクラスタのコストを削減し最大限のメリットを得るためのベストプラクティスを紹介します。
EMR スケーリングは、単にノードをクラスタに追加または削除するより複雑です。よくある誤解の1つは、Amazon EMR のスケーリングは Amazon EC2 のスケーリングとまったく同じように動くということです。 EC2 スケーリングを使用すると、ノードをほぼ即時に、かつ心配なく追加/削除できますが、EMR では複雑さが増します(特にクラスタを縮小する場合)。これは重要なデータがノード上にあったり,ジョブがノード上で実行していたりする可能性があるためです。
データロストを防ぐため、Amazon EMR スケーリングでは、実行中の Apache Hadoop タスクや、ノードを削除する前に失われる可能性のある一意のデータがノードに存在しないことが保証されます。 EMR クラスタのサイズ変更する際にはデコミッションの遅延を考慮する必要があります。このプロセスがどのように機能するかを理解することによって、遅いクラスタのサイズ変更や非効率なオートスケーリングのポリシーなど、他の人が悩まされていた問題を回避できます。
EMR クラスタが縮小されると、終了するノードで2つの異なるデコミッションプロセスがトリガされます。最初のプロセスは、Hadoop リソースマネージャである Hadoop YARN のデコミッションです。 Amazon EMR にサブミットされる Hadoop タスクは一般的に YARN を通じて実行されるため、EMR はノードを削除する前に実行中の YARN タスクが完了していることを保証する必要があります。何らかの理由で YARN タスクがスタックした場合、デコミッショニングを緩やかに終了することを確実にする設定可能なタイムアウトがあります。このタイムアウトが発生すると、YARN タスクは終了し、タスクが正常に完了できるように別のノードに再スケジュールされます。
2番目のデコミッションプロセスは、HDFS(Hadoop Distributed File System)のデコミッションプロセスです。 HDFSは、HDFSを実行している任意のノード上の EMR クラスタを介して分散されたブロックにデータを格納します。 HDFS ノードがデコミッションされると、それらのデータブロックを他のHDFSノードに複製して、ノードが終了した時にそれらが失われないようにする必要があります。
では、このナレッジを Amazon EMR でどのように使用できるでしょうか?
クラスタのサイズ変更の Tips
クラスタのサイズを変更する際に考慮すべき事項は次の通りです。
EMR クラスタでは、Hadoop タスク用にコアノードとタスクノードの2種類のノードを使用できます。コアノードは HDFS DataNode プロセスを実行して永続データをホストし、YARN のリソースマネージャーを介して Hadoop タスクを実行します。タスクノードは YARN リソースマネージャーを介して Hadoop タスクのみ実行し、 HDFS にはデータを保存しません。
実行中のクラスタでタスクノードを縮小する場合、クラスタ上で実行中の Hadoop タスクがデコミッションするのに短い遅延が予想されます。これにより、中断によってタスクの進捗状況を失わないようにし、タスクノードを最大限に活用することができます。ただし、あなたのジョブでこの中断が許されている場合は、yarn-site.xml の yarn.resourcemanager.nodemanager-graceful-decommission-timeout-secs プロパティー(EMR 5.14)を調整して、サイズ変更時のデフォルトの1時間のタイムアウトを調整することができます。このプロセスがタイムアウトすると、タスクノードは実行中のタスクに関係なくシャットダウンされます。このプロセスは通常比較的早く、タスクノードの規模を縮小するのが早くなります。
コアノードを縮小する場合、Amazon EMR は HDFS がデータを保護するためにデコミッションするまで待つ必要があります。 HDFS のデコミッションには比較的長い時間がかかります。 HDFS ブロックの複製は、hdfs-site.xml にある設定を介した設計によって抑制されるためです。これは HDFS のデコミッションが抑制されることを意味します。これによりノードがダウンした場合のクラスタへの高負荷から保護されますが、デコミッショニングが遅くなります。多数のコアノードを縮小する場合は、これらの設定を事前に調整して、より迅速にスケールダウンできるようにすることを検討してください。
たとえば、このエクササイズを HDFS とサイズ変更のスピードで考えてみましょう。
hdfs-site.xml にある HDFS の設定は、ブロック複製の抑制に最も大きな影響を与えます。
- datanode.balance.bandwidthPerSec:各ノードのレプリケーションの帯域幅
- namenode.replication.max-streams:ブロック複製に実行されている最大ストリーム
- namenode.replication.max-streams-hard-limit:最大ストリームのハードリミット
- datanode.balance.max.concurrent.moves:ブロックバランサが保留中の移動に使用するスレッドの数
- namenode.replication.work.multiplier.per.iteration:各レプリケーションインターバル中にすぐに転送を開始するブロック数を決定するために使用されます
(変更時には注意してください。これらの設定を不適切に変更すると、特に高負荷のクラスタではクラスタのパフォーマンスが著しく低下する可能性があります)。
クラスタのサイズ変更を早く行うエクササイズ
これらの設定を変更すると、デコミッションの時間が大幅に短縮されます。 この違いを自分で確認するには、次のエクササイズをしてみてください。
- 次のハードウェア構成で EMR クラスタを作成します。
- マスター:1ノード – m3.xlarge
- コア:6ノード – m3.xlarge
- SSH(Secure Shell)を使用してクラスタのマスターノードに接続します。
詳細については、Amazon EMRのドキュメントでConnect to the Master Node Using SSHを参照してください。
- 次のジョブを使用してHDFSにデータをロードします。
$ hadoop jar /usr/lib/hadoop-mapreduce/hadoop-mapreduce-examples.jar teragen 1000000000 /user/hadoop/data1/ $ s3-dist-cp --src s3://aws-bigdata-blog/artifacts/ClusterResize/smallfiles25k/ --dest hdfs:///user/hadoop/data2/
- hdfs-site.xmlを編集する:
$ sudo vim /etc/hadoop/conf/hdfs-site.xml
- 次に、hdfs-site.xmlのプロパティに次の設定を貼り付けます。
免責事項:これらの値は、例示の目的のため比較的高く、本番環境では必ずしも使用とされるべきでものではありません。 本番で実行中のクラスタの設定変更する前に必ずテストしてください。
<property> <name>dfs.datanode.balance.bandwidthPerSec</name> <value>100m</value> </property> <property> <name>dfs.namenode.replication.max-streams</name> <value>100</value> </property> <property> <name>dfs.namenode.replication.max-streams-hard-limit</name> <value>200</value> </property> <property> <name>dfs.datanode.balance.max.concurrent.moves</name> <value>500</value> </property> <property> <name>dfs.namenode.replication.work.multiplier.per.iteration</name> <value>30</value> </property>
- EMRクラスターのコアノードの数を6から5に変更し、EMRイベントタブで、クラスタのサイズ変更にかかった時間を確認します。
- 構成を変更せずに前の手順を繰り返し、サイズ変更の時間の差を確認します。
このエクササイズを通して、私は45分以上(設定変更なし)から約6分(変更されたhdfs-site configs)までサイズ変更時間を短くなることを確認できました。このエクササイズでは、デフォルトの設定で HDFS がどれくらい抑えられているかを示しています。これらのスロットルを取り外すことは危険であり、それらを使用するパフォーマンスを最初にテストする必要がありますが、デコミッションの時間とサイズ変更の時間を大幅に短縮できます。
クラスタのサイズを変更するための追加のTipsを次に示します。
- 縮小するサイズ変更のタイムアウト。インスタンスグループまたはインスタンスフリートの2つの方法でEMRノードを構成できます。詳細については、 Create a Cluster with Instance Fleets or Uniform Instance Groupsを参照してください。インスタンスフリートでノードが構成されている場合、EMR は縮小するサイズ変更のタイムアウトを実装しました。このタイムアウトは、サイズ変更中に何か問題が生じた場合、インスタンスフリートが無限にリサイズしようとするのを防ぎます。現在はデフォルトで1日になっていますので、インスタンスフリートのサイズを変更する際は注意してください。
インスタンスフリートの縮小リクエストが1日よりも長くかかると、多くの実行中のインスタンスが終了し一時停止します。一方、インスタンスグループにはデフォルトの縮小するサイズ変更タイムアウトはありません。ただし、どちらのタイプも、前述のyarn-site.xmlの yarn.resourcemanager.nodemanager-graceful-decommission-timeout-secs プロパティ(EMR 5.14)で1時間の YARN タイムアウトがあります。
- コアノードのサイズを変更するときは、高頻度の HDFS 書き込みに注意してください。 HDFS に多くの書き込みが発生している場合、HDFS は複製を必要とする多数のブロックを変更します。この複製は、コアノードのデコミッションによるブロック複製を妨げ、サイズ変更のプロセスを著しく遅くする可能性があります。
オートスケーリングのポリシーの設定
手動のスケーリングは便利ではありますが、クラスタのサイズ変更の多くは、Amazon EMR オートスケーリングによって動的に実行されます。一般的に、オートスケーリングポリシーの詳細は、特定の Hadoop ジョブに合わせて調整する必要があるため、ここでは詳しく説明しません。代わりに、クラスタのオートスケーリングポリシーを設定するための一般的なガイドラインをいくつか示します。
オートスケーリングポリシーを設定する際の考慮事項は次のとおりです。
スケーリングのメトリック
スケーリングをトリガーするノードタイプに適したメトリックを選択します。たとえば、YARNMemoryAvailablePercentage メトリックのみでコアノードをスケーリングすることは意味がありません。これは、処理能力だけがさらに必要な場合にHDFSの合計サイズを増減するためです。 HDFSUtilization もタスクノードのスケーリングには意味をなさない、なぜなら、タスクノードに付属していない HDFS ストレージスペースを増やしたいからです。コアノードの一般的なオートスケーリングメトリックは HDFSUtilization です。タスクノードの一般的なオートスケーリングメトリックには ContainerPending-Out および YarnMemoryAvailablePercentage が含まれます。
注意:現在、Amazon EMR には HDFS が必要なため、クラスタには少なくとも1つのコアノードが必要です。コアノードは、CPU およびメモリリソースを提供することもできます。しかし、HDFS を拡張する必要がなく、あなたのジョブにもっと多くの CPU やメモリリソースが必要な場合は、その目的のためにタスクノードを使用することをお勧めします。
コアノードのスケーリング
前述のように、クラスタ内の2つの EMR ノードタイプの1つがコアノードです。コアノードは HDFS を実行するため、デコミッションの遅延が長くなります。つまり、スケールが遅く、積極的にスケールするべきではないことを意味します。一度にいくつかのコアノードを追加したり削除したりするだけで、スケーリングの問題を避けることができます。 HDFS ストレージが必要な場合を除き、通常はタスクノードをスケーリングする方が良い方法です。多数のコアノードを拡張する必要がある場合は、hdfs-site.xml の設定を変更して、より迅速な停止時間とより迅速なスケールダウンを可能にすることを検討してください。
タスクノードのスケーリング
タスクノードはHDFSを実行しないため、動的なジョブを積極的にスケーリングするのに最適です。Hadoop タスクがダウンタイムの間に作業が急増している場合、使用するノードタイプです。
非常に積極的なオートスケーリングポリシーを使用してタスクノードを設定できます。タスクノードは、簡単にスケールアップまたはスケールダウンできます。 HDFS スペースが必要ない場合は、クラスタ内のタスクノードを使用できます。
スポットインスタンスの使用
オートスケーリングは、EMR スポットインスタンスタイプを使用するのに最適です。スポットインスタンスが消えたり現れたりする傾向は、タスクノードにとって完璧です。これらのタスクノードは常に積極的なスケールインスケールアウトに使われているため、スポットインスタンスにはほとんど問題がありません。ただし、時間の影響を受けやすい Hadoop タスクでは、オンデマンドインスタンスの優先順位を設定して可用性を保証する場合があります。
コアノードのスケールインポリシーとスケールアウトポリシー
特にコアノードに対して、スケールインポリシーをスケールアウトポリシーの正反対にするという罠に陥らないでください。多くの場合、デコミッションによりスケールインには追加の遅延が生じます。これを考慮に入れて、スケールインポリシーがスケールアウトポリシーよりも寛容になるようにしてください。これは、サイズ変更をトリガするための長いクールダウンと高いメトリック要件を意味します。
スケールアウトポリシーは、短いクールダウン期間と小さいノード増分で容易にトリガーされると考えることができます。スケールインポリシーは、長いクールダウン期間とノード増分でトリガーを難しくします。
コアノードオートスケーリングのための最小ノード
コアノードを拡大縮小するときに考慮すべき点の1つは、yarn-site.xml にある yarn.app.mapreduce.am.labels プロパティです。 Amazon EMR では、yarn.app.mapreduce.am.labels はデフォルトで「CORE」に設定されています。つまり、アプリケーションマスターは常にコアノードで実行され、タスクノードでは実行されません。 これは、スポットインスタンスがタスクノードに使用されているシナリオでのアプリケーション障害を防ぐのに役立ちます。
これは、最小数のコアノードを設定する場合、クラスタで予定するアプリケーションマスターの同時実行数以上の数を選択する必要があることを意味します。 アプリケーション・マスターをタスク・ノード上でも実行させたい場合は、このプロパティーを変更して「TASK」を含める必要があります。ただし、ベストプラクティスとして、Spot インスタンスがタスクノードに使用されている場合は、yarn.app.mapreduce.am.labels プロパティーを TASK に設定しないでください 。
S3DistCp を使用したデータの集約
この記事を書き終える前に、私はクラスタのサイズ変更について最後に1つ情報を共有します。 コアノードのサイズを変更すると、HDFS のデコミッションに非常に時間がかかる場合があります。 これはクラスタの HDFS に多数の小さなファイルを格納した結果です。 HDFS に多数の小さなファイル(HDFS ブロックサイズの128 MBより小さいファイル)を置くと、メタデータのオーバーヘッドが大きくなり、デコミッションとHadoopタスクの両方の処理が遅くなる可能性があります。
データを集約することで、小さなファイルを最小限に抑えれば、クラスタのデコミッションやジョブをよりスムーズに実行できます。ファイルを集約する方法については、 Seven Tips for Using S3DistCp on Amazon EMR to Move Data Efficiently Between HDFS and Amazon S3 を参照してください。
まとめ
この記事では、Amazon EMR のサイズ変更のロジックがデータとHadoop タスクを保護するためにどのように機能するかについて説明しました。 私はまた、EMR のサイズ変更とオートスケーリングのためのいくつかの追加の考慮事項を提供しました。 これらのプラクティスを念頭に置くと、必要なクラスターリソースだけを使用できクラスタを最大限節約できます。
さらに詳しく知りたい場合
この記事が役立ちましたら、Seven Tips for Using S3DistCp on Amazon EMR to Move Data Efficiently Between HDFS and Amazon S3 と Dynamically Scale Applications on Amazon EMR with Auto Scaling もチェックしてみてください。
著者について
Brandon Scheller は、Amazon EMR のソフトウェア開発エンジニアです。 彼の情熱は、Hadoop エコシステムのアプリケーションを開発し、進歩させ、オープンソースコミュニティーと協力することにあります。 彼は自由な時間にはカスケードの登山を楽しんでいます。
翻訳はソリューションアーキテクト上原誠が行いました。原文は Best practices for resizing and automatic scaling in Amazon EMRです。