Author: ddas
Date: Fri Jul 23 00:05:32 2010
New Revision: 966911
URL: http://svn.apache.org/viewvc?rev=966911&view=rev
Log:
HADOOP-6861. Adds new non-static methods in Credentials to read and write token
storage file. Contributed by Jitendra Pandey & Owen O'Malley.
Modified:
hadoop/common/trunk/CHANGES.txt
hadoop/common/trunk/src/java/org/apache/hadoop/io/WritableUtils.java
hadoop/common/trunk/src/java/org/apache/hadoop/security/Credentials.java
hadoop/common/trunk/src/java/org/apache/hadoop/security/UserGroupInformation.java
hadoop/common/trunk/src/java/org/apache/hadoop/util/GenericOptionsParser.java
hadoop/common/trunk/src/test/core/org/apache/hadoop/util/TestGenericOptionsParser.java
Modified: hadoop/common/trunk/CHANGES.txt
URL:
http://svn.apache.org/viewvc/hadoop/common/trunk/CHANGES.txt?rev=966911&r1=966910&r2=966911&view=diff
==============================================================================
--- hadoop/common/trunk/CHANGES.txt (original)
+++ hadoop/common/trunk/CHANGES.txt Fri Jul 23 00:05:32 2010
@@ -80,6 +80,9 @@ Trunk (unreleased changes)
same principal. Now the principal name is a pattern that has _HOST in it.
(Kan Zhang & Jitendra Pandey via ddas)
+ HADOOP-6861. Adds new non-static methods in Credentials to read and
+ write token storage file. (Jitendra Pandey & Owen O'Malley via ddas)
+
OPTIMIZATIONS
BUG FIXES
Modified: hadoop/common/trunk/src/java/org/apache/hadoop/io/WritableUtils.java
URL:
http://svn.apache.org/viewvc/hadoop/common/trunk/src/java/org/apache/hadoop/io/WritableUtils.java?rev=966911&r1=966910&r2=966911&view=diff
==============================================================================
--- hadoop/common/trunk/src/java/org/apache/hadoop/io/WritableUtils.java
(original)
+++ hadoop/common/trunk/src/java/org/apache/hadoop/io/WritableUtils.java Fri
Jul 23 00:05:32 2010
@@ -57,7 +57,8 @@ public final class WritableUtils {
}
}
- public static int writeCompressedByteArray(DataOutput out, byte[] bytes)
throws IOException {
+ public static int writeCompressedByteArray(DataOutput out,
+ byte[] bytes) throws IOException
{
if (bytes != null) {
ByteArrayOutputStream bos = new ByteArrayOutputStream();
GZIPOutputStream gzout = new GZIPOutputStream(bos);
Modified:
hadoop/common/trunk/src/java/org/apache/hadoop/security/Credentials.java
URL:
http://svn.apache.org/viewvc/hadoop/common/trunk/src/java/org/apache/hadoop/security/Credentials.java?rev=966911&r1=966910&r2=966911&view=diff
==============================================================================
--- hadoop/common/trunk/src/java/org/apache/hadoop/security/Credentials.java
(original)
+++ hadoop/common/trunk/src/java/org/apache/hadoop/security/Credentials.java
Fri Jul 23 00:05:32 2010
@@ -19,13 +19,17 @@
package org.apache.hadoop.security;
import java.io.DataInput;
+import java.io.DataInputStream;
import java.io.DataOutput;
+import java.io.DataOutputStream;
import java.io.IOException;
+import java.util.Arrays;
import java.util.Collection;
import java.util.HashMap;
import java.util.Map;
import org.apache.hadoop.fs.FSDataInputStream;
+import org.apache.hadoop.fs.FSDataOutputStream;
import org.apache.hadoop.fs.FileSystem;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.Text;
@@ -114,24 +118,59 @@ public class Credentials implements Writ
}
/**
- * Convenience method for reading a file, and loading the Tokens
+ * Convenience method for reading a token storage file, and loading the
Tokens
* therein in the passed UGI
* @param filename
* @param conf
- * @param ugi
* @throws IOException
*/
- public static void readTokensAndLoadInUGI(String filename, Configuration
conf,
- UserGroupInformation ugi) throws IOException {
- Path localTokensFile = new Path (filename);
- FileSystem localFS = FileSystem.getLocal(conf);
- FSDataInputStream in = localFS.open(localTokensFile);
- Credentials ts = new Credentials();
- ts.readFields(in);
- for (Token<? extends TokenIdentifier> token : ts.getAllTokens()) {
- ugi.addToken(token);
+ public void readTokenStorageFile(Path filename,
+ Configuration conf) throws IOException {
+ FSDataInputStream in = filename.getFileSystem(conf).open(filename);
+ try {
+ readTokenStorageStream(in);
+ } catch(IOException ioe) {
+ throw new IOException("Exception reading " + filename, ioe);
+ } finally {
+ in.close();
}
}
+
+ /**
+ * Convenience method for reading a token storage file directly from a
+ * datainputstream
+ */
+ public void readTokenStorageStream(DataInputStream in) throws IOException {
+ byte[] magic = new byte[TOKEN_STORAGE_MAGIC.length];
+ in.readFully(magic);
+ if (!Arrays.equals(magic, TOKEN_STORAGE_MAGIC)) {
+ throw new IOException("Bad header found in token storage.");
+ }
+ byte version = in.readByte();
+ if (version != TOKEN_STORAGE_VERSION) {
+ throw new IOException("Unknown version " + version +
+ " in token storage.");
+ }
+ readFields(in);
+ }
+
+ private static final byte[] TOKEN_STORAGE_MAGIC = "HDTS".getBytes();
+ private static final byte TOKEN_STORAGE_VERSION = 0;
+
+ public void writeTokenStorageToStream(DataOutputStream os)
+ throws IOException {
+ os.write(TOKEN_STORAGE_MAGIC);
+ os.write(TOKEN_STORAGE_VERSION);
+ write(os);
+ }
+
+ public void writeTokenStorageFile(Path filename,
+ Configuration conf) throws IOException {
+ FSDataOutputStream os = filename.getFileSystem(conf).create(filename);
+ writeTokenStorageToStream(os);
+ os.close();
+ }
+
/**
* Stores all the keys to DataOutput
* @param out
@@ -151,7 +190,8 @@ public class Credentials implements Writ
WritableUtils.writeVInt(out, secretKeysMap.size());
for(Map.Entry<Text, byte[]> e : secretKeysMap.entrySet()) {
e.getKey().write(out);
- WritableUtils.writeCompressedByteArray(out, e.getValue());
+ WritableUtils.writeVInt(out, e.getValue().length);
+ out.write(e.getValue());
}
}
@@ -178,8 +218,23 @@ public class Credentials implements Writ
for(int i=0; i<size; i++) {
Text alias = new Text();
alias.readFields(in);
- byte[] key = WritableUtils.readCompressedByteArray(in);
- secretKeysMap.put(alias, key);
+ int len = WritableUtils.readVInt(in);
+ byte[] value = new byte[len];
+ in.readFully(value);
+ secretKeysMap.put(alias, value);
+ }
+ }
+
+ /**
+ * Copy all of the credentials from one credential object into another.
+ * @param other the credentials to copy
+ */
+ public void addAll(Credentials other) {
+ for(Map.Entry<Text, byte[]> secret: other.secretKeysMap.entrySet()) {
+ secretKeysMap.put(secret.getKey(), secret.getValue());
+ }
+ for(Map.Entry<Text, Token<?>> token: other.tokenMap.entrySet()){
+ tokenMap.put(token.getKey(), token.getValue());
}
}
}
Modified:
hadoop/common/trunk/src/java/org/apache/hadoop/security/UserGroupInformation.java
URL:
http://svn.apache.org/viewvc/hadoop/common/trunk/src/java/org/apache/hadoop/security/UserGroupInformation.java?rev=966911&r1=966910&r2=966911&view=diff
==============================================================================
---
hadoop/common/trunk/src/java/org/apache/hadoop/security/UserGroupInformation.java
(original)
+++
hadoop/common/trunk/src/java/org/apache/hadoop/security/UserGroupInformation.java
Fri Jul 23 00:05:32 2010
@@ -50,6 +50,7 @@ import org.apache.commons.logging.LogFac
import org.apache.hadoop.classification.InterfaceAudience;
import org.apache.hadoop.classification.InterfaceStability;
import org.apache.hadoop.conf.Configuration;
+import org.apache.hadoop.fs.Path;
import org.apache.hadoop.security.token.Token;
import org.apache.hadoop.security.token.TokenIdentifier;
@@ -135,6 +136,9 @@ public class UserGroupInformation {
private static boolean useKerberos;
/** Server-side groups fetching service */
private static Groups groups;
+ /** The configuration to use */
+ private static Configuration conf;
+
public static final long MIN_TIME_BEFORE_RELOGIN = 10 * 60 * 1000L;
@@ -188,6 +192,7 @@ public class UserGroupInformation {
"configuration", ioe);
}
isInitialized = true;
+ UserGroupInformation.conf = conf;
}
/**
@@ -398,9 +403,15 @@ public class UserGroupInformation {
login.login();
loginUser.setLogin(login);
loginUser = new UserGroupInformation(login.getSubject());
- String tokenFile = System.getenv(HADOOP_TOKEN_FILE_LOCATION);
- if (tokenFile != null && isSecurityEnabled()) {
- Credentials.readTokensAndLoadInUGI(tokenFile, new Configuration(),
loginUser);
+ String fileLocation = System.getenv(HADOOP_TOKEN_FILE_LOCATION);
+ if (fileLocation != null && isSecurityEnabled()) {
+ // load the token storage file and put all of the tokens into the
+ // user.
+ Credentials cred = new Credentials();
+ cred.readTokenStorageFile(new Path("file:///" + fileLocation), conf);
+ for (Token<?> token: cred.getAllTokens()) {
+ loginUser.addToken(token);
+ }
}
} catch (LoginException le) {
throw new IOException("failure to login", le);
Modified:
hadoop/common/trunk/src/java/org/apache/hadoop/util/GenericOptionsParser.java
URL:
http://svn.apache.org/viewvc/hadoop/common/trunk/src/java/org/apache/hadoop/util/GenericOptionsParser.java?rev=966911&r1=966910&r2=966911&view=diff
==============================================================================
---
hadoop/common/trunk/src/java/org/apache/hadoop/util/GenericOptionsParser.java
(original)
+++
hadoop/common/trunk/src/java/org/apache/hadoop/util/GenericOptionsParser.java
Fri Jul 23 00:05:32 2010
@@ -317,7 +317,9 @@ public class GenericOptionsParser {
throw new FileNotFoundException("File "+fileName+" does not exist.");
}
LOG.debug("setting conf tokensFile: " + fileName);
- conf.set("tokenCacheFile", localFs.makeQualified(p).toString());
+ conf.set("mapreduce.job.credentials.json", localFs.makeQualified(p)
+ .toString());
+
}
}
Modified:
hadoop/common/trunk/src/test/core/org/apache/hadoop/util/TestGenericOptionsParser.java
URL:
http://svn.apache.org/viewvc/hadoop/common/trunk/src/test/core/org/apache/hadoop/util/TestGenericOptionsParser.java?rev=966911&r1=966910&r2=966911&view=diff
==============================================================================
---
hadoop/common/trunk/src/test/core/org/apache/hadoop/util/TestGenericOptionsParser.java
(original)
+++
hadoop/common/trunk/src/test/core/org/apache/hadoop/util/TestGenericOptionsParser.java
Fri Jul 23 00:05:32 2010
@@ -126,7 +126,7 @@ public class TestGenericOptionsParser ex
Path tmpPath = new Path(tmpFile.toString());
localFs.create(tmpPath);
new GenericOptionsParser(conf, args);
- String fileName = conf.get("tokenCacheFile");
+ String fileName = conf.get("mapreduce.job.credentials.json");
assertNotNull("files is null", fileName);
assertEquals("files option does not match",
localFs.makeQualified(tmpPath).toString(), fileName);