LinuxでJavaを使ってActive Directoryを認証する
2023-09-26 21:24:58
質問
私は、Java を使用して Active Directory に対して認証を行うという単純なタスクを持っています。単に資格情報を検証するだけで、他には何もありません。私のドメインが "fun.xyz.tld" で、OU パスが不明で、ユーザー名/パスワードが testu/testp であるとします。
このタスクを簡略化する Java ライブラリがいくつかあることは知っていますが、それらを実装することに成功したわけではありません。私が見つけたほとんどの例は、特に Active Directory ではなく、一般的な LDAP に対処していました。LDAPリクエストを発行するということは、その中にOUのパスを送るということですが、私はこれを持っていません。また、LDAPリクエストを発行するアプリケーションは、Active Directoryにアクセスするために、すでにバインドされている必要がある...。認証情報は発見可能な場所に保存されなければならないので、安全ではありません。私は、可能であれば、テスト認証情報でテストバインディングをしたいです - これは、アカウントが有効であることを意味します。
最後に、可能であれば、そのような認証メカニズムを暗号化する方法はありますか?ADがKerberosを使用することは知っていますが、JavaのLDAPメソッドがそうであるかどうかはわかりません。
どなたか動作するコードの例をお持ちですか?ありがとうございます。
どのように解決するのですか?
このブログの例を元にまとめたコードがこちらです。 リンク と、このソースを参考にしました。 リンク .
import com.sun.jndi.ldap.LdapCtxFactory;
import java.util.ArrayList;
import java.util.Hashtable;
import java.util.List;
import java.util.Iterator;
import javax.naming.Context;
import javax.naming.AuthenticationException;
import javax.naming.NamingEnumeration;
import javax.naming.NamingException;
import javax.naming.directory.Attribute;
import javax.naming.directory.Attributes;
import javax.naming.directory.DirContext;
import javax.naming.directory.SearchControls;
import javax.naming.directory.SearchResult;
import static javax.naming.directory.SearchControls.SUBTREE_SCOPE;
class App2 {
public static void main(String[] args) {
if (args.length != 4 && args.length != 2) {
System.out.println("Purpose: authenticate user against Active Directory and list group membership.");
System.out.println("Usage: App2 <username> <password> <domain> <server>");
System.out.println("Short usage: App2 <username> <password>");
System.out.println("(short usage assumes 'xyz.tld' as domain and 'abc' as server)");
System.exit(1);
}
String domainName;
String serverName;
if (args.length == 4) {
domainName = args[2];
serverName = args[3];
} else {
domainName = "xyz.tld";
serverName = "abc";
}
String username = args[0];
String password = args[1];
System.out
.println("Authenticating " + username + "@" + domainName + " through " + serverName + "." + domainName);
// bind by using the specified username/password
Hashtable props = new Hashtable();
String principalName = username + "@" + domainName;
props.put(Context.SECURITY_PRINCIPAL, principalName);
props.put(Context.SECURITY_CREDENTIALS, password);
DirContext context;
try {
context = LdapCtxFactory.getLdapCtxInstance("ldap://" + serverName + "." + domainName + '/', props);
System.out.println("Authentication succeeded!");
// locate this user's record
SearchControls controls = new SearchControls();
controls.setSearchScope(SUBTREE_SCOPE);
NamingEnumeration<SearchResult> renum = context.search(toDC(domainName),
"(& (userPrincipalName=" + principalName + ")(objectClass=user))", controls);
if (!renum.hasMore()) {
System.out.println("Cannot locate user information for " + username);
System.exit(1);
}
SearchResult result = renum.next();
List<String> groups = new ArrayList<String>();
Attribute memberOf = result.getAttributes().get("memberOf");
if (memberOf != null) {// null if this user belongs to no group at all
for (int i = 0; i < memberOf.size(); i++) {
Attributes atts = context.getAttributes(memberOf.get(i).toString(), new String[] { "CN" });
Attribute att = atts.get("CN");
groups.add(att.get().toString());
}
}
context.close();
System.out.println();
System.out.println("User belongs to: ");
Iterator ig = groups.iterator();
while (ig.hasNext()) {
System.out.println(" " + ig.next());
}
} catch (AuthenticationException a) {
System.out.println("Authentication failed: " + a);
System.exit(1);
} catch (NamingException e) {
System.out.println("Failed to bind to LDAP / get account information: " + e);
System.exit(1);
}
}
private static String toDC(String domainName) {
StringBuilder buf = new StringBuilder();
for (String token : domainName.split("\\.")) {
if (token.length() == 0)
continue; // defensive check
if (buf.length() > 0)
buf.append(",");
buf.append("DC=").append(token);
}
return buf.toString();
}
}
関連
-
スレッド "main "での例外 java.util.NoSuchElementException in Java 問題解決済み
-
JAVA_HOME環境変数が正しく定義されていない問題を解決する
-
java -jarコマンドでパッケージを実行すると、無効または破損したjarfile xxxx.jarが表示される。
-
java マイクロソフト払い戻し予期せぬサーバーからのファイルの終了
-
ecplise プロンプトが表示されます。"選択したものは起動できません。" "最近の起動はありません。"
-
org.xml.sax.SAXParseExceptionのエラー解決方法
-
アクセス制限の解決方法: ---- in Java
-
IDEAError:javaの依存性エラー。Annotation processing is not supported for module cycles...(アノテーション処理はモジュールサイクルではサポートされていません。
-
[解決済み] 特定のUnicode文字を含むコメントでのJavaコードの実行が許可されているのはなぜですか?
-
[解決済み] Python + ldap による Active Directory の認証
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
Eclipse問題 アクセス制限。タイプ 'SunJCE' が API でないことを解決し、/jdk ディレクトリにある /jre と jre の違いについて理解を深める。
-
Javaでよくある構文エラー
-
Solve モジュールのビルドに失敗しました。Error: ENOENT: no such file or directory エラー
-
List list = new ArrayList(); Error: ArrayList は型に解決できません。
-
アノテーション「@Retention」の役割
-
CertificateException: XXXに一致するサブジェクトの代替DNS名が見つかりません 解決策
-
X11 DISPLAY変数が設定されていない」問題の解決方法
-
代入の左辺は変数でなければならない 解答
-
Java Runtime Environmentを継続するためのメモリが不足しています。
-
Java:未解決コンパイル問題の解決方法