asfgit closed pull request #3256: NIFI-5945 Add support for password login to kerberos code in nifi-sec… URL: https://github.com/apache/nifi/pull/3256
This is a PR merged from a forked repository. As GitHub hides the original diff on merge, it is displayed below for the sake of provenance: As this is a foreign pull request (from a fork), the diff is supplied below (as it won't show otherwise due to GitHub magic): diff --git a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/StandardKeytabUser.java b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/AbstractKerberosUser.java similarity index 86% rename from nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/StandardKeytabUser.java rename to nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/AbstractKerberosUser.java index 7302ee00eb..32eb9bb3d9 100644 --- a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/StandardKeytabUser.java +++ b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/AbstractKerberosUser.java @@ -23,7 +23,6 @@ import javax.security.auth.Subject; import javax.security.auth.kerberos.KerberosPrincipal; import javax.security.auth.kerberos.KerberosTicket; -import javax.security.auth.login.Configuration; import javax.security.auth.login.LoginContext; import javax.security.auth.login.LoginException; import java.security.PrivilegedAction; @@ -34,14 +33,9 @@ import java.util.Set; import java.util.concurrent.atomic.AtomicBoolean; -/** - * Used to authenticate and execute actions when Kerberos is enabled and a keytab is being used. - * - * Some of the functionality in this class is adapted from Hadoop's UserGroupInformation. - */ -public class StandardKeytabUser implements KeytabUser { +public abstract class AbstractKerberosUser implements KerberosUser { - private static final Logger LOGGER = LoggerFactory.getLogger(StandardKeytabUser.class); + private static final Logger LOGGER = LoggerFactory.getLogger(AbstractKerberosUser.class); static final String DATE_FORMAT = "yyyy-MM-dd'T'HH:mm:ss'Z'"; @@ -50,18 +44,15 @@ */ static final float TICKET_RENEW_WINDOW = 0.80f; - private final String principal; - private final String keytabFile; - private final AtomicBoolean loggedIn = new AtomicBoolean(false); + protected final String principal; + protected final AtomicBoolean loggedIn = new AtomicBoolean(false); - private Subject subject; - private LoginContext loginContext; + protected Subject subject; + protected LoginContext loginContext; - public StandardKeytabUser(final String principal, final String keytabFile) { + public AbstractKerberosUser(final String principal) { this.principal = principal; - this.keytabFile = keytabFile; - Validate.notBlank(principal); - Validate.notBlank(keytabFile); + Validate.notBlank(this.principal); } /** @@ -80,19 +71,19 @@ public synchronized void login() throws LoginException { if (loginContext == null) { LOGGER.debug("Initializing new login context..."); this.subject = new Subject(); - - final Configuration config = new KeytabConfiguration(principal, keytabFile); - this.loginContext = new LoginContext("KeytabConf", subject, null, config); + this.loginContext = createLoginContext(subject); } loginContext.login(); loggedIn.set(true); LOGGER.debug("Successful login for {}", new Object[]{principal}); } catch (LoginException le) { - throw new LoginException("Unable to login with " + principal + " and " + keytabFile + " due to: " + le.getMessage()); + throw new LoginException("Unable to login with " + principal + " due to: " + le.getMessage()); } } + protected abstract LoginContext createLoginContext(final Subject subject) throws LoginException; + /** * Performs a logout of the current user. * @@ -244,14 +235,6 @@ public String getPrincipal() { return principal; } - /** - * @return the keytab file for this user - */ - @Override - public String getKeytabFile() { - return keytabFile; - } - // Visible for testing Subject getSubject() { return this.subject; diff --git a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/ConfigurationUtil.java b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/ConfigurationUtil.java new file mode 100644 index 0000000000..131ff2233a --- /dev/null +++ b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/ConfigurationUtil.java @@ -0,0 +1,25 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.apache.nifi.security.krb; + +public interface ConfigurationUtil { + + boolean IS_IBM = System.getProperty("java.vendor", "").contains("IBM"); + String IBM_KRB5_LOGIN_MODULE = "com.ibm.security.auth.module.Krb5LoginModule"; + String SUN_KRB5_LOGIN_MODULE = "com.sun.security.auth.module.Krb5LoginModule"; + +} diff --git a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabAction.java b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosAction.java similarity index 79% rename from nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabAction.java rename to nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosAction.java index 5e3f5925fa..bd3e1f9264 100644 --- a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabAction.java +++ b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosAction.java @@ -25,24 +25,24 @@ import java.security.PrivilegedAction; /** - * Helper class for processors to perform an action as a KeytabUser. + * Helper class for processors to perform an action as a KerberosUser. */ -public class KeytabAction { +public class KerberosAction { - private final KeytabUser keytabUser; + private final KerberosUser kerberosUser; private final PrivilegedAction action; private final ProcessContext context; private final ComponentLog logger; - public KeytabAction(final KeytabUser keytabUser, - final PrivilegedAction action, - final ProcessContext context, - final ComponentLog logger) { - this.keytabUser = keytabUser; + public KerberosAction(final KerberosUser kerberosUser, + final PrivilegedAction action, + final ProcessContext context, + final ComponentLog logger) { + this.kerberosUser = kerberosUser; this.action = action; this.context = context; this.logger = logger; - Validate.notNull(this.keytabUser); + Validate.notNull(this.kerberosUser); Validate.notNull(this.action); Validate.notNull(this.context); Validate.notNull(this.logger); @@ -50,10 +50,10 @@ public KeytabAction(final KeytabUser keytabUser, public void execute() { // lazily login the first time the processor executes - if (!keytabUser.isLoggedIn()) { + if (!kerberosUser.isLoggedIn()) { try { - keytabUser.login(); - logger.info("Successful login for {}", new Object[]{keytabUser.getPrincipal()}); + kerberosUser.login(); + logger.info("Successful login for {}", new Object[]{kerberosUser.getPrincipal()}); } catch (LoginException e) { // make sure to yield so the processor doesn't keep retrying the rolled back flow files immediately context.yield(); @@ -63,7 +63,7 @@ public void execute() { // check if we need to re-login, will only happen if re-login window is reached (80% of TGT life) try { - keytabUser.checkTGTAndRelogin(); + kerberosUser.checkTGTAndRelogin(); } catch (LoginException e) { // make sure to yield so the processor doesn't keep retrying the rolled back flow files immediately context.yield(); @@ -72,15 +72,15 @@ public void execute() { // attempt to execute the action, if an exception is caught attempt to logout/login and retry try { - keytabUser.doAs(action); + kerberosUser.doAs(action); } catch (SecurityException se) { logger.info("Privileged action failed, attempting relogin and retrying..."); logger.debug("", se); try { - keytabUser.logout(); - keytabUser.login(); - keytabUser.doAs(action); + kerberosUser.logout(); + kerberosUser.login(); + kerberosUser.doAs(action); } catch (Exception e) { // make sure to yield so the processor doesn't keep retrying the rolled back flow files immediately context.yield(); diff --git a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosKeytabUser.java b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosKeytabUser.java new file mode 100644 index 0000000000..a2af82e08a --- /dev/null +++ b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosKeytabUser.java @@ -0,0 +1,59 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.apache.nifi.security.krb; + +import org.apache.commons.lang3.Validate; + +import javax.security.auth.Subject; +import javax.security.auth.login.Configuration; +import javax.security.auth.login.LoginContext; +import javax.security.auth.login.LoginException; + +/** + * Used to authenticate and execute actions when Kerberos is enabled and a keytab is being used. + * + * Some of the functionality in this class is adapted from Hadoop's UserGroupInformation. + */ +public class KerberosKeytabUser extends AbstractKerberosUser { + + private final String keytabFile; + + public KerberosKeytabUser(final String principal, final String keytabFile) { + super(principal); + this.keytabFile = keytabFile; + Validate.notBlank(keytabFile); + } + + @Override + protected LoginContext createLoginContext(Subject subject) throws LoginException { + final Configuration config = new KeytabConfiguration(principal, keytabFile); + return new LoginContext("KeytabConf", subject, null, config); + } + + /** + * @return the keytab file for this user + */ + public String getKeytabFile() { + return keytabFile; + } + + // Visible for testing + Subject getSubject() { + return this.subject; + } + +} diff --git a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosPasswordUser.java b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosPasswordUser.java new file mode 100644 index 0000000000..d81fc850d7 --- /dev/null +++ b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosPasswordUser.java @@ -0,0 +1,110 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.apache.nifi.security.krb; + +import org.apache.commons.lang3.Validate; + +import javax.security.auth.Subject; +import javax.security.auth.callback.Callback; +import javax.security.auth.callback.CallbackHandler; +import javax.security.auth.callback.NameCallback; +import javax.security.auth.callback.PasswordCallback; +import javax.security.auth.callback.UnsupportedCallbackException; +import javax.security.auth.login.AppConfigurationEntry; +import javax.security.auth.login.Configuration; +import javax.security.auth.login.LoginContext; +import javax.security.auth.login.LoginException; +import java.io.IOException; +import java.util.HashMap; + +/** + * KerberosUser that authenticates via username and password instead of keytab. + */ +public class KerberosPasswordUser extends AbstractKerberosUser { + + private final String password; + + public KerberosPasswordUser(final String principal, final String password) { + super(principal); + this.password = password; + Validate.notBlank(this.password); + } + + @Override + protected LoginContext createLoginContext(final Subject subject) throws LoginException { + final Configuration configuration = new PasswordConfig(); + final CallbackHandler callbackHandler = new UsernamePasswordCallbackHandler(principal, password); + return new LoginContext("PasswordConf", subject, callbackHandler, configuration); + } + + /** + * JAAS Configuration to use when logging in with username/password. + */ + private static class PasswordConfig extends Configuration { + + @Override + public AppConfigurationEntry[] getAppConfigurationEntry(String name) { + HashMap<String, String> options = new HashMap<String, String>(); + options.put("storeKey", "true"); + options.put("refreshKrb5Config", "true"); + + final String krbLoginModuleName = ConfigurationUtil.IS_IBM + ? ConfigurationUtil.IBM_KRB5_LOGIN_MODULE : ConfigurationUtil.SUN_KRB5_LOGIN_MODULE; + + return new AppConfigurationEntry[] { + new AppConfigurationEntry( + krbLoginModuleName, + AppConfigurationEntry.LoginModuleControlFlag.REQUIRED, + options + ) + }; + } + + } + + /** + * CallbackHandler that provides the given username and password. + */ + private static class UsernamePasswordCallbackHandler implements CallbackHandler { + + private final String username; + private final String password; + + public UsernamePasswordCallbackHandler(final String username, final String password) { + this.username = username; + this.password = password; + Validate.notBlank(this.username); + Validate.notBlank(this.password); + } + + public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException { + for (final Callback callback : callbacks) { + if (callback instanceof NameCallback) { + final NameCallback nameCallback = (NameCallback) callback; + nameCallback.setName(username); + } else if (callback instanceof PasswordCallback) { + final PasswordCallback passwordCallback = (PasswordCallback) callback; + passwordCallback.setPassword(password.toCharArray()); + } else { + throw new IllegalStateException("Unexpected callback type: " + callback.getClass().getCanonicalName()); + } + } + } + + } + +} diff --git a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabUser.java b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosUser.java similarity index 95% rename from nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabUser.java rename to nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosUser.java index 42089c2d26..16e4fd2b66 100644 --- a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabUser.java +++ b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KerberosUser.java @@ -24,7 +24,7 @@ /** * A keytab-based user that can login/logout and perform actions as the given user. */ -public interface KeytabUser { +public interface KerberosUser { /** * Performs a login for the given user. @@ -80,9 +80,4 @@ */ String getPrincipal(); - /** - * @return the keytab file for this user - */ - String getKeytabFile(); - } diff --git a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabConfiguration.java b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabConfiguration.java index 0ad0efe13c..24af9b207e 100644 --- a/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabConfiguration.java +++ b/nifi-commons/nifi-security-utils/src/main/java/org/apache/nifi/security/krb/KeytabConfiguration.java @@ -28,10 +28,6 @@ */ public class KeytabConfiguration extends Configuration { - static final boolean IS_IBM = System.getProperty("java.vendor", "").contains("IBM"); - static final String IBM_KRB5_LOGIN_MODULE = "com.ibm.security.auth.module.Krb5LoginModule"; - static final String SUN_KRB5_LOGIN_MODULE = "com.sun.security.auth.module.Krb5LoginModule"; - private final String principal; private final String keytabFile; @@ -53,7 +49,7 @@ public KeytabConfiguration(final String principal, final String keytabFile) { options.put("principal", principal); options.put("refreshKrb5Config", "true"); - if (IS_IBM) { + if (ConfigurationUtil.IS_IBM) { options.put("useKeytab", keytabFile); options.put("credsType", "both"); } else { @@ -64,7 +60,8 @@ public KeytabConfiguration(final String principal, final String keytabFile) { options.put("storeKey", "true"); } - final String krbLoginModuleName = IS_IBM ? IBM_KRB5_LOGIN_MODULE : SUN_KRB5_LOGIN_MODULE; + final String krbLoginModuleName = ConfigurationUtil.IS_IBM + ? ConfigurationUtil.IBM_KRB5_LOGIN_MODULE : ConfigurationUtil.SUN_KRB5_LOGIN_MODULE; this.kerberosKeytabConfigEntry = new AppConfigurationEntry( krbLoginModuleName, AppConfigurationEntry.LoginModuleControlFlag.REQUIRED, options); diff --git a/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KDCServer.java b/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KDCServer.java index 5669b07be2..478b4dee16 100644 --- a/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KDCServer.java +++ b/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KDCServer.java @@ -67,8 +67,11 @@ public String getRealm() { return kdc.getRealm(); } - public void createKeytabFile(final File keytabFile, final String... names) throws Exception { + public void createKeytabPrincipal(final File keytabFile, final String... names) throws Exception { kdc.createPrincipal(keytabFile, names); } + public void createPasswordPrincipal(final String principal, final String password) throws Exception { + kdc.createPrincipal(principal, password); + } } diff --git a/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KeytabUserIT.java b/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KerberosUserIT.java similarity index 65% rename from nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KeytabUserIT.java rename to nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KerberosUserIT.java index 795f4fb40a..e6360089c4 100644 --- a/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KeytabUserIT.java +++ b/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/KerberosUserIT.java @@ -37,7 +37,7 @@ import static org.junit.Assert.assertFalse; import static org.junit.Assert.fail; -public class KeytabUserIT { +public class KerberosUserIT { @ClassRule public static TemporaryFolder tmpDir = new TemporaryFolder(); @@ -50,6 +50,9 @@ private static KerberosPrincipal principal2; private static File principal2KeytabFile; + private static KerberosPrincipal principal3; + private static final String principal3Password = "changeme"; + @BeforeClass public static void setupClass() throws Exception { kdc = new KDCServer(tmpDir.newFolder("mini-kdc_")); @@ -58,31 +61,34 @@ public static void setupClass() throws Exception { principal1 = new KerberosPrincipal("user1@" + kdc.getRealm()); principal1KeytabFile = tmpDir.newFile("user1.keytab"); - kdc.createKeytabFile(principal1KeytabFile, "user1"); + kdc.createKeytabPrincipal(principal1KeytabFile, "user1"); principal2 = new KerberosPrincipal("user2@" + kdc.getRealm()); principal2KeytabFile = tmpDir.newFile("user2.keytab"); - kdc.createKeytabFile(principal2KeytabFile, "user2"); + kdc.createKeytabPrincipal(principal2KeytabFile, "user2"); + + principal3 = new KerberosPrincipal("user3@" + kdc.getRealm()); + kdc.createPasswordPrincipal("user3", principal3Password); } @Test - public void testSuccessfulLoginAndLogout() throws LoginException { + public void testKeytabUserSuccessfulLoginAndLogout() throws LoginException { // perform login for user1 - final KeytabUser user1 = new StandardKeytabUser(principal1.getName(), principal1KeytabFile.getAbsolutePath()); + final KerberosUser user1 = new KerberosKeytabUser(principal1.getName(), principal1KeytabFile.getAbsolutePath()); user1.login(); // perform login for user2 - final KeytabUser user2 = new StandardKeytabUser(principal2.getName(), principal2KeytabFile.getAbsolutePath()); + final KerberosUser user2 = new KerberosKeytabUser(principal2.getName(), principal2KeytabFile.getAbsolutePath()); user2.login(); // verify user1 Subject only has user1 principal - final Subject user1Subject = ((StandardKeytabUser) user1).getSubject(); + final Subject user1Subject = ((KerberosKeytabUser) user1).getSubject(); final Set<Principal> user1SubjectPrincipals = user1Subject.getPrincipals(); assertEquals(1, user1SubjectPrincipals.size()); assertEquals(principal1.getName(), user1SubjectPrincipals.iterator().next().getName()); // verify user2 Subject only has user2 principal - final Subject user2Subject = ((StandardKeytabUser) user2).getSubject(); + final Subject user2Subject = ((KerberosKeytabUser) user2).getSubject(); final Set<Principal> user2SubjectPrincipals = user2Subject.getPrincipals(); assertEquals(1, user2SubjectPrincipals.size()); assertEquals(principal2.getName(), user2SubjectPrincipals.iterator().next().getName()); @@ -101,9 +107,9 @@ public void testSuccessfulLoginAndLogout() throws LoginException { } @Test - public void testLoginWithUnknownPrincipal() throws LoginException { + public void testKeytabLoginWithUnknownPrincipal() throws LoginException { final String unknownPrincipal = "doesnotexist@" + kdc.getRealm(); - final KeytabUser user1 = new StandardKeytabUser(unknownPrincipal, principal1KeytabFile.getAbsolutePath()); + final KerberosUser user1 = new KerberosKeytabUser(unknownPrincipal, principal1KeytabFile.getAbsolutePath()); try { user1.login(); fail("Login should have failed"); @@ -113,9 +119,38 @@ public void testLoginWithUnknownPrincipal() throws LoginException { } } + @Test + public void testPasswordUserSuccessfulLoginAndLogout() throws LoginException { + // perform login for user + final KerberosUser user = new KerberosPasswordUser(principal3.getName(), principal3Password); + user.login(); + + // verify user Subject only has user principal + final Subject userSubject = ((KerberosPasswordUser) user).getSubject(); + final Set<Principal> userSubjectPrincipals = userSubject.getPrincipals(); + assertEquals(1, userSubjectPrincipals.size()); + assertEquals(principal3.getName(), userSubjectPrincipals.iterator().next().getName()); + + // call check/relogin and verify neither user performed a relogin + assertFalse(user.checkTGTAndRelogin()); + + // perform logout for both users + user.logout(); + + // verify subjects have no more principals + assertEquals(0, userSubject.getPrincipals().size()); + } + + @Test(expected = LoginException.class) + public void testPasswordUserLoginWithInvalidPassword() throws LoginException { + // perform login for user + final KerberosUser user = new KerberosPasswordUser("user3", "NOT THE PASSWORD"); + user.login(); + } + @Test public void testCheckTGTAndRelogin() throws LoginException, InterruptedException { - final KeytabUser user1 = new StandardKeytabUser(principal1.getName(), principal1KeytabFile.getAbsolutePath()); + final KerberosUser user1 = new KerberosKeytabUser(principal1.getName(), principal1KeytabFile.getAbsolutePath()); user1.login(); // Since we set the lifetime to 15 seconds we should hit a relogin before 15 attempts @@ -136,7 +171,7 @@ public void testCheckTGTAndRelogin() throws LoginException, InterruptedException @Test public void testKeytabAction() { - final KeytabUser user1 = new StandardKeytabUser(principal1.getName(), principal1KeytabFile.getAbsolutePath()); + final KerberosUser user1 = new KerberosKeytabUser(principal1.getName(), principal1KeytabFile.getAbsolutePath()); final AtomicReference<String> resultHolder = new AtomicReference<>(null); final PrivilegedAction privilegedAction = () -> { @@ -148,8 +183,8 @@ public void testKeytabAction() { final ComponentLog logger = Mockito.mock(ComponentLog.class); // create the action to test and execute it - final KeytabAction keytabAction = new KeytabAction(user1, privilegedAction, context, logger); - keytabAction.execute(); + final KerberosAction kerberosAction = new KerberosAction(user1, privilegedAction, context, logger); + kerberosAction.execute(); // if the result holder has the string success then we know the action executed assertEquals("SUCCESS", resultHolder.get()); diff --git a/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/TestKeytabConfiguration.java b/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/TestKeytabConfiguration.java index f1056365c1..663fa06329 100644 --- a/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/TestKeytabConfiguration.java +++ b/nifi-commons/nifi-security-utils/src/test/java/org/apache/nifi/security/krb/TestKeytabConfiguration.java @@ -39,7 +39,7 @@ public void testCreatingKeytabConfiguration() { assertEquals(1, entries.length); final AppConfigurationEntry entry = entries[0]; - assertEquals(KeytabConfiguration.SUN_KRB5_LOGIN_MODULE, entry.getLoginModuleName()); + assertEquals(ConfigurationUtil.SUN_KRB5_LOGIN_MODULE, entry.getLoginModuleName()); assertEquals(principal, entry.getOptions().get("principal")); assertEquals(keytab, entry.getOptions().get("keyTab")); } diff --git a/nifi-nar-bundles/nifi-solr-bundle/nifi-solr-processors/src/main/java/org/apache/nifi/processors/solr/SolrProcessor.java b/nifi-nar-bundles/nifi-solr-bundle/nifi-solr-processors/src/main/java/org/apache/nifi/processors/solr/SolrProcessor.java index fa44b2e604..4a193b62ff 100755 --- a/nifi-nar-bundles/nifi-solr-bundle/nifi-solr-processors/src/main/java/org/apache/nifi/processors/solr/SolrProcessor.java +++ b/nifi-nar-bundles/nifi-solr-bundle/nifi-solr-processors/src/main/java/org/apache/nifi/processors/solr/SolrProcessor.java @@ -28,9 +28,9 @@ import org.apache.nifi.processor.ProcessContext; import org.apache.nifi.processor.ProcessSession; import org.apache.nifi.processor.exception.ProcessException; -import org.apache.nifi.security.krb.KeytabAction; -import org.apache.nifi.security.krb.KeytabUser; -import org.apache.nifi.security.krb.StandardKeytabUser; +import org.apache.nifi.security.krb.KerberosAction; +import org.apache.nifi.security.krb.KerberosUser; +import org.apache.nifi.security.krb.KerberosKeytabUser; import org.apache.nifi.ssl.SSLContextService; import org.apache.solr.client.solrj.SolrClient; @@ -63,7 +63,7 @@ private volatile String basicPassword; private volatile boolean basicAuthEnabled = false; - private volatile KeytabUser keytabUser; + private volatile KerberosUser kerberosUser; @OnScheduled public final void onScheduled(final ProcessContext context) throws IOException { @@ -78,12 +78,12 @@ public final void onScheduled(final ProcessContext context) throws IOException { final KerberosCredentialsService kerberosCredentialsService = context.getProperty(KERBEROS_CREDENTIALS_SERVICE).asControllerService(KerberosCredentialsService.class); if (kerberosCredentialsService != null) { - this.keytabUser = createKeytabUser(kerberosCredentialsService); + this.kerberosUser = createKeytabUser(kerberosCredentialsService); } } - protected KeytabUser createKeytabUser(final KerberosCredentialsService kerberosCredentialsService) { - return new StandardKeytabUser(kerberosCredentialsService.getPrincipal(), kerberosCredentialsService.getKeytab()); + protected KerberosUser createKeytabUser(final KerberosCredentialsService kerberosCredentialsService) { + return new KerberosKeytabUser(kerberosCredentialsService.getPrincipal(), kerberosCredentialsService.getKeytab()); } @OnStopped @@ -96,10 +96,10 @@ public final void closeClient() { } } - if (keytabUser != null) { + if (kerberosUser != null) { try { - keytabUser.logout(); - keytabUser = null; + kerberosUser.logout(); + kerberosUser = null; } catch (LoginException e) { getLogger().debug("Error logging out keytab user", e); } @@ -108,8 +108,8 @@ public final void closeClient() { @Override public final void onTrigger(final ProcessContext context, final ProcessSession session) throws ProcessException { - final KeytabUser keytabUser = getKerberosKeytabUser(); - if (keytabUser == null) { + final KerberosUser kerberosUser = getKerberosKeytabUser(); + if (kerberosUser == null) { doOnTrigger(context, session); } else { // wrap doOnTrigger in a privileged action @@ -119,8 +119,8 @@ public final void onTrigger(final ProcessContext context, final ProcessSession s }; // execute the privileged action as the given keytab user - final KeytabAction keytabAction = new KeytabAction(keytabUser, action, context, getLogger()); - keytabAction.execute(); + final KerberosAction kerberosAction = new KerberosAction(kerberosUser, action, context, getLogger()); + kerberosAction.execute(); } } @@ -168,8 +168,8 @@ protected final boolean isBasicAuthEnabled() { return basicAuthEnabled; } - protected final KeytabUser getKerberosKeytabUser() { - return keytabUser; + protected final KerberosUser getKerberosKeytabUser() { + return kerberosUser; } @Override diff --git a/nifi-nar-bundles/nifi-solr-bundle/nifi-solr-processors/src/test/java/org/apache/nifi/processors/solr/TestPutSolrContentStream.java b/nifi-nar-bundles/nifi-solr-bundle/nifi-solr-processors/src/test/java/org/apache/nifi/processors/solr/TestPutSolrContentStream.java index 4eeb12a524..e3c3b796b7 100755 --- a/nifi-nar-bundles/nifi-solr-bundle/nifi-solr-processors/src/test/java/org/apache/nifi/processors/solr/TestPutSolrContentStream.java +++ b/nifi-nar-bundles/nifi-solr-bundle/nifi-solr-processors/src/test/java/org/apache/nifi/processors/solr/TestPutSolrContentStream.java @@ -21,7 +21,8 @@ import org.apache.nifi.processor.ProcessContext; import org.apache.nifi.processor.exception.ProcessException; import org.apache.nifi.reporting.InitializationException; -import org.apache.nifi.security.krb.KeytabUser; +import org.apache.nifi.security.krb.KerberosKeytabUser; +import org.apache.nifi.security.krb.KerberosUser; import org.apache.nifi.ssl.SSLContextService; import org.apache.nifi.util.TestRunner; import org.apache.nifi.util.TestRunners; @@ -451,10 +452,10 @@ public void testBasicAuthAndKerberosNotAllowedTogether() throws IOException, Ini runner.assertValid(); proc.onScheduled(runner.getProcessContext()); - final KeytabUser keytabUser = proc.getMockKerberosKeytabUser(); - Assert.assertNotNull(keytabUser); - Assert.assertEquals(principal, keytabUser.getPrincipal()); - Assert.assertEquals(keytab, keytabUser.getKeytabFile()); + final KerberosUser kerberosUser = proc.getMockKerberosKeytabUser();; + Assert.assertNotNull(kerberosUser); + Assert.assertEquals(principal, kerberosUser.getPrincipal()); + Assert.assertEquals(keytab, ((KerberosKeytabUser)kerberosUser).getKeytabFile()); } @Test @@ -462,20 +463,20 @@ public void testUpdateWithKerberosAuth() throws IOException, InitializationExcep final String principal = "n...@foo.com"; final String keytab = "src/test/resources/foo.keytab"; - // Setup a mock KeytabUser that will still execute the privileged action - final KeytabUser keytabUser = Mockito.mock(KeytabUser.class); - when(keytabUser.getPrincipal()).thenReturn(principal); - when(keytabUser.getKeytabFile()).thenReturn(keytab); - when(keytabUser.doAs(any(PrivilegedAction.class))).thenAnswer((invocation -> { + // Setup a mock KerberosUser that will still execute the privileged action + final KerberosKeytabUser kerberosUser = Mockito.mock(KerberosKeytabUser.class); + when(kerberosUser.getPrincipal()).thenReturn(principal); + when(kerberosUser.getKeytabFile()).thenReturn(keytab); + when(kerberosUser.doAs(any(PrivilegedAction.class))).thenAnswer((invocation -> { final PrivilegedAction action = (PrivilegedAction) invocation.getArguments()[0]; action.run(); return null; }) ); - // Configure the processor with the mock KeytabUser and with a credentials service + // Configure the processor with the mock KerberosUser and with a credentials service final SolrClient solrClient = createEmbeddedSolrClient(DEFAULT_SOLR_CORE); - final TestableProcessor proc = new TestableProcessor(solrClient, keytabUser); + final TestableProcessor proc = new TestableProcessor(solrClient, kerberosUser); final TestRunner runner = createDefaultTestRunner(proc); final KerberosCredentialsService kerberosCredentialsService = new MockKerberosCredentialsService(principal, keytab); @@ -499,9 +500,9 @@ public void testUpdateWithKerberosAuth() throws IOException, InitializationExcep } // Verify that during the update the user was logged in, TGT was checked, and the action was executed - verify(keytabUser, times(1)).login(); - verify(keytabUser, times(1)).checkTGTAndRelogin(); - verify(keytabUser, times(1)).doAs(any(PrivilegedAction.class)); + verify(kerberosUser, times(1)).login(); + verify(kerberosUser, times(1)).checkTGTAndRelogin(); + verify(kerberosUser, times(1)).doAs(any(PrivilegedAction.class)); } @@ -647,15 +648,15 @@ protected SolrClient createSolrClient(ProcessContext context, String solrLocatio // Override createSolrClient and return the passed in SolrClient private class TestableProcessor extends PutSolrContentStream { private SolrClient solrClient; - private KeytabUser keytabUser; + private KerberosUser kerberosUser; public TestableProcessor(SolrClient solrClient) { this.solrClient = solrClient; } - public TestableProcessor(SolrClient solrClient, KeytabUser keytabUser) { + public TestableProcessor(SolrClient solrClient, KerberosUser kerberosUser) { this.solrClient = solrClient; - this.keytabUser = keytabUser; + this.kerberosUser = kerberosUser; } @Override @@ -664,15 +665,15 @@ protected SolrClient createSolrClient(ProcessContext context, String solrLocatio } @Override - protected KeytabUser createKeytabUser(KerberosCredentialsService kerberosCredentialsService) { - if (keytabUser != null) { - return keytabUser; + protected KerberosUser createKeytabUser(KerberosCredentialsService kerberosCredentialsService) { + if (kerberosUser != null) { + return kerberosUser; } else { return super.createKeytabUser(kerberosCredentialsService); } } - public KeytabUser getMockKerberosKeytabUser() { + public KerberosUser getMockKerberosKeytabUser() { return super.getKerberosKeytabUser(); } } ---------------------------------------------------------------- This is an automated message from the Apache Git Service. To respond to the message, please log on GitHub and use the URL above to go to the specific comment. For queries about this service, please contact Infrastructure at: us...@infra.apache.org With regards, Apache Git Services