Repository: hbase
Updated Branches:
  refs/heads/branch-1 9621debfa -> a2d8b0e52


HBASE-12831 Changing the set of vis labels a user has access to doesn't 
generate an audit log event

Signed-off-by: Sean Busbey <bus...@apache.org>


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

Branch: refs/heads/branch-1
Commit: a2d8b0e52bc412ed857a0b16abef34a243ffefd0
Parents: 9621deb
Author: Ashish Singhi <ashish.sin...@huawei.com>
Authored: Fri Jan 16 08:43:58 2015 +0530
Committer: Sean Busbey <bus...@apache.org>
Committed: Wed Jan 28 21:30:02 2015 -0600

----------------------------------------------------------------------
 conf/log4j.properties                           |  1 +
 .../visibility/VisibilityController.java        | 88 +++++++++++++++++---
 2 files changed, 77 insertions(+), 12 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/hbase/blob/a2d8b0e5/conf/log4j.properties
----------------------------------------------------------------------
diff --git a/conf/log4j.properties b/conf/log4j.properties
index 4e8f145..472fc03 100644
--- a/conf/log4j.properties
+++ b/conf/log4j.properties
@@ -55,6 +55,7 @@ log4j.appender.RFAS.layout.ConversionPattern=%d{ISO8601} %p 
%c: %m%n
 log4j.category.SecurityLogger=${hbase.security.logger}
 log4j.additivity.SecurityLogger=false
 
#log4j.logger.SecurityLogger.org.apache.hadoop.hbase.security.access.AccessController=TRACE
+#log4j.logger.SecurityLogger.org.apache.hadoop.hbase.security.visibility.VisibilityController=TRACE
 
 #
 # Null Appender

http://git-wip-us.apache.org/repos/asf/hbase/blob/a2d8b0e5/hbase-server/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityController.java
----------------------------------------------------------------------
diff --git 
a/hbase-server/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityController.java
 
b/hbase-server/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityController.java
index 0fbef44..d219ed2 100644
--- 
a/hbase-server/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityController.java
+++ 
b/hbase-server/src/main/java/org/apache/hadoop/hbase/security/visibility/VisibilityController.java
@@ -24,6 +24,7 @@ import static 
org.apache.hadoop.hbase.security.visibility.VisibilityConstants.LA
 import static 
org.apache.hadoop.hbase.security.visibility.VisibilityConstants.LABELS_TABLE_NAME;
 
 import java.io.IOException;
+import java.net.InetAddress;
 import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.Iterator;
@@ -38,15 +39,16 @@ import org.apache.hadoop.hbase.CellScanner;
 import org.apache.hadoop.hbase.CellUtil;
 import org.apache.hadoop.hbase.CoprocessorEnvironment;
 import org.apache.hadoop.hbase.DoNotRetryIOException;
-import org.apache.hadoop.hbase.classification.InterfaceAudience;
+import org.apache.hadoop.hbase.HBaseInterfaceAudience;
 import org.apache.hadoop.hbase.HColumnDescriptor;
 import org.apache.hadoop.hbase.HConstants;
 import org.apache.hadoop.hbase.HTableDescriptor;
-import org.apache.hadoop.hbase.TagRewriteCell;
+import org.apache.hadoop.hbase.MetaTableAccessor;
 import org.apache.hadoop.hbase.TableName;
 import org.apache.hadoop.hbase.Tag;
-import org.apache.hadoop.hbase.MetaTableAccessor;
+import org.apache.hadoop.hbase.TagRewriteCell;
 import org.apache.hadoop.hbase.TagType;
+import org.apache.hadoop.hbase.classification.InterfaceAudience;
 import org.apache.hadoop.hbase.client.Append;
 import org.apache.hadoop.hbase.client.Delete;
 import org.apache.hadoop.hbase.client.Get;
@@ -97,7 +99,6 @@ import 
org.apache.hadoop.hbase.replication.ReplicationEndpoint;
 import org.apache.hadoop.hbase.security.AccessDeniedException;
 import org.apache.hadoop.hbase.security.User;
 import org.apache.hadoop.hbase.security.access.AccessControlLists;
-import org.apache.hadoop.hbase.HBaseInterfaceAudience;
 import org.apache.hadoop.hbase.security.access.AccessController;
 import org.apache.hadoop.hbase.util.ByteStringer;
 import org.apache.hadoop.hbase.util.Bytes;
@@ -119,6 +120,8 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
     VisibilityLabelsService.Interface, CoprocessorService {
 
   private static final Log LOG = LogFactory.getLog(VisibilityController.class);
+  private static final Log AUDITLOG = LogFactory.getLog("SecurityLogger."
+      + VisibilityController.class.getName());
   // flags if we are running on a region of the 'labels' table
   private boolean labelsRegion = false;
   // Flag denoting whether AcessController is available or not.
@@ -727,9 +730,9 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
         new VisibilityControllerNotReadyException("VisibilityController not 
yet initialized!"),
         response);
     } else {
+      List<byte[]> labels = new ArrayList<byte[]>(visLabels.size());
       try {
         checkCallingUserAuth();
-        List<byte[]> labels = new ArrayList<byte[]>(visLabels.size());
         RegionActionResult successResult = 
RegionActionResult.newBuilder().build();
         for (VisibilityLabel visLabel : visLabels) {
           byte[] label = visLabel.getLabel().toByteArray();
@@ -740,6 +743,7 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
         }
         if (!labels.isEmpty()) {
           OperationStatus[] opStatus = 
this.visibilityLabelService.addLabels(labels);
+          logResult(true, "addLabels", "Adding labels allowed", null, labels, 
null);
           int i = 0;
           for (OperationStatus status : opStatus) {
             while (response.getResult(i) != successResult)
@@ -753,6 +757,10 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
             i++;
           }
         }
+      } catch (AccessDeniedException e) {
+        logResult(false, "addLabels", e.getMessage(), null, labels, null);
+        LOG.error("User is not having required permissions to add labels", e);
+        setExceptionResults(visLabels.size(), e, response);
       } catch (IOException e) {
         LOG.error(e);
         setExceptionResults(visLabels.size(), e, response);
@@ -781,14 +789,17 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
         new VisibilityControllerNotReadyException("VisibilityController not 
yet initialized!"),
         response);
     } else {
+      byte[] user = request.getUser().toByteArray();
+      List<byte[]> labelAuths = new ArrayList<byte[]>(auths.size());
       try {
         checkCallingUserAuth();
-        List<byte[]> labelAuths = new ArrayList<byte[]>(auths.size());
+
         for (ByteString authBS : auths) {
           labelAuths.add(authBS.toByteArray());
         }
-        OperationStatus[] opStatus = 
this.visibilityLabelService.setAuths(request.getUser()
-            .toByteArray(), labelAuths);
+        OperationStatus[] opStatus = 
this.visibilityLabelService.setAuths(user, labelAuths);
+        logResult(true, "setAuths", "Setting authorization for labels 
allowed", user, labelAuths,
+          null);
         RegionActionResult successResult = 
RegionActionResult.newBuilder().build();
         for (OperationStatus status : opStatus) {
           if (status.getOperationStatusCode() == SUCCESS) {
@@ -800,6 +811,10 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
             response.addResult(failureResultBuilder.build());
           }
         }
+      } catch (AccessDeniedException e) {
+        logResult(false, "setAuths", e.getMessage(), user, labelAuths, null);
+        LOG.error("User is not having required permissions to set 
authorization", e);
+        setExceptionResults(auths.size(), e, response);
       } catch (IOException e) {
         LOG.error(e);
         setExceptionResults(auths.size(), e, response);
@@ -808,6 +823,39 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
     done.run(response.build());
   }
 
+  private void logResult(boolean isAllowed, String request, String reason, 
byte[] user,
+      List<byte[]> labelAuths, String regex) {
+    if (AUDITLOG.isTraceEnabled()) {
+      RequestContext ctx = RequestContext.get();
+      InetAddress remoteAddr = null;
+      if (ctx != null) {
+        remoteAddr = ctx.getRemoteAddress();
+      }
+
+      List<String> labelAuthsStr = new ArrayList<>();
+      if (labelAuths != null) {
+        int labelAuthsSize = labelAuths.size();
+        labelAuthsStr = new ArrayList<>(labelAuthsSize);
+        for (int i = 0; i < labelAuthsSize; i++) {
+          labelAuthsStr.add(Bytes.toString(labelAuths.get(i)));
+        }
+      }
+
+      User requestingUser = null;
+      try {
+        requestingUser = VisibilityUtils.getActiveUser();
+      } catch (IOException e) {
+        LOG.warn("Failed to get active system user.");
+        LOG.debug("Details on failure to get active system user.", e);
+      }
+      AUDITLOG.trace("Access " + (isAllowed ? "allowed" : "denied") + " for 
user "
+          + (requestingUser != null ? requestingUser.getShortName() : 
"UNKNOWN") + "; reason: "
+          + reason + "; remote address: " + (remoteAddr != null ? remoteAddr : 
"") + "; request: "
+          + request + "; user: " + (user != null ? Bytes.toShort(user) : 
"null") + "; labels: "
+          + labelAuthsStr + "; regex: " + regex);
+    }
+  }
+
   @Override
   public synchronized void getAuths(RpcController controller, GetAuthsRequest 
request,
       RpcCallback<GetAuthsResponse> done) {
@@ -843,6 +891,10 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
         } else {
           labels = this.visibilityLabelService.getAuths(user, false);
         }
+        logResult(true, "getAuths", "Get authorizations for user allowed", 
user, null, null);
+      } catch (AccessDeniedException e) {
+        logResult(false, "getAuths", e.getMessage(), user, null, null);
+        ResponseConverter.setControllerException(controller, e);
       } catch (IOException e) {
         ResponseConverter.setControllerException(controller, e);
       }
@@ -865,6 +917,8 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
       setExceptionResults(auths.size(), new CoprocessorException(
           "VisibilityController not yet initialized"), response);
     } else {
+      byte[] requestUser = request.getUser().toByteArray();
+      List<byte[]> labelAuths = new ArrayList<byte[]>(auths.size());
       try {
         // When AC is ON, do AC based user auth check
         if (this.acOn && !isSystemOrSuperUser()) {
@@ -874,12 +928,14 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
         }
         checkCallingUserAuth(); // When AC is not in place the calling user 
should have SYSTEM_LABEL
                                 // auth to do this action.
-        List<byte[]> labelAuths = new ArrayList<byte[]>(auths.size());
         for (ByteString authBS : auths) {
           labelAuths.add(authBS.toByteArray());
         }
-        OperationStatus[] opStatus = 
this.visibilityLabelService.clearAuths(request.getUser()
-            .toByteArray(), labelAuths);
+
+        OperationStatus[] opStatus =
+            this.visibilityLabelService.clearAuths(requestUser, labelAuths);
+        logResult(true, "clearAuths", "Removing authorization for labels 
allowed", requestUser,
+          labelAuths, null);
         RegionActionResult successResult = 
RegionActionResult.newBuilder().build();
         for (OperationStatus status : opStatus) {
           if (status.getOperationStatusCode() == SUCCESS) {
@@ -891,6 +947,10 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
             response.addResult(failureResultBuilder.build());
           }
         }
+      } catch (AccessDeniedException e) {
+        logResult(false, "clearAuths", e.getMessage(), requestUser, 
labelAuths, null);
+        LOG.error("User is not having required permissions to clear 
authorization", e);
+        setExceptionResults(auths.size(), e, response);
       } catch (IOException e) {
         LOG.error(e);
         setExceptionResults(auths.size(), e, response);
@@ -907,6 +967,7 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
       controller.setFailed("VisibilityController not yet initialized");
     } else {
       List<String> labels = null;
+      String regex = request.hasRegex() ? request.getRegex() : null;
       try {
         // We do ACL check here as we create scanner directly on region. It 
will not make calls to
         // AccessController CP methods.
@@ -916,8 +977,11 @@ public class VisibilityController extends 
BaseMasterAndRegionObserver implements
               + (requestingUser != null ? requestingUser.getShortName() : 
"null")
               + "' is not authorized to perform this action.");
         }
-        String regex = request.hasRegex() ? request.getRegex() : null;
         labels = this.visibilityLabelService.listLabels(regex);
+        logResult(false, "listLabels", "Listing labels allowed", null, null, 
regex);
+      } catch (AccessDeniedException e) {
+        logResult(false, "listLabels", e.getMessage(), null, null, regex);
+        ResponseConverter.setControllerException(controller, e);
       } catch (IOException e) {
         ResponseConverter.setControllerException(controller, e);
       }

Reply via email to