我们正在尝试在我们的生产环境中使用 LDAP 身份验证设置 Azkaban。关于如何做到这一点的任何线索?文档说可以通过扩展 UserManager 类来添加插件 jar 文件来完成。我是 azkaban 的新手,正在寻找一些示例代码
问问题
1111 次
2 回答
2
您将需要安装一个自定义的“用户管理器”插件。可以在github上找到:https ://github.com/researchgate/azkaban-ldap-usermanager
关于如何配置用户管理器插件的说明可以在 github repo 的首页找到。
本质上,您将需要:
- 下载并构建插件
- 将您构建的 .jar 文件复制到 Azkaban 安装的 ./extlib 目录中
- 编辑 azkaban.properties 文件,指定 user.manager.class 和一些 user.manager.ldap 属性。
于 2015-08-07T19:07:49.217 回答
1
我们还想在 azkaban 中设置 LDAP 身份验证 - 但第一个答案中提到的开源项目的功能非常有限,并且在与 LDAP 服务器的连接建立后不允许启动 TLS 协商。
我们编写了一个全新的 java 类来处理以下场景:
- 不安全地建立 LDAP 连接(在端口 389 上)
- 启动 TLS 响应和 TLS 协商
- 然后验证用户凭据。
使用这种方法,我们也不必仅为 azkaban 在 LDAP 中创建服务用户。
查看示例代码块
@Override
public User getUser(String username, String password) throws UserManagerException {
if (username == null || username.trim().isEmpty()) {
throw new UserManagerException("Username is empty.");
} else if (password == null || password.trim().isEmpty()) {
throw new UserManagerException("Password is empty.");
}
String email = null;
String groups = null;
StringBuilder url = new StringBuilder("ldap://").append(ldapHost).append(":").append(ldapPort);
Hashtable<String, String> env = new Hashtable<String, String>();
env.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
env.put(Context.PROVIDER_URL, url.toString());
try {
// Create initial context
LdapContext ctx = new InitialLdapContext(env, null);
// Start TLS
StartTlsResponse tls = (StartTlsResponse) ctx.extendedOperation(new StartTlsRequest());
SSLSession sess = tls.negotiate();
// Adding username and password to environment
StringBuilder sb = new StringBuilder("uid=").append(username).append(",").append(ldapUserBase);
ctx.addToEnvironment(Context.SECURITY_AUTHENTICATION, "simple");
ctx.addToEnvironment(Context.SECURITY_PRINCIPAL, sb.toString());
ctx.addToEnvironment(Context.SECURITY_CREDENTIALS, password);
// Search the user in a LDAP directory
final LdapCtx x = (LdapCtx) ctx.lookup(sb.toString());
// Lookup is successful - creating an Azkaban user
User user = new User(username);
// Searching LDAP directory to get email and group
SearchControls ctls = new SearchControls();
String[] attributes = { "cn", "memberOf", "mail" };
ctls.setReturningAttributes(attributes);
NamingEnumeration<?> answer = ctx.search(ldapUserBase, "(uid=" + username + ")", ctls);
Boolean isAdmin = false;
// Search user email and groups
while (answer.hasMore()) {
SearchResult rslt = (SearchResult) answer.next();
Attributes attrs = rslt.getAttributes();
groups = attrs.get("memberof").toString().split(":")[1].trim();
if (attrs.get("memberof") != null && attrs.get("memberof").toString().split(":").length > 0) {
groups = attrs.get("memberof").toString().split(":")[1].trim();
for (String group : groups.split(",")) {
if (ldapAdminGroups.contains(group))
isAdmin = true;
}
}
if (attrs.get("mail") != null) {
email = attrs.get("mail").toString().split(":")[1].trim();
user.setEmail(email);
}
}
// Assign the correct role
if (isAdmin)
user.addRole("admin");
else
user.addRole("read");
ctx.close();
return user;
} catch (NamingException e) {
throw new UserManagerException("LDAP error: " + e.getMessage(), e);
} catch (IOException e) {
// TODO Auto-generated catch block
throw new UserManagerException("IO error", e);
}
}
注意:我在这方面没有做很多异常处理——你需要根据你的需要来做。
如何让它在阿兹卡班工作:
- 构建一个 maven 或 gradle 项目。
- 不需要额外的库(Azkaban 除外 - 即 com.linkedin.azkaban)
- 有一个将继承“azkaban.user.UserManager”的新类
- 在 azkaban/extlibs 中构建并复制 jar
- 在 azkaban.properties - 设置 "user.manager.class=" 以及所有必需的属性,如主机、端口和 ldap 用户库 (ou=Users,dc=stackoverflow,dc=com) 详细信息。
您应该善于通过 LDAP 对用户进行身份验证。
快乐编码!
谢谢,侯赛因·博拉
于 2016-10-28T20:02:24.500 回答