5

アプリケーションサーバーとしてTomcat7.0を使用するJavaベースのWebアプリに取り組んでいます。前の質問に対する有益な回答の後、私はbcryptを使用してパスワードをHSQLDBに安全に保存することにしました。ただし、Tomcatのデフォルトのレルム実装はbcryptを処理できないため、独自に作成する必要があります。これが、カスタムレルムを作成する唯一の理由ですが、他のすべての方法と同様に、プレーンなJDBCRealmは機能します。私はグーグルで例を見てきましたが、いくつかの点でかなり混乱しています。

まず、RealmBaseまたはJDBCRealmを拡張する必要がありますか?私が見つけたほとんどの例はRealmBaseを使用していますが、これまでアプリにJDBCRealmを使用してきました(まだ開発中であるため、パスワードをプレーンテキストで保存し、JDBCRealmを使用して認証を処理することから始めました)。Code Ranchに関する質問では、それを拡張することをお勧めします。ただし、その場合にオーバーライドする必要があるメソッドは正確にはわかりません。認証方法だけですか、それともそれ以上ですか?もしこれがJDBCRealmでユーザーロール、getPrincipal、その他すべてを処理および管理できるとしたら?

次に、上記のリンク先のCodeRanchの例では、何かが足りない場合を除いて、getPasswordメソッドが暗号化されていないパスワードを返しているようです。不可能なbcryptを使うつもりですが、とにかくお勧めできないようですので、と思います。このブログ投稿のような他の例では、getPasswordはデータベースから直接パスワードを返すようです。では、どちらが正しいのでしょうか。getPasswordが正確に何に使用されているのかわかりません。ドキュメントには記載されていません。このためにデータベースに保存されている暗号化された値を返すだけで大丈夫ですか?

どのクラスを拡張する必要があるか、どのメソッドをオーバーライドする必要があるか、どのgetPasswordを返す必要があるかを誰かに教えてもらえれば、本当にありがたいです。

4

1 に答える 1

4

いくつかの試行錯誤の後で、私はこれを行う方法を考え出しました。JDBCRealmを拡張し、認証メソッドを上書きするだけで、完全に機能します。カスタムレルムと同じディレクトリにBCrypt.javaを配置しましたが、このコードが機能しました。

import java.security.Principal;
import org.apache.catalina.realm.JDBCRealm;
public class BCryptRealm extends JDBCRealm
{
  @Override
  public Principal authenticate(String username, String credentials)
  {
    String hashedPassword = getPassword(username);
    // Added this check after discovering checkpw generates a null pointer
    // error if the hashedPassword is null, which happens when the user doesn't
    // exist. I'm assuming returning null immediately would be bad practice as
    // it would let an attacker know which users do and don't exist, so I added
    // a call to hashpw. No idea if that completely solves the problem, so if
    // your application has more stringent security needs this should be
    // investigated further.
    if (hashedPassword == null)
    {
      BCrypt.hashpw("fakePassword", BCrypt.gensalt());
      return null;
    }
    if (BCrypt.checkpw(credentials, hashedPassword))
    {
      return getPrincipal(username);
    }
    return null;
  }
}

于 2012-09-10T01:37:19.320 に答える