Search in sources :

Example 1 with SaslClientCallbackHandler

use of org.apache.zookeeper.SaslClientCallbackHandler in project zookeeper by apache.

the class SecurityUtils method createSaslClient.

/**
 * Create an instance of a SaslClient. It will return null if there is an exception.
 *
 * @param subject subject
 * @param servicePrincipal principal
 * @param protocol name of the protocol for which the authentication is being performed
 * @param serverName name of the server to authenticate to
 * @param LOG logger
 * @param entity can be either zookeeper client or quorum learner
 *
 * @return saslclient object
 * @throws SaslException
 */
public static SaslClient createSaslClient(final Subject subject, final String servicePrincipal, final String protocol, final String serverName, final Logger LOG, final String entity) throws SaslException {
    SaslClient saslClient;
    // mechanism to use: if empty, use DIGEST-MD5; otherwise, use GSSAPI.
    if (subject.getPrincipals().isEmpty()) {
        // no principals: must not be GSSAPI: use DIGEST-MD5 mechanism
        // instead.
        LOG.info("{} will use DIGEST-MD5 as SASL mechanism.", entity);
        String[] mechs = { "DIGEST-MD5" };
        String username = (String) (subject.getPublicCredentials().toArray()[0]);
        String password = (String) (subject.getPrivateCredentials().toArray()[0]);
        // 'domain' parameter is hard-wired between the server and client
        saslClient = Sasl.createSaslClient(mechs, username, protocol, serverName, null, new SaslClientCallbackHandler(password, entity));
        return saslClient;
    } else {
        // GSSAPI.
        final Object[] principals = subject.getPrincipals().toArray();
        // determine client principal from subject.
        final Principal clientPrincipal = (Principal) principals[0];
        boolean usingNativeJgss = Boolean.getBoolean("sun.security.jgss.native");
        if (usingNativeJgss) {
            // """
            try {
                GSSManager manager = GSSManager.getInstance();
                Oid krb5Mechanism = new Oid("1.2.840.113554.1.2.2");
                GSSCredential cred = manager.createCredential(null, GSSContext.DEFAULT_LIFETIME, krb5Mechanism, GSSCredential.INITIATE_ONLY);
                subject.getPrivateCredentials().add(cred);
                LOG.debug("Added private credential to {} principal name: '{}'", entity, clientPrincipal);
            } catch (GSSException ex) {
                LOG.warn("Cannot add private credential to subject; " + "authentication at the server may fail", ex);
            }
        }
        final KerberosName clientKerberosName = new KerberosName(clientPrincipal.getName());
        // assume that server and client are in the same realm (by default;
        // unless the system property
        // "zookeeper.server.realm" is set).
        String serverRealm = System.getProperty("zookeeper.server.realm", clientKerberosName.getRealm());
        KerberosName serviceKerberosName = new KerberosName(servicePrincipal + "@" + serverRealm);
        final String serviceName = serviceKerberosName.getServiceName();
        final String serviceHostname = serviceKerberosName.getHostName();
        final String clientPrincipalName = clientKerberosName.toString();
        try {
            saslClient = Subject.doAs(subject, new PrivilegedExceptionAction<SaslClient>() {

                public SaslClient run() throws SaslException {
                    LOG.info("{} will use GSSAPI as SASL mechanism.", entity);
                    String[] mechs = { "GSSAPI" };
                    LOG.debug("creating sasl client: {}={};service={};serviceHostname={}", new Object[] { entity, clientPrincipalName, serviceName, serviceHostname });
                    SaslClient saslClient = Sasl.createSaslClient(mechs, clientPrincipalName, serviceName, serviceHostname, null, new SaslClientCallbackHandler(null, entity));
                    return saslClient;
                }
            });
            return saslClient;
        } catch (Exception e) {
            LOG.error("Exception while trying to create SASL client", e);
            return null;
        }
    }
}
Also used : Oid(org.ietf.jgss.Oid) KerberosName(org.apache.zookeeper.server.auth.KerberosName) PrivilegedExceptionAction(java.security.PrivilegedExceptionAction) PrivilegedActionException(java.security.PrivilegedActionException) GSSException(org.ietf.jgss.GSSException) SaslException(javax.security.sasl.SaslException) SaslClient(javax.security.sasl.SaslClient) GSSException(org.ietf.jgss.GSSException) GSSCredential(org.ietf.jgss.GSSCredential) GSSManager(org.ietf.jgss.GSSManager) SaslClientCallbackHandler(org.apache.zookeeper.SaslClientCallbackHandler) Principal(java.security.Principal)

Example 2 with SaslClientCallbackHandler

use of org.apache.zookeeper.SaslClientCallbackHandler in project zookeeper by apache.

the class ZooKeeperSaslClient method createSaslClient.

private SaslClient createSaslClient(final String servicePrincipal, final String loginContext) throws LoginException {
    try {
        if (!initializedLogin) {
            synchronized (this) {
                if (login == null) {
                    if (LOG.isDebugEnabled()) {
                        LOG.debug("JAAS loginContext is: " + loginContext);
                    }
                    // note that the login object is static: it's shared amongst all zookeeper-related connections.
                    // in order to ensure the login is initialized only once, it must be synchronized the code snippet.
                    login = new Login(loginContext, new SaslClientCallbackHandler(null, "Client"), clientConfig);
                    login.startThreadIfNeeded();
                    initializedLogin = true;
                }
            }
        }
        return SecurityUtils.createSaslClient(login.getSubject(), servicePrincipal, "zookeeper", "zk-sasl-md5", LOG, "Client");
    } catch (LoginException e) {
        // We throw LoginExceptions...
        throw e;
    } catch (Exception e) {
        // ..but consume (with a log message) all other types of exceptions.
        LOG.error("Exception while trying to create SASL client: " + e);
        return null;
    }
}
Also used : LoginException(javax.security.auth.login.LoginException) Login(org.apache.zookeeper.Login) SaslClientCallbackHandler(org.apache.zookeeper.SaslClientCallbackHandler) LoginException(javax.security.auth.login.LoginException) PrivilegedActionException(java.security.PrivilegedActionException) IOException(java.io.IOException) SaslException(javax.security.sasl.SaslException)

Aggregations

PrivilegedActionException (java.security.PrivilegedActionException)2 SaslException (javax.security.sasl.SaslException)2 SaslClientCallbackHandler (org.apache.zookeeper.SaslClientCallbackHandler)2 IOException (java.io.IOException)1 Principal (java.security.Principal)1 PrivilegedExceptionAction (java.security.PrivilegedExceptionAction)1 LoginException (javax.security.auth.login.LoginException)1 SaslClient (javax.security.sasl.SaslClient)1 Login (org.apache.zookeeper.Login)1 KerberosName (org.apache.zookeeper.server.auth.KerberosName)1 GSSCredential (org.ietf.jgss.GSSCredential)1 GSSException (org.ietf.jgss.GSSException)1 GSSManager (org.ietf.jgss.GSSManager)1 Oid (org.ietf.jgss.Oid)1