accumulo-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From els...@apache.org
Subject [1/2] accumulo git commit: ACCUMULO-3690 Properly login as trace user when sasl is enabled
Date Fri, 20 Mar 2015 17:08:04 GMT
Repository: accumulo
Updated Branches:
  refs/heads/master 9df45b210 -> 4ca314384


ACCUMULO-3690 Properly login as trace user when sasl is enabled


Project: http://git-wip-us.apache.org/repos/asf/accumulo/repo
Commit: http://git-wip-us.apache.org/repos/asf/accumulo/commit/e82d6833
Tree: http://git-wip-us.apache.org/repos/asf/accumulo/tree/e82d6833
Diff: http://git-wip-us.apache.org/repos/asf/accumulo/diff/e82d6833

Branch: refs/heads/master
Commit: e82d6833d6604a606e49200345f1963cef54fcf6
Parents: 9df45b2
Author: Josh Elser <elserj@apache.org>
Authored: Fri Mar 20 12:08:29 2015 -0400
Committer: Josh Elser <elserj@apache.org>
Committed: Fri Mar 20 12:56:47 2015 -0400

----------------------------------------------------------------------
 .../accumulo/monitor/servlets/trace/Basic.java  | 85 +++++++++++++++-----
 .../monitor/servlets/trace/ListType.java        | 26 +++++-
 .../monitor/servlets/trace/ShowTrace.java       | 30 +++++--
 .../monitor/servlets/trace/Summary.java         | 34 +++++---
 4 files changed, 134 insertions(+), 41 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/accumulo/blob/e82d6833/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Basic.java
----------------------------------------------------------------------
diff --git a/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Basic.java
b/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Basic.java
index 19cd2c6..2143766 100644
--- a/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Basic.java
+++ b/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Basic.java
@@ -19,6 +19,8 @@ package org.apache.accumulo.monitor.servlets.trace;
 import static java.nio.charset.StandardCharsets.UTF_8;
 
 import java.io.IOException;
+import java.security.PrivilegedExceptionAction;
+import java.util.AbstractMap;
 import java.util.Date;
 import java.util.Map;
 import java.util.Map.Entry;
@@ -41,6 +43,7 @@ import org.apache.accumulo.monitor.servlets.BasicServlet;
 import org.apache.accumulo.server.client.HdfsZooInstance;
 import org.apache.accumulo.server.security.SecurityUtil;
 import org.apache.accumulo.tracer.TraceFormatter;
+import org.apache.hadoop.security.UserGroupInformation;
 
 abstract class Basic extends BasicServlet {
 
@@ -71,37 +74,77 @@ abstract class Basic extends BasicServlet {
     return TraceFormatter.formatDate(new Date(millis));
   }
 
-  protected Scanner getScanner(StringBuilder sb) throws AccumuloException, AccumuloSecurityException
{
+  protected Entry<Scanner,UserGroupInformation> getScanner(final StringBuilder sb)
throws AccumuloException, AccumuloSecurityException {
     AccumuloConfiguration conf = Monitor.getContext().getConfiguration();
     final boolean saslEnabled = conf.getBoolean(Property.INSTANCE_RPC_SASL_ENABLED);
-    String principal = conf.get(Property.TRACE_USER);
-    AuthenticationToken at;
+    UserGroupInformation traceUgi = null;
+    final String principal;
+    final AuthenticationToken at;
     Map<String,String> loginMap = conf.getAllPropertiesWithPrefix(Property.TRACE_TOKEN_PROPERTY_PREFIX);
-    if (loginMap.isEmpty()) {
-      if (saslEnabled) {
-        try {
-          at = new KerberosToken();
-        } catch (IOException e) {
-          throw new AccumuloException("Failed to create KerberosToken", e);
-        }
-        principal = SecurityUtil.getServerPrincipal(principal);
-      } else {
+    // May be null
+    String keytab = loginMap.get(Property.TRACE_TOKEN_PROPERTY_PREFIX.getKey() + "keytab");
+
+    if (saslEnabled && null != keytab) {
+      principal = SecurityUtil.getServerPrincipal(conf.get(Property.TRACE_USER));
+      try {
+        traceUgi = UserGroupInformation.loginUserFromKeytabAndReturnUGI(principal, keytab);
+      } catch (IOException e) {
+        throw new RuntimeException("Failed to login as trace user", e);
+      }
+    } else {
+      principal = conf.get(Property.TRACE_USER);
+    }
+
+    if (!saslEnabled) {
+      if (loginMap.isEmpty()) {
         Property p = Property.TRACE_PASSWORD;
         at = new PasswordToken(conf.get(p).getBytes(UTF_8));
+      } else {
+        Properties props = new Properties();
+        int prefixLength = Property.TRACE_TOKEN_PROPERTY_PREFIX.getKey().length();
+        for (Entry<String,String> entry : loginMap.entrySet()) {
+          props.put(entry.getKey().substring(prefixLength), entry.getValue());
+        }
+
+        AuthenticationToken token = Property.createInstanceFromPropertyName(conf, Property.TRACE_TOKEN_TYPE,
AuthenticationToken.class, new PasswordToken());
+        token.init(props);
+        at = token;
       }
     } else {
-      Properties props = new Properties();
-      int prefixLength = Property.TRACE_TOKEN_PROPERTY_PREFIX.getKey().length();
-      for (Entry<String,String> entry : loginMap.entrySet()) {
-        props.put(entry.getKey().substring(prefixLength), entry.getValue());
-      }
+      at = null;
+    }
+
+    final String table = conf.get(Property.TRACE_TABLE);
+    Scanner scanner;
+    if (null != traceUgi) {
+      try {
+        scanner = traceUgi.doAs(new PrivilegedExceptionAction<Scanner>() {
 
-      AuthenticationToken token = Property.createInstanceFromPropertyName(conf, Property.TRACE_TOKEN_TYPE,
AuthenticationToken.class, new PasswordToken());
-      token.init(props);
-      at = token;
+          @Override
+          public Scanner run() throws Exception {
+            // Make the KerberosToken inside the doAs
+            AuthenticationToken token = at;
+            if (null == token) {
+              token = new KerberosToken();
+            }
+            return getScanner(table, principal, token, sb);
+          }
+
+        });
+      } catch (IOException | InterruptedException e) {
+        throw new RuntimeException("Failed to obtain scanner", e);
+      }
+    } else {
+      if (null == at) {
+        throw new AssertionError("AuthenticationToken should not be null");
+      }
+      scanner = getScanner(table, principal, at, sb);
     }
 
-    String table = conf.get(Property.TRACE_TABLE);
+    return new AbstractMap.SimpleEntry<Scanner,UserGroupInformation>(scanner, traceUgi);
+  }
+
+  private Scanner getScanner(String table, String principal, AuthenticationToken at, StringBuilder
sb) throws AccumuloException, AccumuloSecurityException {
     try {
       Connector conn = HdfsZooInstance.getInstance().getConnector(principal, at);
       if (!conn.tableOperations().exists(table)) {

http://git-wip-us.apache.org/repos/asf/accumulo/blob/e82d6833/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ListType.java
----------------------------------------------------------------------
diff --git a/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ListType.java
b/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ListType.java
index 84322b5..0148129 100644
--- a/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ListType.java
+++ b/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ListType.java
@@ -16,6 +16,7 @@
  */
 package org.apache.accumulo.monitor.servlets.trace;
 
+import java.security.PrivilegedAction;
 import java.util.Map.Entry;
 
 import javax.servlet.http.HttpServletRequest;
@@ -31,6 +32,7 @@ import org.apache.accumulo.monitor.util.celltypes.StringType;
 import org.apache.accumulo.tracer.TraceFormatter;
 import org.apache.accumulo.tracer.thrift.RemoteSpan;
 import org.apache.hadoop.io.Text;
+import org.apache.hadoop.security.UserGroupInformation;
 
 public class ListType extends Basic {
 
@@ -46,27 +48,43 @@ public class ListType extends Basic {
 
   @Override
   public void pageBody(HttpServletRequest req, HttpServletResponse resp, StringBuilder sb)
throws Exception {
-    String type = getType(req);
+    final String type = getType(req);
     int minutes = getMinutes(req);
     long endTime = System.currentTimeMillis();
     long startTime = endTime - minutes * 60 * 1000;
-    Scanner scanner = getScanner(sb);
+    Entry<Scanner,UserGroupInformation> entry = getScanner(sb);
+    final Scanner scanner = entry.getKey();
     if (scanner == null) {
       return;
     }
     Range range = new Range(new Text("start:" + Long.toHexString(startTime)), new Text("start:"
+ Long.toHexString(endTime)));
     scanner.setRange(range);
-    Table trace = new Table("trace", "Traces for " + getType(req));
+    final Table trace = new Table("trace", "Traces for " + getType(req));
     trace.addSortableColumn("Start", new ShowTraceLinkType(), "Start Time");
     trace.addSortableColumn("ms", new DurationType(), "Span time");
     trace.addUnsortableColumn("Source", new StringType<String>(), "Service and location");
+
+    if (null != entry.getValue()) {
+      entry.getValue().doAs(new PrivilegedAction<Void>() {
+        public Void run() {
+          addRows(scanner, type, trace);
+          return null;
+        }
+      });
+    } else {
+      addRows(scanner, type, trace);
+    }
+
+    trace.generate(req, sb);
+  }
+
+  private void addRows(Scanner scanner, String type, Table trace) {
     for (Entry<Key,Value> entry : scanner) {
       RemoteSpan span = TraceFormatter.getRemoteSpan(entry);
       if (span.description.equals(type)) {
         trace.addRow(span, Long.valueOf(span.stop - span.start), span.svc + ":" + span.sender);
       }
     }
-    trace.generate(req, sb);
   }
 
   @Override

http://git-wip-us.apache.org/repos/asf/accumulo/blob/e82d6833/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ShowTrace.java
----------------------------------------------------------------------
diff --git a/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ShowTrace.java
b/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ShowTrace.java
index 214c12d..39609c3 100644
--- a/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ShowTrace.java
+++ b/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/ShowTrace.java
@@ -20,6 +20,7 @@ import static java.lang.Math.min;
 import static java.nio.charset.StandardCharsets.UTF_8;
 
 import java.nio.ByteBuffer;
+import java.security.PrivilegedAction;
 import java.util.Collection;
 import java.util.Map.Entry;
 import java.util.Set;
@@ -39,6 +40,7 @@ import org.apache.accumulo.tracer.TraceFormatter;
 import org.apache.accumulo.tracer.thrift.Annotation;
 import org.apache.accumulo.tracer.thrift.RemoteSpan;
 import org.apache.hadoop.io.Text;
+import org.apache.hadoop.security.UserGroupInformation;
 
 public class ShowTrace extends Basic {
 
@@ -58,24 +60,38 @@ public class ShowTrace extends Basic {
     return "Trace ID " + id;
   }
 
+  private long addSpans(Scanner scanner, SpanTree tree, long start) {
+    for (Entry<Key,Value> entry : scanner) {
+      RemoteSpan span = TraceFormatter.getRemoteSpan(entry);
+      tree.addNode(span);
+      start = min(start, span.start);
+    }
+    return start;
+  }
+
   @Override
   public void pageBody(HttpServletRequest req, HttpServletResponse resp, final StringBuilder
sb) throws Exception {
     String id = getTraceId(req);
     if (id == null) {
       return;
     }
-    Scanner scanner = getScanner(sb);
+    Entry<Scanner,UserGroupInformation> entry = getScanner(sb);
+    final Scanner scanner = entry.getKey();
     if (scanner == null) {
       return;
     }
     Range range = new Range(new Text(id));
     scanner.setRange(range);
-    SpanTree tree = new SpanTree();
-    long start = Long.MAX_VALUE;
-    for (Entry<Key,Value> entry : scanner) {
-      RemoteSpan span = TraceFormatter.getRemoteSpan(entry);
-      tree.addNode(span);
-      start = min(start, span.start);
+    final SpanTree tree = new SpanTree();
+    long start;
+    if (null != entry.getValue()) {
+      start = entry.getValue().doAs(new PrivilegedAction<Long>() {
+         public Long run() {
+           return addSpans(scanner, tree, Long.MAX_VALUE);
+         }
+      });
+    } else {
+      start = addSpans(scanner, tree, Long.MAX_VALUE);
     }
     sb.append("<style>\n");
     sb.append(" td.right { text-align: right }\n");

http://git-wip-us.apache.org/repos/asf/accumulo/blob/e82d6833/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Summary.java
----------------------------------------------------------------------
diff --git a/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Summary.java
b/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Summary.java
index 9c9d170..c15bbe3 100644
--- a/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Summary.java
+++ b/server/monitor/src/main/java/org/apache/accumulo/monitor/servlets/trace/Summary.java
@@ -16,6 +16,7 @@
  */
 package org.apache.accumulo.monitor.servlets.trace;
 
+import java.security.PrivilegedAction;
 import java.util.Map;
 import java.util.Map.Entry;
 import java.util.TreeMap;
@@ -35,6 +36,7 @@ import org.apache.accumulo.monitor.util.celltypes.StringType;
 import org.apache.accumulo.tracer.TraceFormatter;
 import org.apache.accumulo.tracer.thrift.RemoteSpan;
 import org.apache.hadoop.io.Text;
+import org.apache.hadoop.security.UserGroupInformation;
 
 public class Summary extends Basic {
 
@@ -144,24 +146,38 @@ public class Summary extends Basic {
     return new Range(new Text("start:" + startHexTime), new Text("start:" + endHexTime));
   }
 
+  private void parseSpans(Scanner scanner, Map<String,Stats> summary) {
+    for (Entry<Key,Value> entry : scanner) {
+      RemoteSpan span = TraceFormatter.getRemoteSpan(entry);
+      Stats stats = summary.get(span.description);
+      if (stats == null) {
+        summary.put(span.description, stats = new Stats());
+      }
+      stats.addSpan(span);
+    }
+  }
+
   @Override
   public void pageBody(HttpServletRequest req, HttpServletResponse resp, StringBuilder sb)
throws Exception {
     int minutes = getMinutes(req);
 
-    Scanner scanner = getScanner(sb);
+    Entry<Scanner,UserGroupInformation> pair = getScanner(sb);
+    final Scanner scanner = pair.getKey();
     if (scanner == null) {
       return;
     }
     Range range = getRangeForTrace(minutes);
     scanner.setRange(range);
-    Map<String,Stats> summary = new TreeMap<String,Stats>();
-    for (Entry<Key,Value> entry : scanner) {
-      RemoteSpan span = TraceFormatter.getRemoteSpan(entry);
-      Stats stats = summary.get(span.description);
-      if (stats == null) {
-        summary.put(span.description, stats = new Stats());
-      }
-      stats.addSpan(span);
+    final Map<String,Stats> summary = new TreeMap<String,Stats>();
+    if (null != pair.getValue()) {
+      pair.getValue().doAs(new PrivilegedAction<Void>() {
+        public Void run() {
+          parseSpans(scanner, summary);
+          return null;
+        }
+      });
+    } else {
+      parseSpans(scanner, summary);
     }
     Table trace = new Table("traceSummary", "All Traces");
     trace.addSortableColumn("Type", new ShowTypeLink(minutes), "Trace Type");


Mime
View raw message