web-dev-qa-db-ja.com

hadoopでのすべてのアクションの前にugi.checkTGTAndReloginFromKeytab()を呼び出す必要がありますか?

私のサーバーアプリケーションでは、自分のJavaアプリケーションからKerberosで保護されたHadoopクラスターに接続しています。HDFSファイルシステム、Oozie、Hiveなどのさまざまなコンポーネントを使用しています。アプリケーションの起動時にコール

_UserGroupInformation.loginUserFromKeytabAndReturnUGI( ... );
_

これによりUserGroupInformationインスタンスが返され、アプリケーションの有効期間中は保持されます。特権アクションを実行するときは、ugi.doAs(action)で起動します。

これは正常に動作しますが、UserGroupInformationのkerberosチケットをいつ更新する必要があるのか​​疑問に思います。有効期限が近づくたびにチケットの更新を行うように見えるメソッドUserGroupInformation.checkTGTAndReloginFromKeytab()を見つけました。また、このメソッドがWebHdfsFileSystemなどのさまざまなHadoopツールによって呼び出されていることもわかりました。

私のサーバーアプリケーション(数か月または数年も実行している可能性があります)がチケットの期限切れを経験しないようにするには、どの方法が最適ですか?具体的な質問を提供するには:

  1. 必要なときにいつでもcheckTGTAndReloginFromKeytabと呼ばれるさまざまなHadoopクライアントを信頼できますか?
  2. コード内でcheckTGTAndReloginFromKeytabを自分で呼び出す必要がありますか?
  3. もしそうなら、ugi.doAs(...)を呼び出す前にそれを行うべきですか、それともタイマーを設定して定期的に(どれくらいの頻度で)呼び出すのでしょうか?
23
Jan Zyka

Hadoopコミッターはこちら!これは素晴らしい質問です。

残念ながら、アプリケーションの特定の使用パターンを深く掘り下げることなく、これに対する明確な答えを出すことは困難です。代わりに、一般的なガイドラインを示し、Hadoopがチケットの更新またはキータブからの再ログインを自動的に処理する場合とそうでない場合について説明します。

HadoopエコシステムでのKerberos認証の主な使用例は、認証にSASLを使用するHadoopのRPCフレームワークです。 Hadoopエコシステムのほとんどのデーモンプロセスは、プロセスの起動時にUserGroupInformation#loginUserFromKeytabを1回だけ呼び出すことでこれを処理します。この例には、NameNodeへのRPC呼び出しを認証する必要があるHDFS DataNodeと、ResourceManagerへの呼び出しを認証する必要があるYARN NodeManagerが含まれます。 DataNodeのようなデーモンがプロセスの起動時に1回限りのログインを実行し、通常のチケットの有効期限を過ぎて数か月間実行し続けることができるのはなぜですか。

これは非常に一般的な使用例であるため、HadoopはRPCクライアントレイヤー内に直接自動再ログインメカニズムを実装します。このコードはRPC Client#handleSaslConnectionFailure メソッドで確認できます。

          // try re-login
          if (UserGroupInformation.isLoginKeytabBased()) {
            UserGroupInformation.getLoginUser().reloginFromKeytab();
          } else if (UserGroupInformation.isLoginTicketBased()) {
            UserGroupInformation.getLoginUser().reloginFromTicketCache();
          }

これは、再ログインの「遅延評価」と考えることができます。試行されたRPC接続での認証の失敗に応じて、ログインを再実行するだけです。

これを知っていれば、部分的な答えを出すことができます。アプリケーションの使用パターンがキータブからログインしてから一般的なHadoop RPC呼び出しを実行する場合は、独自の再ログインコードをロールする必要はないでしょう。 RPCクライアント層がそれを行います。 「一般的なHadoop RPC」とは、HDFSを含む、Hadoopと対話するためのJava APIの大部分を意味します FileSystem API、 YarnClient およびMapReduce Job 送信。

ただし、一部のアプリケーション使用パターンには、Hadoop RPCがまったく含まれていません。この例は、HadoopのREST APIs WebHDFS または YARN RESTなどの= API 。その場合、Hadoop HTTP Authentication のドキュメントに記載されているように、認証モデルはSPNEGOを介してKerberosを使用します。

これを知っていれば、答えをさらに増やすことができます。アプリケーションの使用パターンがHadoop RPCをまったく使用せず、代わりにREST APIのみを使用する場合は、独自の再ログインロジックをロールする必要があります。これがまさに WebHdfsFileSystemUserGroupInformation#checkTGTAndReloginFromkeytab を呼び出します。お気付きのとおりです。WebHdfsFileSystemは、すべての操作の直前に呼び出しを行うことを選択します。これは UserGroupInformation#checkTGTAndReloginFromkeytabは、有効期限に「近い」場合にのみチケットを更新します。 それ以外の場合、呼び出しは何もしません。

最後の使用例として、キータブからログインするのではなく、アプリケーションを起動する前にユーザーにkinitを外部で実行するように要求するインタラクティブプロセスを考えてみましょう。ほとんどの場合、これらはHadoop CLIコマンドなどの実行時間の短いアプリケーションになります。ただし、場合によっては、これらのプロセスの実行時間が長くなることがあります。実行時間の長いプロセスをサポートするために、Hadoopはバックグラウンドスレッドを開始して、Kerberosチケットを有効期限に「近づく」ように更新します。このロジックは UserGroupInformation#spawnAutoRenewalThreadForUserCreds で確認できます。 RPCレイヤーで提供される自動再ログインロジックと比較すると、ここには重要な違いがあります。この場合、Hadoopはチケットを更新してその寿命を延ばす機能しか持っていません。チケットは、Kerberosインフラストラクチャによって指示されているように、更新可能な最大有効期間を持っています。その後、チケットは使用できなくなります。この場合、ユーザーにパスワードの再プロンプトを表示することを意味するため、この場合の再ログインは事実上不可能であり、端末から離れた可能性があります。これは、プロセスがチケットの有効期限を超えて実行し続けると、それ以上認証できなくなることを意味します。

繰り返しますが、この情報を使用して、全体的な回答を通知できます。アプリケーションを起動する前に、ユーザーがkinitを介してインタラクティブにログインすることに依存していて、アプリケーションがKerberosチケットの更新可能な最大存続期間よりも長く実行されないと確信している場合は、Hadoop内部を使用して定期的な更新をカバーします。

Keytabベースのログインを使用していて、アプリケーションの使用パターンがHadoop RPCレイヤーの自動再ログインに依存できるかどうかがわからない場合は、控えめなアプローチで独自にロールバックします。 @SamsonScharfrichterは、独自のローリングについてここで優れた答えを出しました。

HBase Kerberos接続更新戦略

最後に、APIの安定性に関するメモを追加します。 Apache Hadoop Compatibility ガイドラインでは、後方互換性に対するHadoop開発コミュニティの取り組みについて詳しく説明しています。 UserGroupInformationのインターフェースには、LimitedPrivateおよびEvolvingの注釈が付けられています。技術的には、これはUserGroupInformationのAPIがパブリックと見なされず、下位互換性のない方法で進化する可能性があることを意味します。実際問題として、UserGroupInformationのインターフェースに依存しているコードはすでにたくさんあるので、重大な変更を加えることは不可能です。確かに、現在の2.xリリースライン内では、メソッドシグネチャがあなたの下から変更され、コードが壊れる心配はありません。

これで背景情報がすべて揃ったので、具体的な質問に戻りましょう。

必要なときにcheckTGTAndReloginFromKeytabを呼び出すさまざまなHadoopクライアントを信頼できますか?

アプリケーションの使用パターンがHadoopクライアントを呼び出すことで、HadoopのRPCフレームワークを利用する場合は、これを信頼できます。アプリケーションの使用パターンがHadoop REST APIのみを呼び出す場合、これに依存することはできません。

コード内でcheckTGTAndReloginFromKeytabを自分で呼び出す必要がありますか?

アプリケーションの使用パターンがHadoop RPC呼び出しの代わりにHadoop REST APIを呼び出すことのみである場合、これを行う必要があります。内部に実装された自動再ログインのメリットは得られません。 HadoopのRPCクライアント。

もしそうなら、私はugi.doAs(...)へのすべての呼び出しの前にそれを行うべきですか、それともタイマーを設定してそれを定期的に(どれくらいの頻度で)呼び出しますか?

認証が必要なすべてのアクションの直前にUserGroupInformation#checkTGTAndReloginFromKeytabを呼び出すのは問題ありません。チケットが有効期限に近づいていない場合、メソッドはノーオペレーションになります。 Kerberosインフラストラクチャの速度が遅いことが疑わしく、クライアントの操作で再ログインの待機時間のコストを支払わせたくない場合は、それが別のバックグラウンドスレッドで実行する理由になります。チケットの実際の有効期限より少し前に留まるようにしてください。チケットが有効期限に「近い」かどうかを判断するために、UserGroupInformation内のロジックを借用する場合があります。実際には、再ログインの待ち時間が問題になることは個人的には見たことがありません。

72
Chris Nauroth