HBASE-21739 Move grant/revoke from regionserver to master
Signed-off-by: Guanghao Zhang <zghao@apache.org>
This commit is contained in:
parent
32f3745e63
commit
ec9029f77e
|
@ -52,6 +52,7 @@ import org.apache.hadoop.hbase.regionserver.wal.FailedLogCloseException;
|
|||
import org.apache.hadoop.hbase.replication.ReplicationException;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerConfig;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerDescription;
|
||||
import org.apache.hadoop.hbase.security.access.UserPermission;
|
||||
import org.apache.hadoop.hbase.snapshot.HBaseSnapshotException;
|
||||
import org.apache.hadoop.hbase.snapshot.RestoreSnapshotException;
|
||||
import org.apache.hadoop.hbase.snapshot.SnapshotCreationException;
|
||||
|
@ -2794,4 +2795,23 @@ public interface Admin extends Abortable, Closeable {
|
|||
* no quota information on that table.
|
||||
*/
|
||||
SpaceQuotaSnapshotView getCurrentSpaceQuotaSnapshot(TableName tableName) throws IOException;
|
||||
|
||||
/**
|
||||
* Grants user specific permissions
|
||||
*
|
||||
* @param userPermission user and permissions
|
||||
* @param mergeExistingPermissions If set to false, later granted permissions will override
|
||||
* previous granted permissions. otherwise, it'll merge with previous granted
|
||||
* permissions.
|
||||
* @throws IOException if a remote or network exception occurs
|
||||
*/
|
||||
void grant(UserPermission userPermission, boolean mergeExistingPermissions) throws IOException;
|
||||
|
||||
/**
|
||||
* Revokes user specific permissions
|
||||
*
|
||||
* @param userPermission user and permissions
|
||||
* @throws IOException if a remote or network exception occurs
|
||||
*/
|
||||
void revoke(UserPermission userPermission) throws IOException;
|
||||
}
|
||||
|
|
|
@ -41,6 +41,7 @@ import org.apache.hadoop.hbase.quotas.QuotaSettings;
|
|||
import org.apache.hadoop.hbase.quotas.SpaceQuotaSnapshotView;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerConfig;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerDescription;
|
||||
import org.apache.hadoop.hbase.security.access.UserPermission;
|
||||
import org.apache.yetus.audience.InterfaceAudience;
|
||||
|
||||
/**
|
||||
|
@ -1293,4 +1294,19 @@ public interface AsyncAdmin {
|
|||
*/
|
||||
CompletableFuture<? extends SpaceQuotaSnapshotView> getCurrentSpaceQuotaSnapshot(
|
||||
TableName tableName);
|
||||
|
||||
/**
|
||||
* Grants user specific permissions
|
||||
* @param userPermission user and permissions
|
||||
* @param mergeExistingPermissions If set to false, later granted permissions will override
|
||||
* previous granted permissions. otherwise, it'll merge with previous granted
|
||||
* permissions.
|
||||
*/
|
||||
CompletableFuture<Void> grant(UserPermission userPermission, boolean mergeExistingPermissions);
|
||||
|
||||
/**
|
||||
* Revokes user specific permissions
|
||||
* @param userPermission user and permissions
|
||||
*/
|
||||
CompletableFuture<Void> revoke(UserPermission userPermission);
|
||||
}
|
||||
|
|
|
@ -41,6 +41,7 @@ import org.apache.hadoop.hbase.quotas.QuotaSettings;
|
|||
import org.apache.hadoop.hbase.quotas.SpaceQuotaSnapshot;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerConfig;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerDescription;
|
||||
import org.apache.hadoop.hbase.security.access.UserPermission;
|
||||
import org.apache.yetus.audience.InterfaceAudience;
|
||||
|
||||
/**
|
||||
|
@ -789,4 +790,15 @@ class AsyncHBaseAdmin implements AsyncAdmin {
|
|||
public CompletableFuture<SpaceQuotaSnapshot> getCurrentSpaceQuotaSnapshot(TableName tableName) {
|
||||
return wrap(rawAdmin.getCurrentSpaceQuotaSnapshot(tableName));
|
||||
}
|
||||
|
||||
@Override
|
||||
public CompletableFuture<Void> grant(UserPermission userPermission,
|
||||
boolean mergeExistingPermissions) {
|
||||
return wrap(rawAdmin.grant(userPermission, mergeExistingPermissions));
|
||||
}
|
||||
|
||||
@Override
|
||||
public CompletableFuture<Void> revoke(UserPermission userPermission) {
|
||||
return wrap(rawAdmin.revoke(userPermission));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -92,6 +92,7 @@ import org.apache.hbase.thirdparty.com.google.protobuf.ServiceException;
|
|||
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.RequestConverter;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.ClientProtos;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.ClientProtos.ClientService.BlockingInterface;
|
||||
|
@ -1765,6 +1766,18 @@ class ConnectionImplementation implements ClusterConnection, Closeable {
|
|||
IsRpcThrottleEnabledRequest request) throws ServiceException {
|
||||
return stub.isRpcThrottleEnabled(controller, request);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AccessControlProtos.GrantResponse grant(RpcController controller,
|
||||
AccessControlProtos.GrantRequest request) throws ServiceException {
|
||||
return stub.grant(controller, request);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AccessControlProtos.RevokeResponse revoke(RpcController controller,
|
||||
AccessControlProtos.RevokeRequest request) throws ServiceException {
|
||||
return stub.revoke(controller, request);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
@ -90,6 +90,8 @@ import org.apache.hadoop.hbase.regionserver.wal.FailedLogCloseException;
|
|||
import org.apache.hadoop.hbase.replication.ReplicationException;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerConfig;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerDescription;
|
||||
import org.apache.hadoop.hbase.security.access.ShadedAccessControlUtil;
|
||||
import org.apache.hadoop.hbase.security.access.UserPermission;
|
||||
import org.apache.hadoop.hbase.snapshot.ClientSnapshotDescriptionUtils;
|
||||
import org.apache.hadoop.hbase.snapshot.HBaseSnapshotException;
|
||||
import org.apache.hadoop.hbase.snapshot.RestoreSnapshotException;
|
||||
|
@ -112,6 +114,8 @@ import org.apache.hbase.thirdparty.com.google.protobuf.ServiceException;
|
|||
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.RequestConverter;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GrantRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.RevokeRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos.AdminService;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos.ClearCompactionQueuesRequest;
|
||||
|
@ -4438,4 +4442,30 @@ public class HBaseAdmin implements Admin {
|
|||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void grant(UserPermission userPermission, boolean mergeExistingPermissions)
|
||||
throws IOException {
|
||||
executeCallable(new MasterCallable<Void>(getConnection(), getRpcControllerFactory()) {
|
||||
@Override
|
||||
protected Void rpcCall() throws Exception {
|
||||
GrantRequest req =
|
||||
ShadedAccessControlUtil.buildGrantRequest(userPermission, mergeExistingPermissions);
|
||||
this.master.grant(getRpcController(), req);
|
||||
return null;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void revoke(UserPermission userPermission) throws IOException {
|
||||
executeCallable(new MasterCallable<Void>(getConnection(), getRpcControllerFactory()) {
|
||||
@Override
|
||||
protected Void rpcCall() throws Exception {
|
||||
RevokeRequest req = ShadedAccessControlUtil.buildRevokeRequest(userPermission);
|
||||
this.master.revoke(getRpcController(), req);
|
||||
return null;
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
|
@ -81,6 +81,8 @@ import org.apache.hadoop.hbase.quotas.SpaceQuotaSnapshot;
|
|||
import org.apache.hadoop.hbase.replication.ReplicationException;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerConfig;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerDescription;
|
||||
import org.apache.hadoop.hbase.security.access.ShadedAccessControlUtil;
|
||||
import org.apache.hadoop.hbase.security.access.UserPermission;
|
||||
import org.apache.hadoop.hbase.snapshot.ClientSnapshotDescriptionUtils;
|
||||
import org.apache.hadoop.hbase.snapshot.RestoreSnapshotException;
|
||||
import org.apache.hadoop.hbase.snapshot.SnapshotCreationException;
|
||||
|
@ -100,6 +102,10 @@ import org.apache.hbase.thirdparty.io.netty.util.TimerTask;
|
|||
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.RequestConverter;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GrantRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GrantResponse;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.RevokeRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.RevokeResponse;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos.AdminService;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos.ClearCompactionQueuesRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos.ClearCompactionQueuesResponse;
|
||||
|
@ -3699,4 +3705,23 @@ class RawAsyncHBaseAdmin implements AsyncAdmin {
|
|||
.filter(s -> s.getTableName().equals(protoTableName)).findFirst()
|
||||
.map(s -> SpaceQuotaSnapshot.toSpaceQuotaSnapshot(s.getSnapshot())).orElse(null));
|
||||
}
|
||||
|
||||
@Override
|
||||
public CompletableFuture<Void> grant(UserPermission userPermission,
|
||||
boolean mergeExistingPermissions) {
|
||||
return this.<Void> newMasterCaller()
|
||||
.action((controller, stub) -> this.<GrantRequest, GrantResponse, Void> call(controller,
|
||||
stub, ShadedAccessControlUtil.buildGrantRequest(userPermission, mergeExistingPermissions),
|
||||
(s, c, req, done) -> s.grant(c, req, done), resp -> null))
|
||||
.call();
|
||||
}
|
||||
|
||||
@Override
|
||||
public CompletableFuture<Void> revoke(UserPermission userPermission) {
|
||||
return this.<Void> newMasterCaller()
|
||||
.action((controller, stub) -> this.<RevokeRequest, RevokeResponse, Void> call(controller,
|
||||
stub, ShadedAccessControlUtil.buildRevokeRequest(userPermission),
|
||||
(s, c, req, done) -> s.revoke(c, req, done), resp -> null))
|
||||
.call();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -20,6 +20,11 @@ package org.apache.hadoop.hbase.client;
|
|||
import org.apache.yetus.audience.InterfaceAudience;
|
||||
import org.apache.hbase.thirdparty.com.google.protobuf.RpcController;
|
||||
import org.apache.hbase.thirdparty.com.google.protobuf.ServiceException;
|
||||
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GrantRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GrantResponse;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.RevokeRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.RevokeResponse;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.ClientProtos.CoprocessorServiceRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.ClientProtos.CoprocessorServiceResponse;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.MasterProtos.AbortProcedureRequest;
|
||||
|
@ -654,4 +659,16 @@ public class ShortCircuitMasterConnection implements MasterKeepAliveConnection {
|
|||
IsRpcThrottleEnabledRequest request) throws ServiceException {
|
||||
return stub.isRpcThrottleEnabled(controller, request);
|
||||
}
|
||||
|
||||
@Override
|
||||
public GrantResponse grant(RpcController controller, GrantRequest request)
|
||||
throws ServiceException {
|
||||
return stub.grant(controller, request);
|
||||
}
|
||||
|
||||
@Override
|
||||
public RevokeResponse revoke(RpcController controller, RevokeRequest request)
|
||||
throws ServiceException {
|
||||
return stub.revoke(controller, request);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -94,10 +94,9 @@ public class AccessControlClient {
|
|||
final String userName, final byte[] family, final byte[] qual, boolean mergeExistingPermissions,
|
||||
final Permission.Action... actions) throws Throwable {
|
||||
// TODO: Priority is not used.
|
||||
try (Table table = connection.getTable(ACL_TABLE_NAME)) {
|
||||
AccessControlUtil.grant(null, getAccessControlServiceStub(table), userName, tableName,
|
||||
family, qual, mergeExistingPermissions, actions);
|
||||
}
|
||||
UserPermission userPermission =
|
||||
new UserPermission(userName, new TablePermission(tableName, family, qual, actions));
|
||||
connection.getAdmin().grant(userPermission, mergeExistingPermissions);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -129,11 +128,9 @@ public class AccessControlClient {
|
|||
*/
|
||||
private static void grant(Connection connection, final String namespace, final String userName,
|
||||
boolean mergeExistingPermissions, final Permission.Action... actions) throws Throwable {
|
||||
// TODO: Pass an rpcController.
|
||||
try (Table table = connection.getTable(ACL_TABLE_NAME)) {
|
||||
AccessControlUtil.grant(null, getAccessControlServiceStub(table), userName, namespace,
|
||||
mergeExistingPermissions, actions);
|
||||
}
|
||||
UserPermission userPermission =
|
||||
new UserPermission(userName, new NamespacePermission(namespace, actions));
|
||||
connection.getAdmin().grant(userPermission, mergeExistingPermissions);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -152,7 +149,7 @@ public class AccessControlClient {
|
|||
}
|
||||
|
||||
/**
|
||||
* Grants permission on the specified namespace for the specified user.
|
||||
* Grant global permissions for the specified user.
|
||||
* @param connection
|
||||
* @param userName
|
||||
* @param mergeExistingPermissions If set to false, later granted permissions will override
|
||||
|
@ -163,11 +160,8 @@ public class AccessControlClient {
|
|||
*/
|
||||
private static void grant(Connection connection, final String userName,
|
||||
boolean mergeExistingPermissions, final Permission.Action... actions) throws Throwable {
|
||||
// TODO: Pass an rpcController
|
||||
try (Table table = connection.getTable(ACL_TABLE_NAME)) {
|
||||
AccessControlUtil.grant(null, getAccessControlServiceStub(table), userName,
|
||||
mergeExistingPermissions, actions);
|
||||
}
|
||||
UserPermission userPermission = new UserPermission(userName, new GlobalPermission(actions));
|
||||
connection.getAdmin().grant(userPermission, mergeExistingPermissions);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -204,19 +198,13 @@ public class AccessControlClient {
|
|||
public static void revoke(Connection connection, final TableName tableName,
|
||||
final String username, final byte[] family, final byte[] qualifier,
|
||||
final Permission.Action... actions) throws Throwable {
|
||||
/** TODO: Pass an rpcController
|
||||
HBaseRpcController controller
|
||||
= ((ClusterConnection) connection).getRpcControllerFactory().newController();
|
||||
controller.setPriority(tableName);
|
||||
*/
|
||||
try (Table table = connection.getTable(ACL_TABLE_NAME)) {
|
||||
AccessControlUtil.revoke(null, getAccessControlServiceStub(table), username, tableName,
|
||||
family, qualifier, actions);
|
||||
}
|
||||
UserPermission userPermission =
|
||||
new UserPermission(username, new TablePermission(tableName, family, qualifier, actions));
|
||||
connection.getAdmin().revoke(userPermission);
|
||||
}
|
||||
|
||||
/**
|
||||
* Revokes the permission on the table for the specified user.
|
||||
* Revokes the permission on the namespace for the specified user.
|
||||
* @param connection The Connection instance to use
|
||||
* @param namespace
|
||||
* @param userName
|
||||
|
@ -225,14 +213,9 @@ public class AccessControlClient {
|
|||
*/
|
||||
public static void revoke(Connection connection, final String namespace,
|
||||
final String userName, final Permission.Action... actions) throws Throwable {
|
||||
/** TODO: Pass an rpcController
|
||||
HBaseRpcController controller
|
||||
= ((ClusterConnection) connection).getRpcControllerFactory().newController();
|
||||
*/
|
||||
try (Table table = connection.getTable(ACL_TABLE_NAME)) {
|
||||
AccessControlUtil.revoke(null, getAccessControlServiceStub(table), userName, namespace,
|
||||
actions);
|
||||
}
|
||||
UserPermission userPermission =
|
||||
new UserPermission(userName, new NamespacePermission(namespace, actions));
|
||||
connection.getAdmin().revoke(userPermission);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -241,13 +224,8 @@ public class AccessControlClient {
|
|||
*/
|
||||
public static void revoke(Connection connection, final String userName,
|
||||
final Permission.Action... actions) throws Throwable {
|
||||
/** TODO: Pass an rpc controller.
|
||||
HBaseRpcController controller
|
||||
= ((ClusterConnection) connection).getRpcControllerFactory().newController();
|
||||
*/
|
||||
try (Table table = connection.getTable(ACL_TABLE_NAME)) {
|
||||
AccessControlUtil.revoke(null, getAccessControlServiceStub(table), userName, actions);
|
||||
}
|
||||
UserPermission userPermission = new UserPermission(userName, new GlobalPermission(actions));
|
||||
connection.getAdmin().revoke(userPermission);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -25,6 +25,7 @@ import java.util.Map;
|
|||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.apache.hadoop.hbase.HConstants;
|
||||
import org.apache.hadoop.hbase.TableName;
|
||||
import org.apache.hadoop.hbase.client.Admin;
|
||||
import org.apache.yetus.audience.InterfaceAudience;
|
||||
import org.apache.hadoop.hbase.protobuf.ProtobufUtil;
|
||||
import org.apache.hadoop.hbase.protobuf.generated.AccessControlProtos;
|
||||
|
@ -490,7 +491,9 @@ public class AccessControlUtil {
|
|||
* @param userShortName the short name of the user to grant permissions
|
||||
* @param actions the permissions to be granted
|
||||
* @throws ServiceException
|
||||
* @deprecated Use {@link Admin#grant(UserPermission, boolean)} instead.
|
||||
*/
|
||||
@Deprecated
|
||||
public static void grant(RpcController controller,
|
||||
AccessControlService.BlockingInterface protocol, String userShortName, boolean mergeExistingPermissions,
|
||||
Permission.Action... actions) throws ServiceException {
|
||||
|
@ -517,7 +520,9 @@ public class AccessControlUtil {
|
|||
* @param q optional qualifier
|
||||
* @param actions the permissions to be granted
|
||||
* @throws ServiceException
|
||||
* @deprecated Use {@link Admin#grant(UserPermission, boolean)} instead.
|
||||
*/
|
||||
@Deprecated
|
||||
public static void grant(RpcController controller,
|
||||
AccessControlService.BlockingInterface protocol, String userShortName, TableName tableName,
|
||||
byte[] f, byte[] q, boolean mergeExistingPermissions, Permission.Action... actions)
|
||||
|
@ -543,7 +548,9 @@ public class AccessControlUtil {
|
|||
* @param namespace the short name of the user to grant permissions
|
||||
* @param actions the permissions to be granted
|
||||
* @throws ServiceException
|
||||
* @deprecated Use {@link Admin#grant(UserPermission, boolean)} instead.
|
||||
*/
|
||||
@Deprecated
|
||||
public static void grant(RpcController controller,
|
||||
AccessControlService.BlockingInterface protocol, String userShortName, String namespace,
|
||||
boolean mergeExistingPermissions, Permission.Action... actions) throws ServiceException {
|
||||
|
@ -567,7 +574,9 @@ public class AccessControlUtil {
|
|||
* @param userShortName the short name of the user to revoke permissions
|
||||
* @param actions the permissions to be revoked
|
||||
* @throws ServiceException on failure
|
||||
* @deprecated Use {@link Admin#grant(UserPermission, boolean)} instead.
|
||||
*/
|
||||
@Deprecated
|
||||
public static void revoke(RpcController controller,
|
||||
AccessControlService.BlockingInterface protocol, String userShortName,
|
||||
Permission.Action... actions) throws ServiceException {
|
||||
|
@ -595,7 +604,9 @@ public class AccessControlUtil {
|
|||
* @param q optional qualifier
|
||||
* @param actions the permissions to be revoked
|
||||
* @throws ServiceException on failure
|
||||
* @deprecated Use {@link Admin#grant(UserPermission, boolean)} instead.
|
||||
*/
|
||||
@Deprecated
|
||||
public static void revoke(RpcController controller,
|
||||
AccessControlService.BlockingInterface protocol, String userShortName, TableName tableName,
|
||||
byte[] f, byte[] q, Permission.Action... actions) throws ServiceException {
|
||||
|
@ -620,7 +631,9 @@ public class AccessControlUtil {
|
|||
* @param namespace optional table name
|
||||
* @param actions the permissions to be revoked
|
||||
* @throws ServiceException on failure
|
||||
* @deprecated Use {@link Admin#grant(UserPermission, boolean)} instead.
|
||||
*/
|
||||
@Deprecated
|
||||
public static void revoke(RpcController controller,
|
||||
AccessControlService.BlockingInterface protocol, String userShortName, String namespace,
|
||||
Permission.Action... actions) throws ServiceException {
|
||||
|
|
|
@ -18,20 +18,21 @@
|
|||
|
||||
package org.apache.hadoop.hbase.security.access;
|
||||
|
||||
|
||||
import org.apache.hbase.thirdparty.com.google.common.collect.ArrayListMultimap;
|
||||
import org.apache.hbase.thirdparty.com.google.common.collect.ListMultimap;
|
||||
import org.apache.hadoop.hbase.TableName;
|
||||
import org.apache.yetus.audience.InterfaceAudience;
|
||||
import org.apache.hadoop.hbase.security.access.Permission.Action;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.HBaseProtos;
|
||||
import org.apache.hbase.thirdparty.com.google.protobuf.ByteString;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import org.apache.hadoop.hbase.TableName;
|
||||
import org.apache.hadoop.hbase.security.access.Permission.Action;
|
||||
import org.apache.yetus.audience.InterfaceAudience;
|
||||
|
||||
import org.apache.hbase.thirdparty.com.google.common.collect.ArrayListMultimap;
|
||||
import org.apache.hbase.thirdparty.com.google.common.collect.ListMultimap;
|
||||
import org.apache.hbase.thirdparty.com.google.protobuf.ByteString;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GrantRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.RevokeRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.HBaseProtos;
|
||||
|
||||
/**
|
||||
* Convert protobuf objects in AccessControl.proto under hbase-protocol-shaded to user-oriented
|
||||
|
@ -49,20 +50,18 @@ public class ShadedAccessControlUtil {
|
|||
/**
|
||||
* Convert a client user permission to a user permission shaded proto.
|
||||
*/
|
||||
public static
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Action
|
||||
toPermissionAction(Permission.Action action) {
|
||||
public static AccessControlProtos.Permission.Action toPermissionAction(Permission.Action action) {
|
||||
switch (action) {
|
||||
case READ:
|
||||
return org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Action.READ;
|
||||
case WRITE:
|
||||
return org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Action.WRITE;
|
||||
case EXEC:
|
||||
return org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Action.EXEC;
|
||||
case CREATE:
|
||||
return org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Action.CREATE;
|
||||
case ADMIN:
|
||||
return org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Action.ADMIN;
|
||||
case READ:
|
||||
return AccessControlProtos.Permission.Action.READ;
|
||||
case WRITE:
|
||||
return AccessControlProtos.Permission.Action.WRITE;
|
||||
case EXEC:
|
||||
return AccessControlProtos.Permission.Action.EXEC;
|
||||
case CREATE:
|
||||
return AccessControlProtos.Permission.Action.CREATE;
|
||||
case ADMIN:
|
||||
return AccessControlProtos.Permission.Action.ADMIN;
|
||||
}
|
||||
throw new IllegalArgumentException("Unknown action value " + action.name());
|
||||
}
|
||||
|
@ -70,8 +69,7 @@ public class ShadedAccessControlUtil {
|
|||
/**
|
||||
* Convert a Permission.Action shaded proto to a client Permission.Action object.
|
||||
*/
|
||||
public static Permission.Action toPermissionAction(
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Action action) {
|
||||
public static Permission.Action toPermissionAction(AccessControlProtos.Permission.Action action) {
|
||||
switch (action) {
|
||||
case READ:
|
||||
return Permission.Action.READ;
|
||||
|
@ -94,9 +92,9 @@ public class ShadedAccessControlUtil {
|
|||
* @return the converted list of Actions
|
||||
*/
|
||||
public static List<Permission.Action> toPermissionActions(
|
||||
List<org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Action> protoActions) {
|
||||
List<AccessControlProtos.Permission.Action> protoActions) {
|
||||
List<Permission.Action> actions = new ArrayList<>(protoActions.size());
|
||||
for (org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Action a : protoActions) {
|
||||
for (AccessControlProtos.Permission.Action a : protoActions) {
|
||||
actions.add(toPermissionAction(a));
|
||||
}
|
||||
return actions;
|
||||
|
@ -163,20 +161,15 @@ public class ShadedAccessControlUtil {
|
|||
* @param perm the client Permission
|
||||
* @return the protobuf Permission
|
||||
*/
|
||||
public static org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission
|
||||
toPermission(Permission perm) {
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Builder ret =
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission
|
||||
.newBuilder();
|
||||
public static AccessControlProtos.Permission toPermission(Permission perm) {
|
||||
AccessControlProtos.Permission.Builder ret = AccessControlProtos.Permission.newBuilder();
|
||||
if (perm instanceof NamespacePermission) {
|
||||
NamespacePermission nsPerm = (NamespacePermission) perm;
|
||||
ret.setType(
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Type.Namespace);
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.NamespacePermission.Builder builder =
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.NamespacePermission
|
||||
.newBuilder();
|
||||
ret.setType(AccessControlProtos.Permission.Type.Namespace);
|
||||
AccessControlProtos.NamespacePermission.Builder builder =
|
||||
AccessControlProtos.NamespacePermission.newBuilder();
|
||||
builder.setNamespaceName(org.apache.hbase.thirdparty.com.google.protobuf.ByteString
|
||||
.copyFromUtf8(nsPerm.getNamespace()));
|
||||
.copyFromUtf8(nsPerm.getNamespace()));
|
||||
Permission.Action[] actions = perm.getActions();
|
||||
if (actions != null) {
|
||||
for (Permission.Action a : actions) {
|
||||
|
@ -186,11 +179,9 @@ public class ShadedAccessControlUtil {
|
|||
ret.setNamespacePermission(builder);
|
||||
} else if (perm instanceof TablePermission) {
|
||||
TablePermission tablePerm = (TablePermission) perm;
|
||||
ret.setType(
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Type.Table);
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.TablePermission.Builder builder =
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.TablePermission
|
||||
.newBuilder();
|
||||
ret.setType(AccessControlProtos.Permission.Type.Table);
|
||||
AccessControlProtos.TablePermission.Builder builder =
|
||||
AccessControlProtos.TablePermission.newBuilder();
|
||||
builder.setTableName(toProtoTableName(tablePerm.getTableName()));
|
||||
if (tablePerm.hasFamily()) {
|
||||
builder.setFamily(ByteString.copyFrom(tablePerm.getFamily()));
|
||||
|
@ -207,11 +198,9 @@ public class ShadedAccessControlUtil {
|
|||
ret.setTablePermission(builder);
|
||||
} else {
|
||||
// perm.getAccessScope() == Permission.Scope.GLOBAL
|
||||
ret.setType(
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.Permission.Type.Global);
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GlobalPermission.Builder builder =
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GlobalPermission
|
||||
.newBuilder();
|
||||
ret.setType(AccessControlProtos.Permission.Type.Global);
|
||||
AccessControlProtos.GlobalPermission.Builder builder =
|
||||
AccessControlProtos.GlobalPermission.newBuilder();
|
||||
Permission.Action[] actions = perm.getActions();
|
||||
if (actions != null) {
|
||||
for (Permission.Action a : actions) {
|
||||
|
@ -230,9 +219,9 @@ public class ShadedAccessControlUtil {
|
|||
* @return the converted UserPermission
|
||||
*/
|
||||
public static ListMultimap<String, Permission> toUserTablePermissions(
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.UsersAndPermissions proto) {
|
||||
AccessControlProtos.UsersAndPermissions proto) {
|
||||
ListMultimap<String, Permission> perms = ArrayListMultimap.create();
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.UsersAndPermissions.UserPermissions userPerm;
|
||||
AccessControlProtos.UsersAndPermissions.UserPermissions userPerm;
|
||||
for (int i = 0; i < proto.getUserPermissionsCount(); i++) {
|
||||
userPerm = proto.getUserPermissions(i);
|
||||
for (int j = 0; j < userPerm.getPermissionsCount(); j++) {
|
||||
|
@ -249,16 +238,13 @@ public class ShadedAccessControlUtil {
|
|||
* @param perm the list of user and table permissions
|
||||
* @return the protobuf UserTablePermissions
|
||||
*/
|
||||
public static
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.UsersAndPermissions
|
||||
public static AccessControlProtos.UsersAndPermissions
|
||||
toUserTablePermissions(ListMultimap<String, UserPermission> perm) {
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.UsersAndPermissions.Builder builder =
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.UsersAndPermissions
|
||||
.newBuilder();
|
||||
AccessControlProtos.UsersAndPermissions.Builder builder =
|
||||
AccessControlProtos.UsersAndPermissions.newBuilder();
|
||||
for (Map.Entry<String, Collection<UserPermission>> entry : perm.asMap().entrySet()) {
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.UsersAndPermissions.UserPermissions.Builder userPermBuilder =
|
||||
org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.UsersAndPermissions.UserPermissions
|
||||
.newBuilder();
|
||||
AccessControlProtos.UsersAndPermissions.UserPermissions.Builder userPermBuilder =
|
||||
AccessControlProtos.UsersAndPermissions.UserPermissions.newBuilder();
|
||||
userPermBuilder.setUser(ByteString.copyFromUtf8(entry.getKey()));
|
||||
for (UserPermission userPerm : entry.getValue()) {
|
||||
userPermBuilder.addPermissions(toPermission(userPerm.getPermission()));
|
||||
|
@ -267,4 +253,34 @@ public class ShadedAccessControlUtil {
|
|||
}
|
||||
return builder.build();
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts a user permission proto to a client user permission object.
|
||||
* @param proto the protobuf UserPermission
|
||||
* @return the converted UserPermission
|
||||
*/
|
||||
public static UserPermission toUserPermission(AccessControlProtos.UserPermission proto) {
|
||||
return new UserPermission(proto.getUser().toStringUtf8(), toPermission(proto.getPermission()));
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert a client user permission to a user permission proto
|
||||
* @param perm the client UserPermission
|
||||
* @return the protobuf UserPermission
|
||||
*/
|
||||
public static AccessControlProtos.UserPermission toUserPermission(UserPermission perm) {
|
||||
return AccessControlProtos.UserPermission.newBuilder()
|
||||
.setUser(ByteString.copyFromUtf8(perm.getUser()))
|
||||
.setPermission(toPermission(perm.getPermission())).build();
|
||||
}
|
||||
|
||||
public static GrantRequest buildGrantRequest(UserPermission userPermission,
|
||||
boolean mergeExistingPermissions) {
|
||||
return GrantRequest.newBuilder().setUserPermission(toUserPermission(userPermission))
|
||||
.setMergeExistingPermissions(mergeExistingPermissions).build();
|
||||
}
|
||||
|
||||
public static RevokeRequest buildRevokeRequest(UserPermission userPermission) {
|
||||
return RevokeRequest.newBuilder().setUserPermission(toUserPermission(userPermission)).build();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -36,6 +36,7 @@ import "Procedure.proto";
|
|||
import "Quota.proto";
|
||||
import "Replication.proto";
|
||||
import "Snapshot.proto";
|
||||
import "AccessControl.proto";
|
||||
|
||||
/* Column-level protobufs */
|
||||
|
||||
|
@ -1010,6 +1011,10 @@ service MasterService {
|
|||
/** Get if is rpc throttled enabled */
|
||||
rpc IsRpcThrottleEnabled (IsRpcThrottleEnabledRequest)
|
||||
returns (IsRpcThrottleEnabledResponse);
|
||||
|
||||
rpc Grant(GrantRequest) returns (GrantResponse);
|
||||
|
||||
rpc Revoke(RevokeRequest) returns (RevokeResponse);
|
||||
}
|
||||
|
||||
// HBCK Service definitions.
|
||||
|
|
|
@ -36,6 +36,7 @@ import org.apache.hadoop.hbase.master.RegionPlan;
|
|||
import org.apache.hadoop.hbase.net.Address;
|
||||
import org.apache.hadoop.hbase.quotas.GlobalQuotaSettings;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerConfig;
|
||||
import org.apache.hadoop.hbase.security.access.UserPermission;
|
||||
import org.apache.yetus.audience.InterfaceAudience;
|
||||
import org.apache.yetus.audience.InterfaceStability;
|
||||
|
||||
|
@ -1486,4 +1487,42 @@ public interface MasterObserver {
|
|||
default void postIsRpcThrottleEnabled(final ObserverContext<MasterCoprocessorEnvironment> ctx,
|
||||
final boolean rpcThrottleEnabled) throws IOException {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called before granting user permissions.
|
||||
* @param ctx the coprocessor instance's environment
|
||||
* @param userPermission the user and permissions
|
||||
* @param mergeExistingPermissions True if merge with previous granted permissions
|
||||
*/
|
||||
default void preGrant(ObserverContext<MasterCoprocessorEnvironment> ctx,
|
||||
UserPermission userPermission, boolean mergeExistingPermissions) throws IOException {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called after granting user permissions.
|
||||
* @param ctx the coprocessor instance's environment
|
||||
* @param userPermission the user and permissions
|
||||
* @param mergeExistingPermissions True if merge with previous granted permissions
|
||||
*/
|
||||
default void postGrant(ObserverContext<MasterCoprocessorEnvironment> ctx,
|
||||
UserPermission userPermission, boolean mergeExistingPermissions) throws IOException {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called before revoking user permissions.
|
||||
* @param ctx the coprocessor instance's environment
|
||||
* @param userPermission the user and permissions
|
||||
*/
|
||||
default void preRevoke(ObserverContext<MasterCoprocessorEnvironment> ctx,
|
||||
UserPermission userPermission) throws IOException {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called after revoking user permissions.
|
||||
* @param ctx the coprocessor instance's environment
|
||||
* @param userPermission the user and permissions
|
||||
*/
|
||||
default void postRevoke(ObserverContext<MasterCoprocessorEnvironment> ctx,
|
||||
UserPermission userPermission) throws IOException {
|
||||
}
|
||||
}
|
||||
|
|
|
@ -57,6 +57,7 @@ import org.apache.hadoop.hbase.procedure2.ProcedureExecutor;
|
|||
import org.apache.hadoop.hbase.quotas.GlobalQuotaSettings;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerConfig;
|
||||
import org.apache.hadoop.hbase.security.User;
|
||||
import org.apache.hadoop.hbase.security.access.UserPermission;
|
||||
import org.apache.yetus.audience.InterfaceAudience;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
@ -1740,4 +1741,42 @@ public class MasterCoprocessorHost
|
|||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void preGrant(UserPermission userPermission, boolean mergeExistingPermissions)
|
||||
throws IOException {
|
||||
execOperation(coprocEnvironments.isEmpty() ? null : new MasterObserverOperation() {
|
||||
@Override
|
||||
public void call(MasterObserver observer) throws IOException {
|
||||
observer.preGrant(this, userPermission, mergeExistingPermissions);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void postGrant(UserPermission userPermission, boolean mergeExistingPermissions)
|
||||
throws IOException {
|
||||
execOperation(coprocEnvironments.isEmpty() ? null : new MasterObserverOperation() {
|
||||
@Override
|
||||
public void call(MasterObserver observer) throws IOException {
|
||||
observer.postGrant(this, userPermission, mergeExistingPermissions);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void preRevoke(UserPermission userPermission) throws IOException {
|
||||
execOperation(coprocEnvironments.isEmpty() ? null : new MasterObserverOperation() {
|
||||
@Override
|
||||
public void call(MasterObserver observer) throws IOException {
|
||||
observer.preRevoke(this, userPermission);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void postRevoke(UserPermission userPermission) throws IOException {
|
||||
execOperation(coprocEnvironments.isEmpty() ? null : new MasterObserverOperation() {
|
||||
@Override
|
||||
public void call(MasterObserver observer) throws IOException {
|
||||
observer.postRevoke(this, userPermission);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
|
@ -49,6 +49,7 @@ import org.apache.hadoop.hbase.client.ColumnFamilyDescriptor;
|
|||
import org.apache.hadoop.hbase.client.MasterSwitchType;
|
||||
import org.apache.hadoop.hbase.client.RegionInfo;
|
||||
import org.apache.hadoop.hbase.client.RegionInfoBuilder;
|
||||
import org.apache.hadoop.hbase.client.Table;
|
||||
import org.apache.hadoop.hbase.client.TableDescriptor;
|
||||
import org.apache.hadoop.hbase.client.TableState;
|
||||
import org.apache.hadoop.hbase.client.VersionInfoUtil;
|
||||
|
@ -92,8 +93,11 @@ import org.apache.hadoop.hbase.replication.ReplicationPeerConfig;
|
|||
import org.apache.hadoop.hbase.replication.ReplicationPeerDescription;
|
||||
import org.apache.hadoop.hbase.security.User;
|
||||
import org.apache.hadoop.hbase.security.access.AccessChecker;
|
||||
import org.apache.hadoop.hbase.security.access.AccessControlLists;
|
||||
import org.apache.hadoop.hbase.security.access.AccessController;
|
||||
import org.apache.hadoop.hbase.security.access.Permission;
|
||||
import org.apache.hadoop.hbase.security.access.ShadedAccessControlUtil;
|
||||
import org.apache.hadoop.hbase.security.access.UserPermission;
|
||||
import org.apache.hadoop.hbase.security.visibility.VisibilityController;
|
||||
import org.apache.hadoop.hbase.snapshot.ClientSnapshotDescriptionUtils;
|
||||
import org.apache.hadoop.hbase.snapshot.SnapshotDescriptionUtils;
|
||||
|
@ -114,6 +118,10 @@ import org.apache.hbase.thirdparty.com.google.protobuf.UnsafeByteOperations;
|
|||
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.ResponseConverter;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GrantRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.GrantResponse;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.RevokeRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AccessControlProtos.RevokeResponse;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos.CompactRegionRequest;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos.CompactRegionResponse;
|
||||
import org.apache.hadoop.hbase.shaded.protobuf.generated.AdminProtos.GetRegionInfoRequest;
|
||||
|
@ -2468,6 +2476,50 @@ public class MasterRpcServices extends RSRpcServices
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public GrantResponse grant(RpcController controller, GrantRequest request)
|
||||
throws ServiceException {
|
||||
try {
|
||||
final UserPermission perm =
|
||||
ShadedAccessControlUtil.toUserPermission(request.getUserPermission());
|
||||
boolean mergeExistingPermissions = request.getMergeExistingPermissions();
|
||||
if (master.cpHost != null) {
|
||||
master.cpHost.preGrant(perm, mergeExistingPermissions);
|
||||
}
|
||||
try (Table table = master.getConnection().getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
AccessControlLists.addUserPermission(getConfiguration(), perm, table,
|
||||
mergeExistingPermissions);
|
||||
}
|
||||
if (master.cpHost != null) {
|
||||
master.cpHost.postGrant(perm, mergeExistingPermissions);
|
||||
}
|
||||
return GrantResponse.getDefaultInstance();
|
||||
} catch (IOException ioe) {
|
||||
throw new ServiceException(ioe);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public RevokeResponse revoke(RpcController controller, RevokeRequest request)
|
||||
throws ServiceException {
|
||||
try {
|
||||
final UserPermission userPermission =
|
||||
ShadedAccessControlUtil.toUserPermission(request.getUserPermission());
|
||||
if (master.cpHost != null) {
|
||||
master.cpHost.preRevoke(userPermission);
|
||||
}
|
||||
try (Table table = master.getConnection().getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
AccessControlLists.removeUserPermission(master.getConfiguration(), userPermission, table);
|
||||
}
|
||||
if (master.cpHost != null) {
|
||||
master.cpHost.postRevoke(userPermission);
|
||||
}
|
||||
return RevokeResponse.getDefaultInstance();
|
||||
} catch (IOException ioe) {
|
||||
throw new ServiceException(ioe);
|
||||
}
|
||||
}
|
||||
|
||||
private boolean containMetaWals(ServerName serverName) throws IOException {
|
||||
Path logDir = new Path(master.getWALRootDir(),
|
||||
AbstractFSWALProvider.getWALDirectoryName(serverName.toString()));
|
||||
|
|
|
@ -130,7 +130,7 @@ public class AccessControlLists {
|
|||
* @param t acl table instance. It is closed upon method return.
|
||||
* @throws IOException in the case of an error accessing the metadata table
|
||||
*/
|
||||
static void addUserPermission(Configuration conf, UserPermission userPerm, Table t,
|
||||
public static void addUserPermission(Configuration conf, UserPermission userPerm, Table t,
|
||||
boolean mergeExistingPermissions) throws IOException {
|
||||
Permission permission = userPerm.getPermission();
|
||||
Permission.Action[] actions = permission.getActions();
|
||||
|
@ -222,7 +222,7 @@ public class AccessControlLists {
|
|||
* @param t acl table
|
||||
* @throws IOException if there is an error accessing the metadata table
|
||||
*/
|
||||
static void removeUserPermission(Configuration conf, UserPermission userPerm, Table t)
|
||||
public static void removeUserPermission(Configuration conf, UserPermission userPerm, Table t)
|
||||
throws IOException {
|
||||
if (null == userPerm.getPermission().getActions() ||
|
||||
userPerm.getPermission().getActions().length == 0) {
|
||||
|
|
|
@ -2053,6 +2053,10 @@ public class AccessController implements MasterCoprocessor, RegionCoprocessor,
|
|||
|
||||
/* ---- Protobuf AccessControlService implementation ---- */
|
||||
|
||||
/**
|
||||
* @deprecated Use {@link Admin#grant(UserPermission, boolean)} instead.
|
||||
*/
|
||||
@Deprecated
|
||||
@Override
|
||||
public void grant(RpcController controller,
|
||||
AccessControlProtos.GrantRequest request,
|
||||
|
@ -2070,36 +2074,10 @@ public class AccessController implements MasterCoprocessor, RegionCoprocessor,
|
|||
LOG.debug("Received request from {} to grant access permission {}",
|
||||
caller.getName(), perm.toString());
|
||||
}
|
||||
preGrantOrRevoke(caller, "grant", perm);
|
||||
|
||||
switch(request.getUserPermission().getPermission().getType()) {
|
||||
case Global :
|
||||
accessChecker.requireGlobalPermission(caller, "grant", Action.ADMIN, "");
|
||||
break;
|
||||
case Table :
|
||||
TablePermission tablePerm = (TablePermission) perm.getPermission();
|
||||
accessChecker.requirePermission(caller, "grant", tablePerm.getTableName(),
|
||||
tablePerm.getFamily(), tablePerm.getQualifier(), null, Action.ADMIN);
|
||||
break;
|
||||
case Namespace :
|
||||
NamespacePermission namespacePer = (NamespacePermission) perm.getPermission();
|
||||
accessChecker.requireNamespacePermission(caller, "grant", namespacePer.getNamespace(),
|
||||
null, Action.ADMIN);
|
||||
break;
|
||||
}
|
||||
|
||||
User.runAsLoginUser(new PrivilegedExceptionAction<Void>() {
|
||||
@Override
|
||||
public Void run() throws Exception {
|
||||
// regionEnv is set at #start. Hopefully not null at this point.
|
||||
try (Table table = regionEnv.getConnection().
|
||||
getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
AccessControlLists.addUserPermission(regionEnv.getConfiguration(), perm, table,
|
||||
request.getMergeExistingPermissions());
|
||||
}
|
||||
return null;
|
||||
}
|
||||
});
|
||||
|
||||
// regionEnv is set at #start. Hopefully not null at this point.
|
||||
regionEnv.getConnection().getAdmin().grant(perm, request.getMergeExistingPermissions());
|
||||
if (AUDITLOG.isTraceEnabled()) {
|
||||
// audit log should store permission changes in addition to auth results
|
||||
AUDITLOG.trace("Granted permission " + perm.toString());
|
||||
|
@ -2116,9 +2094,12 @@ public class AccessController implements MasterCoprocessor, RegionCoprocessor,
|
|||
done.run(response);
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated Use {@link Admin#revoke(UserPermission)} instead.
|
||||
*/
|
||||
@Deprecated
|
||||
@Override
|
||||
public void revoke(RpcController controller,
|
||||
AccessControlProtos.RevokeRequest request,
|
||||
public void revoke(RpcController controller, AccessControlProtos.RevokeRequest request,
|
||||
RpcCallback<AccessControlProtos.RevokeResponse> done) {
|
||||
final UserPermission perm = AccessControlUtil.toUserPermission(request.getUserPermission());
|
||||
AccessControlProtos.RevokeResponse response = null;
|
||||
|
@ -2133,35 +2114,9 @@ public class AccessController implements MasterCoprocessor, RegionCoprocessor,
|
|||
LOG.debug("Received request from {} to revoke access permission {}",
|
||||
caller.getShortName(), perm.toString());
|
||||
}
|
||||
|
||||
switch(request.getUserPermission().getPermission().getType()) {
|
||||
case Global :
|
||||
accessChecker.requireGlobalPermission(caller, "revoke", Action.ADMIN, "");
|
||||
break;
|
||||
case Table :
|
||||
TablePermission tablePerm = (TablePermission) perm.getPermission();
|
||||
accessChecker.requirePermission(caller, "revoke", tablePerm.getTableName(),
|
||||
tablePerm.getFamily(), tablePerm.getQualifier(), null, Action.ADMIN);
|
||||
break;
|
||||
case Namespace :
|
||||
NamespacePermission namespacePer = (NamespacePermission) perm.getPermission();
|
||||
accessChecker.requireNamespacePermission(caller, "revoke",
|
||||
namespacePer.getNamespace(), null, Action.ADMIN);
|
||||
break;
|
||||
}
|
||||
|
||||
User.runAsLoginUser(new PrivilegedExceptionAction<Void>() {
|
||||
@Override
|
||||
public Void run() throws Exception {
|
||||
// regionEnv is set at #start. Hopefully not null here.
|
||||
try (Table table = regionEnv.getConnection().
|
||||
getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
AccessControlLists.removeUserPermission(regionEnv.getConfiguration(), perm, table);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
});
|
||||
|
||||
preGrantOrRevoke(caller, "revoke", perm);
|
||||
// regionEnv is set at #start. Hopefully not null here.
|
||||
regionEnv.getConnection().getAdmin().revoke(perm);
|
||||
if (AUDITLOG.isTraceEnabled()) {
|
||||
// audit log should record all permission changes
|
||||
AUDITLOG.trace("Revoked permission " + perm.toString());
|
||||
|
@ -2674,4 +2629,36 @@ public class AccessController implements MasterCoprocessor, RegionCoprocessor,
|
|||
}
|
||||
done.run(response);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void preGrant(ObserverContext<MasterCoprocessorEnvironment> ctx,
|
||||
UserPermission userPermission, boolean mergeExistingPermissions) throws IOException {
|
||||
preGrantOrRevoke(getActiveUser(ctx), "grant", userPermission);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void preRevoke(ObserverContext<MasterCoprocessorEnvironment> ctx,
|
||||
UserPermission userPermission) throws IOException {
|
||||
preGrantOrRevoke(getActiveUser(ctx), "revoke", userPermission);
|
||||
}
|
||||
|
||||
private void preGrantOrRevoke(User caller, String request, UserPermission userPermission)
|
||||
throws IOException {
|
||||
switch (userPermission.getPermission().scope) {
|
||||
case GLOBAL:
|
||||
accessChecker.requireGlobalPermission(caller, request, Action.ADMIN, "");
|
||||
break;
|
||||
case NAMESPACE:
|
||||
NamespacePermission namespacePerm = (NamespacePermission) userPermission.getPermission();
|
||||
accessChecker.requireNamespacePermission(caller, request, namespacePerm.getNamespace(),
|
||||
null, Action.ADMIN);
|
||||
break;
|
||||
case TABLE:
|
||||
TablePermission tablePerm = (TablePermission) userPermission.getPermission();
|
||||
accessChecker.requirePermission(caller, request, tablePerm.getTableName(),
|
||||
tablePerm.getFamily(), tablePerm.getQualifier(), null, Action.ADMIN);
|
||||
break;
|
||||
default:
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -34,7 +34,6 @@ import com.google.protobuf.ServiceException;
|
|||
import org.apache.hadoop.conf.Configuration;
|
||||
import org.apache.hadoop.hbase.Coprocessor;
|
||||
import org.apache.hadoop.hbase.HBaseTestingUtility;
|
||||
import org.apache.hadoop.hbase.HConstants;
|
||||
import org.apache.hadoop.hbase.MiniHBaseCluster;
|
||||
import org.apache.hadoop.hbase.NamespaceDescriptor;
|
||||
import org.apache.hadoop.hbase.TableName;
|
||||
|
@ -375,12 +374,8 @@ public class SecureTestUtil {
|
|||
@Override
|
||||
public Void call() throws Exception {
|
||||
try (Connection connection = ConnectionFactory.createConnection(util.getConfiguration())) {
|
||||
try (Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.grant(null, protocol, user, false, actions);
|
||||
}
|
||||
connection.getAdmin().grant(new UserPermission(user, new GlobalPermission(actions)),
|
||||
false);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -398,12 +393,7 @@ public class SecureTestUtil {
|
|||
@Override
|
||||
public Void call() throws Exception {
|
||||
try (Connection connection = ConnectionFactory.createConnection(util.getConfiguration())) {
|
||||
try (Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.revoke(null, protocol, user, actions);
|
||||
}
|
||||
connection.getAdmin().revoke(new UserPermission(user, new GlobalPermission(actions)));
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -421,12 +411,8 @@ public class SecureTestUtil {
|
|||
@Override
|
||||
public Void call() throws Exception {
|
||||
try (Connection connection = ConnectionFactory.createConnection(util.getConfiguration())) {
|
||||
try (Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.grant(null, protocol, user, namespace, false, actions);
|
||||
}
|
||||
connection.getAdmin()
|
||||
.grant(new UserPermission(user, new NamespacePermission(namespace, actions)), false);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -486,12 +472,8 @@ public class SecureTestUtil {
|
|||
@Override
|
||||
public Void call() throws Exception {
|
||||
try (Connection connection = ConnectionFactory.createConnection(util.getConfiguration())) {
|
||||
try (Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.revoke(null, protocol, user, namespace, actions);
|
||||
}
|
||||
connection.getAdmin()
|
||||
.revoke(new UserPermission(user, new NamespacePermission(namespace, actions)));
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -510,12 +492,9 @@ public class SecureTestUtil {
|
|||
@Override
|
||||
public Void call() throws Exception {
|
||||
try (Connection connection = ConnectionFactory.createConnection(util.getConfiguration())) {
|
||||
try (Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.grant(null, protocol, user, table, family, qualifier, false, actions);
|
||||
}
|
||||
connection.getAdmin().grant(
|
||||
new UserPermission(user, new TablePermission(table, family, qualifier, actions)),
|
||||
false);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -576,12 +555,8 @@ public class SecureTestUtil {
|
|||
@Override
|
||||
public Void call() throws Exception {
|
||||
try (Connection connection = ConnectionFactory.createConnection(util.getConfiguration())) {
|
||||
try (Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.revoke(null, protocol, user, table, family, qualifier, actions);
|
||||
}
|
||||
connection.getAdmin().revoke(
|
||||
new UserPermission(user, new TablePermission(table, family, qualifier, actions)));
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
|
|
@ -1167,13 +1167,10 @@ public class TestAccessController extends SecureTestUtil {
|
|||
AccessTestAction grantAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
try(Connection conn = ConnectionFactory.createConnection(conf);
|
||||
Table acl = conn.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(TEST_TABLE.getName());
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.grant(null, protocol, USER_RO.getShortName(), TEST_TABLE, TEST_FAMILY,
|
||||
null, false, Action.READ);
|
||||
try (Connection conn = ConnectionFactory.createConnection(conf)) {
|
||||
conn.getAdmin().grant(new UserPermission(USER_RO.getShortName(),
|
||||
new TablePermission(TEST_TABLE, TEST_FAMILY, Action.READ)),
|
||||
false);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -1182,13 +1179,9 @@ public class TestAccessController extends SecureTestUtil {
|
|||
AccessTestAction revokeAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
try(Connection conn = ConnectionFactory.createConnection(conf);
|
||||
Table acl = conn.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(TEST_TABLE.getName());
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.revoke(null, protocol, USER_RO.getShortName(), TEST_TABLE, TEST_FAMILY, null,
|
||||
Action.READ);
|
||||
try(Connection conn = ConnectionFactory.createConnection(conf)) {
|
||||
conn.getAdmin().revoke(new UserPermission(USER_RO.getShortName(),
|
||||
new TablePermission(TEST_TABLE, TEST_FAMILY, Action.READ)));
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -1222,6 +1215,57 @@ public class TestAccessController extends SecureTestUtil {
|
|||
}
|
||||
};
|
||||
|
||||
AccessTestAction preGrantAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
ACCESS_CONTROLLER.preGrant(ObserverContextImpl.createAndPrepare(CP_ENV),
|
||||
new UserPermission(USER_RO.getShortName(),
|
||||
new TablePermission(TEST_TABLE, TEST_FAMILY, Action.READ)),
|
||||
false);
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
AccessTestAction preRevokeAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
ACCESS_CONTROLLER.preRevoke(ObserverContextImpl.createAndPrepare(CP_ENV),
|
||||
new UserPermission(USER_RO.getShortName(),
|
||||
new TablePermission(TEST_TABLE, TEST_FAMILY, Action.READ)));
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
AccessTestAction grantCPAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
try (Connection conn = ConnectionFactory.createConnection(conf);
|
||||
Table acl = conn.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(TEST_TABLE.getName());
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.grant(null, protocol, USER_RO.getShortName(), TEST_TABLE, TEST_FAMILY,
|
||||
null, false, Action.READ);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
AccessTestAction revokeCPAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
try (Connection conn = ConnectionFactory.createConnection(conf);
|
||||
Table acl = conn.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(TEST_TABLE.getName());
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.revoke(null, protocol, USER_RO.getShortName(), TEST_TABLE, TEST_FAMILY,
|
||||
null, Action.READ);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
verifyAllowed(grantAction, SUPERUSER, USER_ADMIN, USER_OWNER, USER_GROUP_ADMIN);
|
||||
verifyDenied(grantAction, USER_CREATE, USER_RW, USER_RO, USER_NONE, USER_GROUP_READ,
|
||||
USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
|
@ -1237,6 +1281,22 @@ public class TestAccessController extends SecureTestUtil {
|
|||
verifyAllowed(getGlobalPermissionsAction, SUPERUSER, USER_ADMIN, USER_GROUP_ADMIN);
|
||||
verifyDenied(getGlobalPermissionsAction, USER_CREATE, USER_OWNER, USER_RW, USER_RO,
|
||||
USER_NONE, USER_GROUP_READ, USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
|
||||
verifyAllowed(preGrantAction, SUPERUSER, USER_ADMIN, USER_OWNER, USER_GROUP_ADMIN);
|
||||
verifyDenied(preGrantAction, USER_CREATE, USER_RW, USER_RO, USER_NONE, USER_GROUP_READ,
|
||||
USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
|
||||
verifyAllowed(preRevokeAction, SUPERUSER, USER_ADMIN, USER_OWNER, USER_GROUP_ADMIN);
|
||||
verifyDenied(preRevokeAction, USER_CREATE, USER_RW, USER_RO, USER_NONE, USER_GROUP_READ,
|
||||
USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
|
||||
verifyAllowed(grantCPAction, SUPERUSER, USER_ADMIN, USER_OWNER, USER_GROUP_ADMIN);
|
||||
verifyDenied(grantCPAction, USER_CREATE, USER_RW, USER_RO, USER_NONE, USER_GROUP_READ,
|
||||
USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
|
||||
verifyAllowed(revokeCPAction, SUPERUSER, USER_ADMIN, USER_OWNER, USER_GROUP_ADMIN);
|
||||
verifyDenied(revokeCPAction, USER_CREATE, USER_RW, USER_RO, USER_NONE, USER_GROUP_READ,
|
||||
USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
} finally {
|
||||
// Cleanup, Grant the revoked permission back to the user
|
||||
grantOnTable(TEST_UTIL, USER_RO.getShortName(), TEST_TABLE, TEST_FAMILY, null,
|
||||
|
|
|
@ -355,40 +355,27 @@ public class TestNamespaceCommands extends SecureTestUtil {
|
|||
}
|
||||
|
||||
@Test
|
||||
public void testGrantRevoke() throws Exception{
|
||||
public void testGrantRevoke() throws Exception {
|
||||
final String testUser = "testUser";
|
||||
|
||||
// Test if client API actions are authorized
|
||||
|
||||
AccessTestAction grantAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
Connection connection = ConnectionFactory.createConnection(conf);
|
||||
Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME);
|
||||
try {
|
||||
BlockingRpcChannel service =
|
||||
acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.grant(null, protocol, testUser, TEST_NAMESPACE, false, Action.WRITE);
|
||||
} finally {
|
||||
acl.close();
|
||||
connection.close();
|
||||
try (Connection connection = ConnectionFactory.createConnection(conf)) {
|
||||
connection.getAdmin().grant(
|
||||
new UserPermission(testUser, new NamespacePermission(TEST_NAMESPACE, Action.WRITE)),
|
||||
false);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
AccessTestAction grantNamespaceAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
try(Connection conn = ConnectionFactory.createConnection(conf);
|
||||
Table acl = conn.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.grant(null, protocol, USER_GROUP_NS_ADMIN.getShortName(),
|
||||
TEST_NAMESPACE, false, Action.READ);
|
||||
try (Connection conn = ConnectionFactory.createConnection(conf)) {
|
||||
conn.getAdmin().grant(
|
||||
new UserPermission(USER_GROUP_NS_ADMIN.getShortName(), TEST_NAMESPACE, Action.READ),
|
||||
false);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -397,37 +384,19 @@ public class TestNamespaceCommands extends SecureTestUtil {
|
|||
AccessTestAction revokeAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
Connection connection = ConnectionFactory.createConnection(conf);
|
||||
Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME);
|
||||
try {
|
||||
BlockingRpcChannel service =
|
||||
acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.revoke(null, protocol, testUser, TEST_NAMESPACE, Action.WRITE);
|
||||
} finally {
|
||||
acl.close();
|
||||
connection.close();
|
||||
try (Connection connection = ConnectionFactory.createConnection(conf)) {
|
||||
connection.getAdmin().revoke(
|
||||
new UserPermission(testUser, new NamespacePermission(TEST_NAMESPACE, Action.WRITE)));
|
||||
}
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
AccessTestAction revokeNamespaceAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
Connection connection = ConnectionFactory.createConnection(conf);
|
||||
Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME);
|
||||
try {
|
||||
BlockingRpcChannel service =
|
||||
acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.revoke(null, protocol, USER_GROUP_NS_ADMIN.getShortName(),
|
||||
TEST_NAMESPACE, Action.READ);
|
||||
} finally {
|
||||
acl.close();
|
||||
connection.close();
|
||||
try (Connection connection = ConnectionFactory.createConnection(conf)) {
|
||||
connection.getAdmin().revoke(new UserPermission(USER_GROUP_NS_ADMIN.getShortName(),
|
||||
new NamespacePermission(TEST_NAMESPACE, Action.READ)));
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -436,16 +405,57 @@ public class TestNamespaceCommands extends SecureTestUtil {
|
|||
AccessTestAction getPermissionsAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
Connection connection = ConnectionFactory.createConnection(conf);
|
||||
Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME);
|
||||
try {
|
||||
try (Connection connection = ConnectionFactory.createConnection(conf);
|
||||
Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.getUserPermissions(null, protocol, Bytes.toBytes(TEST_NAMESPACE));
|
||||
} finally {
|
||||
acl.close();
|
||||
connection.close();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
AccessTestAction preGrantAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
ACCESS_CONTROLLER.preGrant(ObserverContextImpl.createAndPrepare(CP_ENV),
|
||||
new UserPermission(testUser, new NamespacePermission(TEST_NAMESPACE, Action.WRITE)),
|
||||
false);
|
||||
return null;
|
||||
}
|
||||
};
|
||||
AccessTestAction preRevokeAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
ACCESS_CONTROLLER.preRevoke(ObserverContextImpl.createAndPrepare(CP_ENV),
|
||||
new UserPermission(testUser, new NamespacePermission(TEST_NAMESPACE, Action.WRITE)));
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
AccessTestAction grantCPAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
try (Connection connection = ConnectionFactory.createConnection(conf);
|
||||
Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.grant(null, protocol, testUser, TEST_NAMESPACE, false, Action.WRITE);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
};
|
||||
AccessTestAction revokeCPAction = new AccessTestAction() {
|
||||
@Override
|
||||
public Object run() throws Exception {
|
||||
try (Connection connection = ConnectionFactory.createConnection(conf);
|
||||
Table acl = connection.getTable(AccessControlLists.ACL_TABLE_NAME)) {
|
||||
BlockingRpcChannel service = acl.coprocessorService(HConstants.EMPTY_START_ROW);
|
||||
AccessControlService.BlockingInterface protocol =
|
||||
AccessControlService.newBlockingStub(service);
|
||||
AccessControlUtil.revoke(null, protocol, testUser, TEST_NAMESPACE, Action.WRITE);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
@ -455,7 +465,6 @@ public class TestNamespaceCommands extends SecureTestUtil {
|
|||
verifyDenied(grantAction, USER_GLOBAL_CREATE, USER_GLOBAL_WRITE, USER_GLOBAL_READ,
|
||||
USER_GLOBAL_EXEC, USER_NS_CREATE, USER_NS_WRITE, USER_NS_READ, USER_NS_EXEC,
|
||||
USER_TABLE_CREATE, USER_TABLE_WRITE, USER_GROUP_READ, USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
|
||||
verifyAllowed(grantNamespaceAction, SUPERUSER, USER_GLOBAL_ADMIN, USER_GROUP_ADMIN,
|
||||
USER_NS_ADMIN, USER_GROUP_NS_ADMIN);
|
||||
verifyDenied(grantNamespaceAction, USER_GLOBAL_CREATE, USER_GLOBAL_WRITE, USER_GLOBAL_READ,
|
||||
|
@ -466,7 +475,6 @@ public class TestNamespaceCommands extends SecureTestUtil {
|
|||
verifyDenied(revokeAction, USER_GLOBAL_CREATE, USER_GLOBAL_WRITE, USER_GLOBAL_READ,
|
||||
USER_GLOBAL_EXEC, USER_NS_CREATE, USER_NS_WRITE, USER_NS_READ, USER_NS_EXEC,
|
||||
USER_TABLE_CREATE, USER_TABLE_WRITE, USER_GROUP_READ, USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
|
||||
verifyAllowed(revokeNamespaceAction, SUPERUSER, USER_GLOBAL_ADMIN, USER_GROUP_ADMIN,
|
||||
USER_NS_ADMIN, USER_GROUP_NS_ADMIN);
|
||||
verifyDenied(revokeNamespaceAction, USER_GLOBAL_CREATE, USER_GLOBAL_WRITE, USER_GLOBAL_READ,
|
||||
|
@ -478,6 +486,24 @@ public class TestNamespaceCommands extends SecureTestUtil {
|
|||
verifyDenied(getPermissionsAction, USER_GLOBAL_CREATE, USER_GLOBAL_WRITE, USER_GLOBAL_READ,
|
||||
USER_GLOBAL_EXEC, USER_NS_CREATE, USER_NS_WRITE, USER_NS_READ, USER_NS_EXEC,
|
||||
USER_TABLE_CREATE, USER_TABLE_WRITE, USER_GROUP_READ, USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
|
||||
verifyAllowed(preGrantAction, SUPERUSER, USER_GLOBAL_ADMIN, USER_GROUP_ADMIN, USER_NS_ADMIN);
|
||||
verifyDenied(preGrantAction, USER_GLOBAL_CREATE, USER_GLOBAL_WRITE, USER_GLOBAL_READ,
|
||||
USER_GLOBAL_EXEC, USER_NS_CREATE, USER_NS_WRITE, USER_NS_READ, USER_NS_EXEC,
|
||||
USER_TABLE_CREATE, USER_TABLE_WRITE, USER_GROUP_READ, USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
verifyAllowed(preRevokeAction, SUPERUSER, USER_GLOBAL_ADMIN, USER_GROUP_ADMIN, USER_NS_ADMIN);
|
||||
verifyDenied(preRevokeAction, USER_GLOBAL_CREATE, USER_GLOBAL_WRITE, USER_GLOBAL_READ,
|
||||
USER_GLOBAL_EXEC, USER_NS_CREATE, USER_NS_WRITE, USER_NS_READ, USER_NS_EXEC,
|
||||
USER_TABLE_CREATE, USER_TABLE_WRITE, USER_GROUP_READ, USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
|
||||
verifyAllowed(grantCPAction, SUPERUSER, USER_GLOBAL_ADMIN, USER_GROUP_ADMIN, USER_NS_ADMIN);
|
||||
verifyDenied(grantCPAction, USER_GLOBAL_CREATE, USER_GLOBAL_WRITE, USER_GLOBAL_READ,
|
||||
USER_GLOBAL_EXEC, USER_NS_CREATE, USER_NS_WRITE, USER_NS_READ, USER_NS_EXEC,
|
||||
USER_TABLE_CREATE, USER_TABLE_WRITE, USER_GROUP_READ, USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
verifyAllowed(revokeCPAction, SUPERUSER, USER_GLOBAL_ADMIN, USER_GROUP_ADMIN, USER_NS_ADMIN);
|
||||
verifyDenied(revokeCPAction, USER_GLOBAL_CREATE, USER_GLOBAL_WRITE, USER_GLOBAL_READ,
|
||||
USER_GLOBAL_EXEC, USER_NS_CREATE, USER_NS_WRITE, USER_NS_READ, USER_NS_EXEC,
|
||||
USER_TABLE_CREATE, USER_TABLE_WRITE, USER_GROUP_READ, USER_GROUP_WRITE, USER_GROUP_CREATE);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
|
@ -59,6 +59,7 @@ import org.apache.hadoop.hbase.quotas.SpaceQuotaSnapshot;
|
|||
import org.apache.hadoop.hbase.replication.ReplicationException;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerConfig;
|
||||
import org.apache.hadoop.hbase.replication.ReplicationPeerDescription;
|
||||
import org.apache.hadoop.hbase.security.access.UserPermission;
|
||||
import org.apache.hadoop.hbase.thrift2.ThriftUtilities;
|
||||
import org.apache.hadoop.hbase.thrift2.generated.TColumnFamilyDescriptor;
|
||||
import org.apache.hadoop.hbase.thrift2.generated.THBaseService;
|
||||
|
@ -1409,4 +1410,14 @@ public class ThriftAdmin implements Admin {
|
|||
public SpaceQuotaSnapshot getCurrentSpaceQuotaSnapshot(TableName tableName) throws IOException {
|
||||
throw new NotImplementedException("getCurrentSpaceQuotaSnapshot not supported in ThriftAdmin");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void grant(UserPermission userPermission, boolean mergeExistingPermissions) {
|
||||
throw new NotImplementedException("grant not supported in ThriftAdmin");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void revoke(UserPermission userPermission) {
|
||||
throw new NotImplementedException("revoke not supported in ThriftAdmin");
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue