You are viewing a plain text version of this content. The canonical link for it is here.
Posted to issues@hive.apache.org by "Muthuraj Ramasamy (JIRA)" <ji...@apache.org> on 2016/09/10 03:30:23 UTC
[jira] [Commented] (HIVE-6517) Improvement on HiveServer2 JDBC: in
Kerberos auth mode, accept username / password passed from the client's
SessionConf
[ https://issues.apache.org/jira/browse/HIVE-6517?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=15479051#comment-15479051 ]
Muthuraj Ramasamy commented on HIVE-6517:
-----------------------------------------
Can HiveDriver class be modified to use preauthenticated subject creation in this scenario. Below has the sample code which i used for testing purpose.
Reference : https://issues.apache.org/jira/browse/HIVE-6486
Sample Connection String : jdbc:hive2://%HIVESERVER2%:10000/default;krb5_kdc=%KDC%;principal=hive/%HIVESERVER2%@%REALM%;auth=kerberos;kerberosAuthType=fromSubject
public Connection connect(final String url, final Properties info) throws SQLException {
if (url.contains("kerberosAuthType=fromSubject")) {
return getConnection(url, info);
} else {
return acceptsURL(url) ? new HiveConnection(url, info) : null;
}
}
private Connection getConnection(final String url, final Properties info) throws SQLException {
synchronized (SYNCHRONIZED_OBJ) {
String[] urlParams = url.split(";");
String krb5_realm = null;
String krb5_kdc = null;
JaasConfiguration jaasConf = new JaasConfiguration();
Configuration.setConfiguration(jaasConf);
for (String _urlParam : urlParams) {
if (_urlParam.contains("principal=")) {
krb5_realm = _urlParam.replace("krb5_realm=", "");
krb5_realm = krb5_realm.substring(krb5_realm.indexOf("@") + 1);
}
if (_urlParam.contains("krb5_kdc=")) {
krb5_kdc = _urlParam.replace("krb5_kdc=", "");
}
}
System.setProperty("java.security.krb5.realm", krb5_realm);
System.setProperty("java.security.krb5.kdc", krb5_kdc);
String subjectName = "SampleClient" + (new Date().getTime());
Subject signedOnUserSubject = getSubject(info.getProperty("user"), info.getProperty("password"), krb5_realm, krb5_kdc, subjectName);
Connection conn = null;
try {
conn = (Connection) Subject.doAs(signedOnUserSubject, new PrivilegedExceptionAction<Object>() {
public Object run() {
Connection con = null;
try {
con = acceptsURL(url) ? new HiveConnection(url, info) : null;
} catch (SQLException e) {
e.printStackTrace();
}
return con;
}
});
} catch (PrivilegedActionException e) {
new SQLException(e);
}
return conn;
}
}
private static class JaasConfiguration extends Configuration {
@Override
public AppConfigurationEntry[] getAppConfigurationEntry(String appName) {
Map<String, String> krbOptions = new HashMap<String, String>();
krbOptions.put("refreshKrb5Config", "true");
krbOptions.put("storeKey", "true");
AppConfigurationEntry testClientEntry = new AppConfigurationEntry("com.sun.security.auth.module.Krb5LoginModule", LoginModuleControlFlag.REQUIRED, krbOptions);
return new AppConfigurationEntry[] { testClientEntry };
}
}
public class MyCallbackHandler implements CallbackHandler {
String username = null;
String krb5_realm = null;
String krb5_kdc = null;
String password = null;
public MyCallbackHandler(String username, String password, String krb5_realm, String krb5_kdc) {
this.username = username;
this.krb5_realm = krb5_realm;
this.krb5_kdc = krb5_kdc;
this.password = password;
}
public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException {
for (int i = 0; i < callbacks.length; i++) {
if (callbacks[i] instanceof NameCallback) {
NameCallback nc = (NameCallback) callbacks[i];
nc.setName(username + "@" + krb5_realm);
} else if (callbacks[i] instanceof PasswordCallback) {
PasswordCallback nc = (PasswordCallback) callbacks[i];
nc.setPassword(password.toCharArray());
} else
throw new UnsupportedCallbackException(callbacks[i], "Unrecognised callback");
}
}
}
public Subject getSubject(String username, String password, String krb5_realm, String krb5_kdc, String subjectName) throws SQLException {
Subject signedOnUserSubject = null;
LoginContext lc;
try {
lc = new LoginContext(subjectName, new MyCallbackHandler(username, password, krb5_realm, krb5_kdc));
lc.login();
signedOnUserSubject = lc.getSubject();
} catch (LoginException e1) {
throw new SQLException(e1);
}
return signedOnUserSubject;
}
> Improvement on HiveServer2 JDBC: in Kerberos auth mode, accept username / password passed from the client's SessionConf
> -----------------------------------------------------------------------------------------------------------------------
>
> Key: HIVE-6517
> URL: https://issues.apache.org/jira/browse/HIVE-6517
> Project: Hive
> Issue Type: Improvement
> Components: Authentication, HiveServer2, JDBC
> Reporter: Jacob Magner
> Assignee: Prasad Mujumdar
>
> The default JDBC driver ignores username/password completely in Kerberos auth mode.
> To be able to auth from a web interface, we could enable password pass through by changing
> how the Kerberos transport is established. Specifically, we could use LoginContext to authenticate
> with the kdc, and then use the resulting security context to connect with the hive server.
--
This message was sent by Atlassian JIRA
(v6.3.4#6332)