You are viewing a plain text version of this content. The canonical link for it is here.
Posted to common-commits@hadoop.apache.org by ki...@apache.org on 2014/04/28 15:54:49 UTC
svn commit: r1590639 - in
/hadoop/common/branches/branch-2/hadoop-common-project: hadoop-auth/
hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/
hadoop-auth/src/test/java/org/apache/hadoop/security/authentication/util/
hadoop-co...
Author: kihwal
Date: Mon Apr 28 13:54:48 2014
New Revision: 1590639
URL: http://svn.apache.org/r1590639
Log:
svn merge -c 1590637 merging from trunk to branch-2 to fix:HADOOP-10322. Add ability to read principal names from a keytab. Contributed by Benoy Antony and Daryn Sharp.
Modified:
hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/pom.xml
hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/KerberosUtil.java
hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/test/java/org/apache/hadoop/security/authentication/util/TestKerberosUtil.java
hadoop/common/branches/branch-2/hadoop-common-project/hadoop-common/CHANGES.txt
Modified: hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/pom.xml
URL: http://svn.apache.org/viewvc/hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/pom.xml?rev=1590639&r1=1590638&r2=1590639&view=diff
==============================================================================
--- hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/pom.xml (original)
+++ hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/pom.xml Mon Apr 28 13:54:48 2014
@@ -102,6 +102,12 @@
<artifactId>httpclient</artifactId>
<scope>compile</scope>
</dependency>
+ <dependency>
+ <groupId>org.apache.directory.server</groupId>
+ <artifactId>apacheds-kerberos-codec</artifactId>
+ <version>2.0.0-M15</version>
+ <scope>compile</scope>
+ </dependency>
</dependencies>
<build>
Modified: hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/KerberosUtil.java
URL: http://svn.apache.org/viewvc/hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/KerberosUtil.java?rev=1590639&r1=1590638&r2=1590639&view=diff
==============================================================================
--- hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/KerberosUtil.java (original)
+++ hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/main/java/org/apache/hadoop/security/authentication/util/KerberosUtil.java Mon Apr 28 13:54:48 2014
@@ -17,18 +17,27 @@
*/
package org.apache.hadoop.security.authentication.util;
+import static org.apache.hadoop.util.PlatformName.IBM_JAVA;
+
+import java.io.File;
+import java.io.IOException;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.net.InetAddress;
import java.net.UnknownHostException;
+import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
import java.util.Locale;
+import java.util.Set;
+import java.util.regex.Pattern;
+import org.apache.directory.server.kerberos.shared.keytab.Keytab;
+import org.apache.directory.server.kerberos.shared.keytab.KeytabEntry;
import org.ietf.jgss.GSSException;
import org.ietf.jgss.Oid;
-import static org.apache.hadoop.util.PlatformName.IBM_JAVA;
-
public class KerberosUtil {
/* Return the Kerberos login module name */
@@ -103,4 +112,48 @@ public class KerberosUtil {
// with uppercase characters.
return service + "/" + fqdn.toLowerCase(Locale.US);
}
+
+ /**
+ * Get all the unique principals present in the keytabfile.
+ *
+ * @param keytabFileName
+ * Name of the keytab file to be read.
+ * @return list of unique principals in the keytab.
+ * @throws IOException
+ * If keytab entries cannot be read from the file.
+ */
+ static final String[] getPrincipalNames(String keytabFileName) throws IOException {
+ Keytab keytab = Keytab.read(new File(keytabFileName));
+ Set<String> principals = new HashSet<String>();
+ List<KeytabEntry> entries = keytab.getEntries();
+ for (KeytabEntry entry: entries){
+ principals.add(entry.getPrincipalName().replace("\\", "/"));
+ }
+ return principals.toArray(new String[0]);
+ }
+
+ /**
+ * Get all the unique principals from keytabfile which matches a pattern.
+ *
+ * @param keytab
+ * Name of the keytab file to be read.
+ * @param pattern
+ * pattern to be matched.
+ * @return list of unique principals which matches the pattern.
+ * @throws IOException
+ */
+ public static final String[] getPrincipalNames(String keytab,
+ Pattern pattern) throws IOException {
+ String[] principals = getPrincipalNames(keytab);
+ if (principals.length != 0) {
+ List<String> matchingPrincipals = new ArrayList<String>();
+ for (String principal : principals) {
+ if (pattern.matcher(principal).matches()) {
+ matchingPrincipals.add(principal);
+ }
+ }
+ principals = matchingPrincipals.toArray(new String[0]);
+ }
+ return principals;
+ }
}
Modified: hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/test/java/org/apache/hadoop/security/authentication/util/TestKerberosUtil.java
URL: http://svn.apache.org/viewvc/hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/test/java/org/apache/hadoop/security/authentication/util/TestKerberosUtil.java?rev=1590639&r1=1590638&r2=1590639&view=diff
==============================================================================
--- hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/test/java/org/apache/hadoop/security/authentication/util/TestKerberosUtil.java (original)
+++ hadoop/common/branches/branch-2/hadoop-common-project/hadoop-auth/src/test/java/org/apache/hadoop/security/authentication/util/TestKerberosUtil.java Mon Apr 28 13:54:48 2014
@@ -16,13 +16,39 @@
*/
package org.apache.hadoop.security.authentication.util;
-import org.junit.Assert;
-
+import java.io.File;
import java.io.IOException;
-
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import java.util.regex.Pattern;
+
+import org.apache.directory.server.kerberos.shared.keytab.Keytab;
+import org.apache.directory.server.kerberos.shared.keytab.KeytabEntry;
+import org.apache.directory.shared.kerberos.KerberosTime;
+import org.apache.directory.shared.kerberos.codec.types.EncryptionType;
+import org.apache.directory.shared.kerberos.components.EncryptionKey;
+import org.junit.After;
+import org.junit.Assert;
import org.junit.Test;
public class TestKerberosUtil {
+ static String testKeytab = "test.keytab";
+ static String[] testPrincipals = new String[]{
+ "HTTP@testRealm",
+ "test/testhost@testRealm",
+ "HTTP/testhost@testRealm",
+ "HTTP1/testhost@testRealm",
+ "HTTP/testhostanother@testRealm"
+ };
+
+ @After
+ public void deleteKeytab() {
+ File keytabFile = new File(testKeytab);
+ if (keytabFile.exists()){
+ keytabFile.delete();
+ }
+ }
@Test
public void testGetServerPrincipal() throws IOException {
@@ -51,4 +77,84 @@ public class TestKerberosUtil {
service + "/" + testHost.toLowerCase(),
KerberosUtil.getServicePrincipal(service, testHost.toLowerCase()));
}
+
+ @Test
+ public void testGetPrincipalNamesMissingKeytab() {
+ try {
+ KerberosUtil.getPrincipalNames(testKeytab);
+ Assert.fail("Exception should have been thrown");
+ } catch (IOException e) {
+ //expects exception
+ }
+ }
+
+ @Test
+ public void testGetPrincipalNamesMissingPattern() throws IOException {
+ createKeyTab(testKeytab, new String[]{"test/testhost@testRealm"});
+ try {
+ KerberosUtil.getPrincipalNames(testKeytab, null);
+ Assert.fail("Exception should have been thrown");
+ } catch (Exception e) {
+ //expects exception
+ }
+ }
+
+ @Test
+ public void testGetPrincipalNamesFromKeytab() throws IOException {
+ createKeyTab(testKeytab, testPrincipals);
+ // read all principals in the keytab file
+ String[] principals = KerberosUtil.getPrincipalNames(testKeytab);
+ Assert.assertNotNull("principals cannot be null", principals);
+
+ int expectedSize = 0;
+ List<String> principalList = Arrays.asList(principals);
+ for (String principal : testPrincipals) {
+ Assert.assertTrue("missing principal "+principal,
+ principalList.contains(principal));
+ expectedSize++;
+ }
+ Assert.assertEquals(expectedSize, principals.length);
+ }
+
+ @Test
+ public void testGetPrincipalNamesFromKeytabWithPattern() throws IOException {
+ createKeyTab(testKeytab, testPrincipals);
+ // read the keytab file
+ // look for principals with HTTP as the first part
+ Pattern httpPattern = Pattern.compile("HTTP/.*");
+ String[] httpPrincipals =
+ KerberosUtil.getPrincipalNames(testKeytab, httpPattern);
+ Assert.assertNotNull("principals cannot be null", httpPrincipals);
+
+ int expectedSize = 0;
+ List<String> httpPrincipalList = Arrays.asList(httpPrincipals);
+ for (String principal : testPrincipals) {
+ if (httpPattern.matcher(principal).matches()) {
+ Assert.assertTrue("missing principal "+principal,
+ httpPrincipalList.contains(principal));
+ expectedSize++;
+ }
+ }
+ Assert.assertEquals(expectedSize, httpPrincipals.length);
+ }
+
+ private void createKeyTab(String fileName, String[] principalNames)
+ throws IOException {
+ //create a test keytab file
+ List<KeytabEntry> lstEntries = new ArrayList<KeytabEntry>();
+ for (String principal : principalNames){
+ // create 3 versions of the key to ensure methods don't return
+ // duplicate principals
+ for (int kvno=1; kvno <= 3; kvno++) {
+ EncryptionKey key = new EncryptionKey(
+ EncryptionType.UNKNOWN, "samplekey1".getBytes(), kvno);
+ KeytabEntry keytabEntry = new KeytabEntry(
+ principal, 1 , new KerberosTime(), (byte) 1, key);
+ lstEntries.add(keytabEntry);
+ }
+ }
+ Keytab keytab = Keytab.getInstance();
+ keytab.setEntries(lstEntries);
+ keytab.write(new File(testKeytab));
+ }
}
\ No newline at end of file
Modified: hadoop/common/branches/branch-2/hadoop-common-project/hadoop-common/CHANGES.txt
URL: http://svn.apache.org/viewvc/hadoop/common/branches/branch-2/hadoop-common-project/hadoop-common/CHANGES.txt?rev=1590639&r1=1590638&r2=1590639&view=diff
==============================================================================
--- hadoop/common/branches/branch-2/hadoop-common-project/hadoop-common/CHANGES.txt (original)
+++ hadoop/common/branches/branch-2/hadoop-common-project/hadoop-common/CHANGES.txt Mon Apr 28 13:54:48 2014
@@ -30,6 +30,9 @@ Release 2.5.0 - UNRELEASED
HADOOP-10535. Make the retry numbers in ActiveStandbyElector configurable.
(jing9)
+ HADOOP-10322. Add ability to read principal names from a keytab.
+ (Benoy Antony and Daryn Sharp via kihwal)
+
OPTIMIZATIONS
BUG FIXES