Repository: sentry Updated Branches: refs/heads/master 8e64b2fa5 -> 96a473390
http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-api/src/gen/thrift/gen-javabean/org/apache/sentry/api/service/thrift/TSentryPrivilegesResponse.java ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-api/src/gen/thrift/gen-javabean/org/apache/sentry/api/service/thrift/TSentryPrivilegesResponse.java b/sentry-service/sentry-service-api/src/gen/thrift/gen-javabean/org/apache/sentry/api/service/thrift/TSentryPrivilegesResponse.java new file mode 100644 index 0000000..cea868f --- /dev/null +++ b/sentry-service/sentry-service-api/src/gen/thrift/gen-javabean/org/apache/sentry/api/service/thrift/TSentryPrivilegesResponse.java @@ -0,0 +1,604 @@ +/** + * Autogenerated by Thrift Compiler (0.9.3) + * + * DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING + * @generated + */ +package org.apache.sentry.api.service.thrift; + +import org.apache.thrift.scheme.IScheme; +import org.apache.thrift.scheme.SchemeFactory; +import org.apache.thrift.scheme.StandardScheme; + +import org.apache.thrift.scheme.TupleScheme; +import org.apache.thrift.protocol.TTupleProtocol; +import org.apache.thrift.protocol.TProtocolException; +import org.apache.thrift.EncodingUtils; +import org.apache.thrift.TException; +import org.apache.thrift.async.AsyncMethodCallback; +import org.apache.thrift.server.AbstractNonblockingServer.*; +import java.util.List; +import java.util.ArrayList; +import java.util.Map; +import java.util.HashMap; +import java.util.EnumMap; +import java.util.Set; +import java.util.HashSet; +import java.util.EnumSet; +import java.util.Collections; +import java.util.BitSet; +import java.nio.ByteBuffer; +import java.util.Arrays; +import javax.annotation.Generated; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +@SuppressWarnings({"cast", "rawtypes", "serial", "unchecked"}) +/** + * API that returns either all users or roles privileges found on the Sentry server. + * + * The response returns a mapping object that maps the role or user name to the privileges + * they have in the server. An empty set of privileges may be returned to each role or user + * name. Null values are not returned. + * + */ +@Generated(value = "Autogenerated by Thrift Compiler (0.9.3)") +public class TSentryPrivilegesResponse implements org.apache.thrift.TBase<TSentryPrivilegesResponse, TSentryPrivilegesResponse._Fields>, java.io.Serializable, Cloneable, Comparable<TSentryPrivilegesResponse> { + private static final org.apache.thrift.protocol.TStruct STRUCT_DESC = new org.apache.thrift.protocol.TStruct("TSentryPrivilegesResponse"); + + private static final org.apache.thrift.protocol.TField STATUS_FIELD_DESC = new org.apache.thrift.protocol.TField("status", org.apache.thrift.protocol.TType.STRUCT, (short)1); + private static final org.apache.thrift.protocol.TField PRIVILEGES_MAP_FIELD_DESC = new org.apache.thrift.protocol.TField("privilegesMap", org.apache.thrift.protocol.TType.MAP, (short)2); + + private static final Map<Class<? extends IScheme>, SchemeFactory> schemes = new HashMap<Class<? extends IScheme>, SchemeFactory>(); + static { + schemes.put(StandardScheme.class, new TSentryPrivilegesResponseStandardSchemeFactory()); + schemes.put(TupleScheme.class, new TSentryPrivilegesResponseTupleSchemeFactory()); + } + + private org.apache.sentry.service.thrift.TSentryResponseStatus status; // required + private Map<String,Set<TSentryPrivilege>> privilegesMap; // required + + /** The set of fields this struct contains, along with convenience methods for finding and manipulating them. */ + public enum _Fields implements org.apache.thrift.TFieldIdEnum { + STATUS((short)1, "status"), + PRIVILEGES_MAP((short)2, "privilegesMap"); + + private static final Map<String, _Fields> byName = new HashMap<String, _Fields>(); + + static { + for (_Fields field : EnumSet.allOf(_Fields.class)) { + byName.put(field.getFieldName(), field); + } + } + + /** + * Find the _Fields constant that matches fieldId, or null if its not found. + */ + public static _Fields findByThriftId(int fieldId) { + switch(fieldId) { + case 1: // STATUS + return STATUS; + case 2: // PRIVILEGES_MAP + return PRIVILEGES_MAP; + default: + return null; + } + } + + /** + * Find the _Fields constant that matches fieldId, throwing an exception + * if it is not found. + */ + public static _Fields findByThriftIdOrThrow(int fieldId) { + _Fields fields = findByThriftId(fieldId); + if (fields == null) throw new IllegalArgumentException("Field " + fieldId + " doesn't exist!"); + return fields; + } + + /** + * Find the _Fields constant that matches name, or null if its not found. + */ + public static _Fields findByName(String name) { + return byName.get(name); + } + + private final short _thriftId; + private final String _fieldName; + + _Fields(short thriftId, String fieldName) { + _thriftId = thriftId; + _fieldName = fieldName; + } + + public short getThriftFieldId() { + return _thriftId; + } + + public String getFieldName() { + return _fieldName; + } + } + + // isset id assignments + public static final Map<_Fields, org.apache.thrift.meta_data.FieldMetaData> metaDataMap; + static { + Map<_Fields, org.apache.thrift.meta_data.FieldMetaData> tmpMap = new EnumMap<_Fields, org.apache.thrift.meta_data.FieldMetaData>(_Fields.class); + tmpMap.put(_Fields.STATUS, new org.apache.thrift.meta_data.FieldMetaData("status", org.apache.thrift.TFieldRequirementType.REQUIRED, + new org.apache.thrift.meta_data.StructMetaData(org.apache.thrift.protocol.TType.STRUCT, org.apache.sentry.service.thrift.TSentryResponseStatus.class))); + tmpMap.put(_Fields.PRIVILEGES_MAP, new org.apache.thrift.meta_data.FieldMetaData("privilegesMap", org.apache.thrift.TFieldRequirementType.REQUIRED, + new org.apache.thrift.meta_data.MapMetaData(org.apache.thrift.protocol.TType.MAP, + new org.apache.thrift.meta_data.FieldValueMetaData(org.apache.thrift.protocol.TType.STRING), + new org.apache.thrift.meta_data.SetMetaData(org.apache.thrift.protocol.TType.SET, + new org.apache.thrift.meta_data.StructMetaData(org.apache.thrift.protocol.TType.STRUCT, TSentryPrivilege.class))))); + metaDataMap = Collections.unmodifiableMap(tmpMap); + org.apache.thrift.meta_data.FieldMetaData.addStructMetaDataMap(TSentryPrivilegesResponse.class, metaDataMap); + } + + public TSentryPrivilegesResponse() { + } + + public TSentryPrivilegesResponse( + org.apache.sentry.service.thrift.TSentryResponseStatus status, + Map<String,Set<TSentryPrivilege>> privilegesMap) + { + this(); + this.status = status; + this.privilegesMap = privilegesMap; + } + + /** + * Performs a deep copy on <i>other</i>. + */ + public TSentryPrivilegesResponse(TSentryPrivilegesResponse other) { + if (other.isSetStatus()) { + this.status = new org.apache.sentry.service.thrift.TSentryResponseStatus(other.status); + } + if (other.isSetPrivilegesMap()) { + Map<String,Set<TSentryPrivilege>> __this__privilegesMap = new HashMap<String,Set<TSentryPrivilege>>(other.privilegesMap.size()); + for (Map.Entry<String, Set<TSentryPrivilege>> other_element : other.privilegesMap.entrySet()) { + + String other_element_key = other_element.getKey(); + Set<TSentryPrivilege> other_element_value = other_element.getValue(); + + String __this__privilegesMap_copy_key = other_element_key; + + Set<TSentryPrivilege> __this__privilegesMap_copy_value = new HashSet<TSentryPrivilege>(other_element_value.size()); + for (TSentryPrivilege other_element_value_element : other_element_value) { + __this__privilegesMap_copy_value.add(new TSentryPrivilege(other_element_value_element)); + } + + __this__privilegesMap.put(__this__privilegesMap_copy_key, __this__privilegesMap_copy_value); + } + this.privilegesMap = __this__privilegesMap; + } + } + + public TSentryPrivilegesResponse deepCopy() { + return new TSentryPrivilegesResponse(this); + } + + @Override + public void clear() { + this.status = null; + this.privilegesMap = null; + } + + public org.apache.sentry.service.thrift.TSentryResponseStatus getStatus() { + return this.status; + } + + public void setStatus(org.apache.sentry.service.thrift.TSentryResponseStatus status) { + this.status = status; + } + + public void unsetStatus() { + this.status = null; + } + + /** Returns true if field status is set (has been assigned a value) and false otherwise */ + public boolean isSetStatus() { + return this.status != null; + } + + public void setStatusIsSet(boolean value) { + if (!value) { + this.status = null; + } + } + + public int getPrivilegesMapSize() { + return (this.privilegesMap == null) ? 0 : this.privilegesMap.size(); + } + + public void putToPrivilegesMap(String key, Set<TSentryPrivilege> val) { + if (this.privilegesMap == null) { + this.privilegesMap = new HashMap<String,Set<TSentryPrivilege>>(); + } + this.privilegesMap.put(key, val); + } + + public Map<String,Set<TSentryPrivilege>> getPrivilegesMap() { + return this.privilegesMap; + } + + public void setPrivilegesMap(Map<String,Set<TSentryPrivilege>> privilegesMap) { + this.privilegesMap = privilegesMap; + } + + public void unsetPrivilegesMap() { + this.privilegesMap = null; + } + + /** Returns true if field privilegesMap is set (has been assigned a value) and false otherwise */ + public boolean isSetPrivilegesMap() { + return this.privilegesMap != null; + } + + public void setPrivilegesMapIsSet(boolean value) { + if (!value) { + this.privilegesMap = null; + } + } + + public void setFieldValue(_Fields field, Object value) { + switch (field) { + case STATUS: + if (value == null) { + unsetStatus(); + } else { + setStatus((org.apache.sentry.service.thrift.TSentryResponseStatus)value); + } + break; + + case PRIVILEGES_MAP: + if (value == null) { + unsetPrivilegesMap(); + } else { + setPrivilegesMap((Map<String,Set<TSentryPrivilege>>)value); + } + break; + + } + } + + public Object getFieldValue(_Fields field) { + switch (field) { + case STATUS: + return getStatus(); + + case PRIVILEGES_MAP: + return getPrivilegesMap(); + + } + throw new IllegalStateException(); + } + + /** Returns true if field corresponding to fieldID is set (has been assigned a value) and false otherwise */ + public boolean isSet(_Fields field) { + if (field == null) { + throw new IllegalArgumentException(); + } + + switch (field) { + case STATUS: + return isSetStatus(); + case PRIVILEGES_MAP: + return isSetPrivilegesMap(); + } + throw new IllegalStateException(); + } + + @Override + public boolean equals(Object that) { + if (that == null) + return false; + if (that instanceof TSentryPrivilegesResponse) + return this.equals((TSentryPrivilegesResponse)that); + return false; + } + + public boolean equals(TSentryPrivilegesResponse that) { + if (that == null) + return false; + + boolean this_present_status = true && this.isSetStatus(); + boolean that_present_status = true && that.isSetStatus(); + if (this_present_status || that_present_status) { + if (!(this_present_status && that_present_status)) + return false; + if (!this.status.equals(that.status)) + return false; + } + + boolean this_present_privilegesMap = true && this.isSetPrivilegesMap(); + boolean that_present_privilegesMap = true && that.isSetPrivilegesMap(); + if (this_present_privilegesMap || that_present_privilegesMap) { + if (!(this_present_privilegesMap && that_present_privilegesMap)) + return false; + if (!this.privilegesMap.equals(that.privilegesMap)) + return false; + } + + return true; + } + + @Override + public int hashCode() { + List<Object> list = new ArrayList<Object>(); + + boolean present_status = true && (isSetStatus()); + list.add(present_status); + if (present_status) + list.add(status); + + boolean present_privilegesMap = true && (isSetPrivilegesMap()); + list.add(present_privilegesMap); + if (present_privilegesMap) + list.add(privilegesMap); + + return list.hashCode(); + } + + @Override + public int compareTo(TSentryPrivilegesResponse other) { + if (!getClass().equals(other.getClass())) { + return getClass().getName().compareTo(other.getClass().getName()); + } + + int lastComparison = 0; + + lastComparison = Boolean.valueOf(isSetStatus()).compareTo(other.isSetStatus()); + if (lastComparison != 0) { + return lastComparison; + } + if (isSetStatus()) { + lastComparison = org.apache.thrift.TBaseHelper.compareTo(this.status, other.status); + if (lastComparison != 0) { + return lastComparison; + } + } + lastComparison = Boolean.valueOf(isSetPrivilegesMap()).compareTo(other.isSetPrivilegesMap()); + if (lastComparison != 0) { + return lastComparison; + } + if (isSetPrivilegesMap()) { + lastComparison = org.apache.thrift.TBaseHelper.compareTo(this.privilegesMap, other.privilegesMap); + if (lastComparison != 0) { + return lastComparison; + } + } + return 0; + } + + public _Fields fieldForId(int fieldId) { + return _Fields.findByThriftId(fieldId); + } + + public void read(org.apache.thrift.protocol.TProtocol iprot) throws org.apache.thrift.TException { + schemes.get(iprot.getScheme()).getScheme().read(iprot, this); + } + + public void write(org.apache.thrift.protocol.TProtocol oprot) throws org.apache.thrift.TException { + schemes.get(oprot.getScheme()).getScheme().write(oprot, this); + } + + @Override + public String toString() { + StringBuilder sb = new StringBuilder("TSentryPrivilegesResponse("); + boolean first = true; + + sb.append("status:"); + if (this.status == null) { + sb.append("null"); + } else { + sb.append(this.status); + } + first = false; + if (!first) sb.append(", "); + sb.append("privilegesMap:"); + if (this.privilegesMap == null) { + sb.append("null"); + } else { + sb.append(this.privilegesMap); + } + first = false; + sb.append(")"); + return sb.toString(); + } + + public void validate() throws org.apache.thrift.TException { + // check for required fields + if (!isSetStatus()) { + throw new org.apache.thrift.protocol.TProtocolException("Required field 'status' is unset! Struct:" + toString()); + } + + if (!isSetPrivilegesMap()) { + throw new org.apache.thrift.protocol.TProtocolException("Required field 'privilegesMap' is unset! Struct:" + toString()); + } + + // check for sub-struct validity + if (status != null) { + status.validate(); + } + } + + private void writeObject(java.io.ObjectOutputStream out) throws java.io.IOException { + try { + write(new org.apache.thrift.protocol.TCompactProtocol(new org.apache.thrift.transport.TIOStreamTransport(out))); + } catch (org.apache.thrift.TException te) { + throw new java.io.IOException(te); + } + } + + private void readObject(java.io.ObjectInputStream in) throws java.io.IOException, ClassNotFoundException { + try { + read(new org.apache.thrift.protocol.TCompactProtocol(new org.apache.thrift.transport.TIOStreamTransport(in))); + } catch (org.apache.thrift.TException te) { + throw new java.io.IOException(te); + } + } + + private static class TSentryPrivilegesResponseStandardSchemeFactory implements SchemeFactory { + public TSentryPrivilegesResponseStandardScheme getScheme() { + return new TSentryPrivilegesResponseStandardScheme(); + } + } + + private static class TSentryPrivilegesResponseStandardScheme extends StandardScheme<TSentryPrivilegesResponse> { + + public void read(org.apache.thrift.protocol.TProtocol iprot, TSentryPrivilegesResponse struct) throws org.apache.thrift.TException { + org.apache.thrift.protocol.TField schemeField; + iprot.readStructBegin(); + while (true) + { + schemeField = iprot.readFieldBegin(); + if (schemeField.type == org.apache.thrift.protocol.TType.STOP) { + break; + } + switch (schemeField.id) { + case 1: // STATUS + if (schemeField.type == org.apache.thrift.protocol.TType.STRUCT) { + struct.status = new org.apache.sentry.service.thrift.TSentryResponseStatus(); + struct.status.read(iprot); + struct.setStatusIsSet(true); + } else { + org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); + } + break; + case 2: // PRIVILEGES_MAP + if (schemeField.type == org.apache.thrift.protocol.TType.MAP) { + { + org.apache.thrift.protocol.TMap _map228 = iprot.readMapBegin(); + struct.privilegesMap = new HashMap<String,Set<TSentryPrivilege>>(2*_map228.size); + String _key229; + Set<TSentryPrivilege> _val230; + for (int _i231 = 0; _i231 < _map228.size; ++_i231) + { + _key229 = iprot.readString(); + { + org.apache.thrift.protocol.TSet _set232 = iprot.readSetBegin(); + _val230 = new HashSet<TSentryPrivilege>(2*_set232.size); + TSentryPrivilege _elem233; + for (int _i234 = 0; _i234 < _set232.size; ++_i234) + { + _elem233 = new TSentryPrivilege(); + _elem233.read(iprot); + _val230.add(_elem233); + } + iprot.readSetEnd(); + } + struct.privilegesMap.put(_key229, _val230); + } + iprot.readMapEnd(); + } + struct.setPrivilegesMapIsSet(true); + } else { + org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); + } + break; + default: + org.apache.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type); + } + iprot.readFieldEnd(); + } + iprot.readStructEnd(); + struct.validate(); + } + + public void write(org.apache.thrift.protocol.TProtocol oprot, TSentryPrivilegesResponse struct) throws org.apache.thrift.TException { + struct.validate(); + + oprot.writeStructBegin(STRUCT_DESC); + if (struct.status != null) { + oprot.writeFieldBegin(STATUS_FIELD_DESC); + struct.status.write(oprot); + oprot.writeFieldEnd(); + } + if (struct.privilegesMap != null) { + oprot.writeFieldBegin(PRIVILEGES_MAP_FIELD_DESC); + { + oprot.writeMapBegin(new org.apache.thrift.protocol.TMap(org.apache.thrift.protocol.TType.STRING, org.apache.thrift.protocol.TType.SET, struct.privilegesMap.size())); + for (Map.Entry<String, Set<TSentryPrivilege>> _iter235 : struct.privilegesMap.entrySet()) + { + oprot.writeString(_iter235.getKey()); + { + oprot.writeSetBegin(new org.apache.thrift.protocol.TSet(org.apache.thrift.protocol.TType.STRUCT, _iter235.getValue().size())); + for (TSentryPrivilege _iter236 : _iter235.getValue()) + { + _iter236.write(oprot); + } + oprot.writeSetEnd(); + } + } + oprot.writeMapEnd(); + } + oprot.writeFieldEnd(); + } + oprot.writeFieldStop(); + oprot.writeStructEnd(); + } + + } + + private static class TSentryPrivilegesResponseTupleSchemeFactory implements SchemeFactory { + public TSentryPrivilegesResponseTupleScheme getScheme() { + return new TSentryPrivilegesResponseTupleScheme(); + } + } + + private static class TSentryPrivilegesResponseTupleScheme extends TupleScheme<TSentryPrivilegesResponse> { + + @Override + public void write(org.apache.thrift.protocol.TProtocol prot, TSentryPrivilegesResponse struct) throws org.apache.thrift.TException { + TTupleProtocol oprot = (TTupleProtocol) prot; + struct.status.write(oprot); + { + oprot.writeI32(struct.privilegesMap.size()); + for (Map.Entry<String, Set<TSentryPrivilege>> _iter237 : struct.privilegesMap.entrySet()) + { + oprot.writeString(_iter237.getKey()); + { + oprot.writeI32(_iter237.getValue().size()); + for (TSentryPrivilege _iter238 : _iter237.getValue()) + { + _iter238.write(oprot); + } + } + } + } + } + + @Override + public void read(org.apache.thrift.protocol.TProtocol prot, TSentryPrivilegesResponse struct) throws org.apache.thrift.TException { + TTupleProtocol iprot = (TTupleProtocol) prot; + struct.status = new org.apache.sentry.service.thrift.TSentryResponseStatus(); + struct.status.read(iprot); + struct.setStatusIsSet(true); + { + org.apache.thrift.protocol.TMap _map239 = new org.apache.thrift.protocol.TMap(org.apache.thrift.protocol.TType.STRING, org.apache.thrift.protocol.TType.SET, iprot.readI32()); + struct.privilegesMap = new HashMap<String,Set<TSentryPrivilege>>(2*_map239.size); + String _key240; + Set<TSentryPrivilege> _val241; + for (int _i242 = 0; _i242 < _map239.size; ++_i242) + { + _key240 = iprot.readString(); + { + org.apache.thrift.protocol.TSet _set243 = new org.apache.thrift.protocol.TSet(org.apache.thrift.protocol.TType.STRUCT, iprot.readI32()); + _val241 = new HashSet<TSentryPrivilege>(2*_set243.size); + TSentryPrivilege _elem244; + for (int _i245 = 0; _i245 < _set243.size; ++_i245) + { + _elem244 = new TSentryPrivilege(); + _elem244.read(iprot); + _val241.add(_elem244); + } + } + struct.privilegesMap.put(_key240, _val241); + } + } + struct.setPrivilegesMapIsSet(true); + } + } + +} + http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClient.java ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClient.java b/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClient.java index dc1d67b..6137fa8 100644 --- a/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClient.java +++ b/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClient.java @@ -300,5 +300,26 @@ public interface SentryPolicyServiceClient extends AutoCloseable { */ long notifyHmsNotification(TSentryHmsEventNotification sentryHmsEventNotification) throws SentryUserException; + /** + * Lists all roles and their privileges found on the Sentry server. If a role does not have + * any privileges assigned, then returns an empty set of privileges for that role. + * + * @param requestorUserName : user on whose behalf the request is issued + * @return A mapping between role and privileges in the form [roleName, set<privileges>]. + * If a role does not have privileges, then an empty set is returned for that role. + * @throws SentryUserException if an error occurs requesting the privileges from the server. + */ + Map<String, Set<TSentryPrivilege>> listAllRolesPrivileges(String requestorUserName) throws SentryUserException; + /** + * Lists all users and their privileges found on the Sentry server. Sentry does not keep + * users without privileges, but if a user name is stale, then this method returns an + * empty set of privileges for that user. + * + * @param requestorUserName : user on whose behalf the request is issued + * @return A mapping between user and privileges in the form [userName, set<privileges>]. + * If a stale user does not have privileges, then an empty set is returned for that user. + * @throws SentryUserException if an error occurs requesting the privileges from the server. + */ + Map<String, Set<TSentryPrivilege>> listAllUsersPrivileges(String requestorUserName) throws SentryUserException; } http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClientDefaultImpl.java ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClientDefaultImpl.java b/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClientDefaultImpl.java index 5f76cb0..74e358f 100644 --- a/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClientDefaultImpl.java +++ b/sentry-service/sentry-service-api/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyServiceClientDefaultImpl.java @@ -1178,4 +1178,38 @@ public class SentryPolicyServiceClientDefaultImpl implements SentryPolicyService throw new SentryUserException(THRIFT_EXCEPTION_MESSAGE, e); } } + + @Override + public Map<String, Set<TSentryPrivilege>> listAllRolesPrivileges(String requestorUserName) + throws SentryUserException { + TSentryPrivilegesRequest request = new TSentryPrivilegesRequest(); + request.setProtocol_version(ThriftConstants.TSENTRY_SERVICE_VERSION_CURRENT); + request.setRequestorUserName(requestorUserName); + + try { + TSentryPrivilegesResponse response = client.list_roles_privileges(request); + Status.throwIfNotOk(response.getStatus()); + + return response.getPrivilegesMap(); + } catch (TException e) { + throw new SentryUserException(THRIFT_EXCEPTION_MESSAGE, e); + } + } + + @Override + public Map<String, Set<TSentryPrivilege>> listAllUsersPrivileges(String requestorUserName) + throws SentryUserException { + TSentryPrivilegesRequest request = new TSentryPrivilegesRequest(); + request.setProtocol_version(ThriftConstants.TSENTRY_SERVICE_VERSION_CURRENT); + request.setRequestorUserName(requestorUserName); + + try { + TSentryPrivilegesResponse response = client.list_users_privileges(request); + Status.throwIfNotOk(response.getStatus()); + + return response.getPrivilegesMap(); + } catch (TException e) { + throw new SentryUserException(THRIFT_EXCEPTION_MESSAGE, e); + } + } } \ No newline at end of file http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-api/src/main/resources/sentry_policy_service.thrift ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-api/src/main/resources/sentry_policy_service.thrift b/sentry-service/sentry-service-api/src/main/resources/sentry_policy_service.thrift index 56aedcb..1b0de6a 100644 --- a/sentry-service/sentry-service-api/src/main/resources/sentry_policy_service.thrift +++ b/sentry-service/sentry-service-api/src/main/resources/sentry_policy_service.thrift @@ -367,6 +367,25 @@ struct TSentryHmsEventNotificationResponse { 2: required i64 id // Most recent processed ID } +/** +* API that requests all roles and users privileges from the Sentry server. +**/ +struct TSentryPrivilegesRequest { +1: required i32 protocol_version = sentry_common_service.TSENTRY_SERVICE_V2, +2: required string requestorUserName # user on whose behalf the request is issued +} + +/** +* API that returns either all users or roles privileges found on the Sentry server. +* +* The response returns a mapping object that maps the role or user name to the privileges +* they have in the server. An empty set of privileges may be returned to each role or user +* name. Null values are not returned. +**/ +struct TSentryPrivilegesResponse { +1: required sentry_common_service.TSentryResponseStatus status +2: required map<string, set<TSentryPrivilege>> privilegesMap; +} service SentryPolicyService { @@ -411,4 +430,12 @@ service SentryPolicyService # Notify Sentry about new events in HMS. Currently used to synchronize between HMS/Sentry # and also update sentry with the owner information. TSentryHmsEventNotificationResponse sentry_notify_hms_event(1:TSentryHmsEventNotification request); + + # Returns a map of all roles and their privileges that exist in the Sentry server. + # The mapping object returned will be in the form of [roleName, set<privileges>] + TSentryPrivilegesResponse list_roles_privileges(1:TSentryPrivilegesRequest request); + + # Returns a map of all users and their privileges that exist in the Sentry server. + # The mapping object returned will be in the form of [userName, set<privileges>] + TSentryPrivilegesResponse list_users_privileges(1:TSentryPrivilegesRequest request); } http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-api/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyServiceClientDefaultImpl.java ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-api/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyServiceClientDefaultImpl.java b/sentry-service/sentry-service-api/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyServiceClientDefaultImpl.java index 1666e32..c714584 100644 --- a/sentry-service/sentry-service-api/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyServiceClientDefaultImpl.java +++ b/sentry-service/sentry-service-api/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyServiceClientDefaultImpl.java @@ -21,10 +21,13 @@ package org.apache.sentry.api.service.thrift; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; +import com.google.common.collect.ImmutableMap; +import com.google.common.collect.Maps; import com.google.common.collect.Sets; import java.io.IOException; import java.util.Arrays; import java.util.List; +import java.util.Map; import java.util.Set; import org.apache.hadoop.conf.Configuration; import org.apache.sentry.api.common.Status; @@ -159,4 +162,76 @@ public class TestSentryPolicyServiceClientDefaultImpl { response.setPrivileges(privileges); return response; } + + @Test + public void testListAllRolesPrivileges() throws SentryUserException, TException { + Map<String, Set<TSentryPrivilege>> rolesPrivileges; + TSentryPrivilegesResponse response; + TSentryPrivilegesRequest request; + + request = new TSentryPrivilegesRequest(); + request.setRequestorUserName("admin"); + + // An empty privileges map is returned if no roles exist yet + response = new TSentryPrivilegesResponse(); + response.setPrivilegesMap(Maps.newHashMap()); + response.setStatus(Status.OK()); + Mockito.when(mockClient.list_roles_privileges(request)).thenReturn(response); + rolesPrivileges = sentryClient.listAllRolesPrivileges("admin"); + assertEquals(0, rolesPrivileges.size()); + + // A map of roles privileges is returned when roles exist + response = new TSentryPrivilegesResponse(); + response.setPrivilegesMap(ImmutableMap.of( + "role1", (Set<TSentryPrivilege>)Sets.newHashSet( + newSentryPrivilege("TABLE", "db1", "tbl1", "ALL"), + newSentryPrivilege("DATABASE", "db1", "", "INSERT")), + "role2", (Set<TSentryPrivilege>)Sets.newHashSet( + newSentryPrivilege("SERVER", "", "", "ALL")), + "role3", Sets.<TSentryPrivilege>newHashSet() + )); + response.setStatus(Status.OK()); + Mockito.when(mockClient.list_roles_privileges(request)).thenReturn(response); + rolesPrivileges = sentryClient.listAllRolesPrivileges("admin"); + assertEquals(3, rolesPrivileges.size()); + assertEquals(2, rolesPrivileges.get("role1").size()); + assertEquals(1, rolesPrivileges.get("role2").size()); + assertEquals(0, rolesPrivileges.get("role3").size()); + } + + @Test + public void testListAllUsersPrivileges() throws SentryUserException, TException { + Map<String, Set<TSentryPrivilege>> usersPrivileges; + TSentryPrivilegesResponse response; + TSentryPrivilegesRequest request; + + request = new TSentryPrivilegesRequest(); + request.setRequestorUserName("admin"); + + // An empty privileges map is returned if no roles exist yet + response = new TSentryPrivilegesResponse(); + response.setPrivilegesMap(Maps.newHashMap()); + response.setStatus(Status.OK()); + Mockito.when(mockClient.list_users_privileges(request)).thenReturn(response); + usersPrivileges = sentryClient.listAllUsersPrivileges("admin"); + assertEquals(0, usersPrivileges.size()); + + // A map of roles privileges is returned when roles exist + response = new TSentryPrivilegesResponse(); + response.setPrivilegesMap(ImmutableMap.of( + "user1", (Set<TSentryPrivilege>)Sets.newHashSet( + newSentryPrivilege("TABLE", "db1", "tbl1", "ALL"), + newSentryPrivilege("DATABASE", "db1", "", "INSERT")), + "user2", (Set<TSentryPrivilege>)Sets.newHashSet( + newSentryPrivilege("SERVER", "", "", "ALL")), + "user3", Sets.<TSentryPrivilege>newHashSet() + )); + response.setStatus(Status.OK()); + Mockito.when(mockClient.list_users_privileges(request)).thenReturn(response); + usersPrivileges = sentryClient.listAllUsersPrivileges("admin"); + assertEquals(3, usersPrivileges.size()); + assertEquals(2, usersPrivileges.get("user1").size()); + assertEquals(1, usersPrivileges.get("user2").size()); + assertEquals(0, usersPrivileges.get("user3").size()); + } } \ No newline at end of file http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyStoreProcessor.java ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyStoreProcessor.java b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyStoreProcessor.java index 3927150..fe6389c 100644 --- a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyStoreProcessor.java +++ b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/api/service/thrift/SentryPolicyStoreProcessor.java @@ -1416,6 +1416,74 @@ public class SentryPolicyStoreProcessor implements SentryPolicyService.Iface { return response; } + @Override + public TSentryPrivilegesResponse list_roles_privileges(TSentryPrivilegesRequest request) + throws TException { + TSentryPrivilegesResponse response = new TSentryPrivilegesResponse(); + String requestor = request.getRequestorUserName(); + + try { + // Throws SentryThriftAPIMismatchException if protocol version mismatch + validateClientVersion(request.getProtocol_version()); + + // Throws SentryUserException with the Status.ACCESS_DENIED status if the requestor + // is not an admin. Only admins can request all roles and privileges of the system. + authorize(requestor, getRequestorGroups(requestor)); + + response.setPrivilegesMap(sentryStore.getAllRolesPrivileges()); + response.setStatus(Status.OK()); + } catch (SentryThriftAPIMismatchException e) { + LOGGER.error(e.getMessage(), e); + response.setStatus(Status.THRIFT_VERSION_MISMATCH(e.getMessage(), e)); + } catch (SentryAccessDeniedException e) { + LOGGER.error(e.getMessage(), e); + response.setStatus(Status.AccessDenied(e.getMessage(), e)); + } catch (SentryUserException e) { + LOGGER.error(e.getMessage(), e); + response.setStatus(Status.AccessDenied(e.getMessage(), e)); + } catch (Exception e) { + String msg = "Could not read roles and privileges from the database: " + e.getMessage(); + LOGGER.error(msg, e); + response.setStatus(Status.RuntimeError(msg, e)); + } + + return response; + } + + @Override + public TSentryPrivilegesResponse list_users_privileges(TSentryPrivilegesRequest request) + throws TException { + TSentryPrivilegesResponse response = new TSentryPrivilegesResponse(); + String requestor = request.getRequestorUserName(); + + try { + // Throws SentryThriftAPIMismatchException if protocol version mismatch + validateClientVersion(request.getProtocol_version()); + + // Throws SentryUserException with the Status.ACCESS_DENIED status if the requestor + // is not an admin. Only admins can request all users and privileges of the system. + authorize(requestor, getRequestorGroups(requestor)); + + response.setPrivilegesMap(sentryStore.getAllUsersPrivileges()); + response.setStatus(Status.OK()); + } catch (SentryThriftAPIMismatchException e) { + LOGGER.error(e.getMessage(), e); + response.setStatus(Status.THRIFT_VERSION_MISMATCH(e.getMessage(), e)); + } catch (SentryAccessDeniedException e) { + LOGGER.error(e.getMessage(), e); + response.setStatus(Status.AccessDenied(e.getMessage(), e)); + } catch (SentryUserException e) { + LOGGER.error(e.getMessage(), e); + response.setStatus(Status.AccessDenied(e.getMessage(), e)); + } catch (Exception e) { + String msg = "Could not read users and privileges from the database: " + e.getMessage(); + LOGGER.error(msg, e); + response.setStatus(Status.RuntimeError(msg, e)); + } + + return response; + } + /** * Grants owner privilege to an authorizable. * http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStore.java ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStore.java b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStore.java index d8ab1fc..004f06d 100644 --- a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStore.java +++ b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStore.java @@ -4718,4 +4718,73 @@ public class SentryStore implements SentryStoreInterface { return (PrivilegeEntity) query.execute(name); } + /** + * Returns all roles and privileges found on the Sentry database. + * + * @return A mapping between role and privileges in the form [roleName, set<privileges>]. + * If a role does not have privileges, then an empty set is returned for that role. + * If no roles are found, then an empty map object is returned. + */ + @Override + public Map<String, Set<TSentryPrivilege>> getAllRolesPrivileges() throws Exception { + return tm.executeTransaction( + pm -> { + // No need to detach objects + pm.setDetachAllOnCommit(false); + + Query query = pm.newQuery(MSentryRole.class); + query.addExtension(LOAD_RESULTS_AT_COMMIT, "false"); + + List<MSentryRole> mSentryRoles = (List<MSentryRole>)query.execute(); + if (mSentryRoles == null || mSentryRoles.isEmpty()) { + return Collections.emptyMap(); + } + + // Transform the list of privileges to a map [roleName, set<privileges>] + Map<String, Set<TSentryPrivilege>> allRolesPrivileges = Maps.newHashMap(); + for (MSentryRole mSentryRole : mSentryRoles) { + // convertToTSentryPrivileges returns an empty set in case is null + Set<TSentryPrivilege> tPrivileges = convertToTSentryPrivileges(mSentryRole.getPrivileges()); + allRolesPrivileges.put(mSentryRole.getRoleName(), tPrivileges); + } + + return allRolesPrivileges; + } + ); + } + + /** + * Returns all users and privileges found on the Sentry database. + * + * @return A mapping between user and privileges in the form [userName, set<privileges>]. + * If a user does not have privileges, then an empty set is returned for that user. + * If no users are found, then an empty map object is returned. + */ + @Override + public Map<String, Set<TSentryPrivilege>> getAllUsersPrivileges() throws Exception { + return tm.executeTransaction( + pm -> { + // No need to detach objects + pm.setDetachAllOnCommit(false); + + Query query = pm.newQuery(MSentryUser.class); + query.addExtension(LOAD_RESULTS_AT_COMMIT, "false"); + + List<MSentryUser> mSentryUsers = (List<MSentryUser>)query.execute(); + if (mSentryUsers == null || mSentryUsers.isEmpty()) { + return Collections.emptyMap(); + } + + // Transform the list of privileges to a map [userName, set<privileges>] + Map<String, Set<TSentryPrivilege>> allUsersPrivileges = Maps.newHashMap(); + for (MSentryUser mSentryUser : mSentryUsers) { + // convertToTSentryPrivileges returns an empty set in case is null + Set<TSentryPrivilege> tPrivileges = convertToTSentryPrivileges(mSentryUser.getPrivileges()); + allUsersPrivileges.put(mSentryUser.getUserName(), tPrivileges); + } + + return allUsersPrivileges; + } + ); + } } http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStoreInterface.java ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStoreInterface.java b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStoreInterface.java index f61ae57..19c2972 100644 --- a/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStoreInterface.java +++ b/sentry-service/sentry-service-server/src/main/java/org/apache/sentry/provider/db/service/persistent/SentryStoreInterface.java @@ -782,4 +782,22 @@ public interface SentryStoreInterface { void updateOwnerPrivilege(final TSentryAuthorizable tAuthorizable, String ownerName, SentryEntityType entityType, final List<Update> updates) throws Exception; + + /** + * Returns all roles and privileges found on the Sentry database. + * + * @return A mapping between role and privileges in the form [roleName, set<privileges>]. + * If a role does not have privileges, then an empty set is returned for that role. + * If no roles are found, then an empty map object is returned. + */ + Map<String, Set<TSentryPrivilege>> getAllRolesPrivileges() throws Exception; + + /** + * Returns all users and privileges found on the Sentry database. + * + * @return A mapping between user and privileges in the form [userName, set<privileges>]. + * If a user does not have privileges, then an empty set is returned for that user. + * If no users are found, then an empty map object is returned. + */ + Map<String, Set<TSentryPrivilege>> getAllUsersPrivileges() throws Exception; } http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyStoreProcessor.java ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyStoreProcessor.java b/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyStoreProcessor.java index de4e001..c8051e3 100644 --- a/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyStoreProcessor.java +++ b/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/api/service/thrift/TestSentryPolicyStoreProcessor.java @@ -21,7 +21,9 @@ import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import com.codahale.metrics.Gauge; +import com.google.common.collect.ImmutableMap; import com.google.common.collect.Sets; +import java.util.Collections; import java.util.Set; import org.apache.hadoop.hive.metastore.messaging.EventMessage; import org.apache.hadoop.hive.metastore.messaging.EventMessage.EventType; @@ -402,4 +404,102 @@ public class TestSentryPolicyStoreProcessor { ).updateOwnerPrivilege(Mockito.eq(authorizable), Mockito.eq(OWNER), Mockito.eq(SentryEntityType.ROLE), Mockito.anyList()); } + + @Test + public void testListRolesPrivileges() throws Exception { + MockGroupMappingService.addUserGroupMapping("admin", Sets.newHashSet("admin")); + + Configuration conf = new Configuration(); + conf.set(ServerConfig.SENTRY_STORE_GROUP_MAPPING, MockGroupMappingService.class.getName()); + conf.set(ServerConfig.ADMIN_GROUPS, "admin"); + + SentryPolicyStoreProcessor policyStoreProcessor = + new SentryPolicyStoreProcessor(ApiConstants.SentryPolicyServiceConstants.SENTRY_POLICY_SERVICE_NAME, + conf, sentryStore); + + TSentryPrivilegesResponse returnedResp; + + TSentryPrivilegesRequest request = new TSentryPrivilegesRequest(); + request.setRequestorUserName("user1"); + + // Request privileges when requestorUser is not an admin returns an access denied exception + returnedResp = policyStoreProcessor.list_roles_privileges(request); + Assert.assertEquals(Status.ACCESS_DENIED.getCode(), returnedResp.getStatus().getValue()); + + request.setRequestorUserName("admin"); + + // Request privileges when no roles are created yet returns an empty map object + Mockito.when(sentryStore.getAllRolesPrivileges()).thenReturn( + Collections.emptyMap()); + returnedResp = policyStoreProcessor.list_roles_privileges(request); + Assert.assertEquals(Status.OK.getCode(), returnedResp.getStatus().getValue()); + Assert.assertEquals(0, returnedResp.getPrivilegesMap().size()); + + // Request privileges when roles exist returns a map of the form [roleName, set<privileges>] + ImmutableMap<String, Set<TSentryPrivilege>> rolesPrivileges = ImmutableMap.of( + "role1", Sets.newHashSet( + newSentryPrivilege("TABLE", "db1", "tbl1", "ALL"), + newSentryPrivilege("DATABASE", "db1", "", "INSERT")), + "role2", Sets.newHashSet( + newSentryPrivilege("SERVER", "", "", "ALL")), + "role3", Sets.newHashSet() + ); + + Mockito.when(sentryStore.getAllRolesPrivileges()).thenReturn(rolesPrivileges); + returnedResp = policyStoreProcessor.list_roles_privileges(request); + Assert.assertEquals(Status.OK(), returnedResp.getStatus()); + Assert.assertEquals(3, returnedResp.getPrivilegesMap().size()); + Assert.assertEquals(2, returnedResp.getPrivilegesMap().get("role1").size()); + Assert.assertEquals(1, returnedResp.getPrivilegesMap().get("role2").size()); + Assert.assertEquals(0, returnedResp.getPrivilegesMap().get("role3").size()); + } + + @Test + public void testListUsersPrivileges() throws Exception { + MockGroupMappingService.addUserGroupMapping("admin", Sets.newHashSet("admin")); + + Configuration conf = new Configuration(); + conf.set(ServerConfig.SENTRY_STORE_GROUP_MAPPING, MockGroupMappingService.class.getName()); + conf.set(ServerConfig.ADMIN_GROUPS, "admin"); + + SentryPolicyStoreProcessor policyStoreProcessor = + new SentryPolicyStoreProcessor(ApiConstants.SentryPolicyServiceConstants.SENTRY_POLICY_SERVICE_NAME, + conf, sentryStore); + + TSentryPrivilegesResponse returnedResp; + + TSentryPrivilegesRequest request = new TSentryPrivilegesRequest(); + request.setRequestorUserName("user1"); + + // Request privileges when requestorUser is not an admin returns an access denied exception + returnedResp = policyStoreProcessor.list_users_privileges(request); + Assert.assertEquals(Status.ACCESS_DENIED.getCode(), returnedResp.getStatus().getValue()); + + request.setRequestorUserName("admin"); + + // Request privileges when no roles are created yet returns an empty map object + Mockito.when(sentryStore.getAllUsersPrivileges()).thenReturn( + Collections.emptyMap()); + returnedResp = policyStoreProcessor.list_users_privileges(request); + Assert.assertEquals(Status.OK.getCode(), returnedResp.getStatus().getValue()); + Assert.assertEquals(0, returnedResp.getPrivilegesMap().size()); + + // Request privileges when roles exist returns a map of the form [userName, set<privileges>] + ImmutableMap<String, Set<TSentryPrivilege>> usersPrivileges = ImmutableMap.of( + "user1", Sets.newHashSet( + newSentryPrivilege("TABLE", "db1", "tbl1", "ALL"), + newSentryPrivilege("DATABASE", "db1", "", "INSERT")), + "user2", Sets.newHashSet( + newSentryPrivilege("SERVER", "", "", "ALL")), + "user3", Sets.newHashSet() + ); + + Mockito.when(sentryStore.getAllUsersPrivileges()).thenReturn(usersPrivileges); + returnedResp = policyStoreProcessor.list_users_privileges(request); + Assert.assertEquals(Status.OK(), returnedResp.getStatus()); + Assert.assertEquals(3, returnedResp.getPrivilegesMap().size()); + Assert.assertEquals(2, returnedResp.getPrivilegesMap().get("user1").size()); + Assert.assertEquals(1, returnedResp.getPrivilegesMap().get("user2").size()); + Assert.assertEquals(0, returnedResp.getPrivilegesMap().get("user3").size()); + } } http://git-wip-us.apache.org/repos/asf/sentry/blob/96a47339/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/provider/db/service/persistent/TestSentryStore.java ---------------------------------------------------------------------- diff --git a/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/provider/db/service/persistent/TestSentryStore.java b/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/provider/db/service/persistent/TestSentryStore.java index 52ce72c..954122e 100644 --- a/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/provider/db/service/persistent/TestSentryStore.java +++ b/sentry-service/sentry-service-server/src/test/java/org/apache/sentry/provider/db/service/persistent/TestSentryStore.java @@ -4322,4 +4322,113 @@ public class TestSentryStore extends org.junit.Assert { user = sentryStore.getMSentryUserByName(userName, false); assertNull(user); } + + @Test + public void testGetAllRolesPrivileges() throws Exception { + Map<String, Set<TSentryPrivilege>> allPrivileges; + + // The map must be empty (no null) if no roles exist on the system yet + allPrivileges = sentryStore.getAllRolesPrivileges(); + assertNotNull(allPrivileges); + assertTrue(allPrivileges.isEmpty()); + + final String GRANTOR = "g1"; + + final String ROLE1 = "role1"; + final TSentryPrivilege ROLE1_PRIV1 = + toTSentryPrivilege("ALL", "TABLE", "server1", "db1", "table1"); + final TSentryPrivilege ROLE1_PRIV2 = + toTSentryPrivilege("SELECT", "TABLE", "server1", "db1", "table2"); + + createRole(ROLE1); + sentryStore.alterSentryGrantPrivilege(GRANTOR, SentryEntityType.ROLE, ROLE1, ROLE1_PRIV1, null); + sentryStore.alterSentryGrantPrivilege(GRANTOR, SentryEntityType.ROLE, ROLE1, ROLE1_PRIV2, null); + + final String ROLE2 = "role2"; + final TSentryPrivilege ROLE2_PRIV1 = + toTSentryPrivilege("INSERT", "DATABASE", "server1", "db1", ""); + final TSentryPrivilege ROLE2_PRIV2 = + toTSentryPrivilege("ALL", "SERVER", "server1", "", ""); + + createRole(ROLE2); + sentryStore.alterSentryGrantPrivilege(GRANTOR, SentryEntityType.ROLE, ROLE2, ROLE2_PRIV1, null); + sentryStore.alterSentryGrantPrivilege(GRANTOR, SentryEntityType.ROLE, ROLE2, ROLE2_PRIV2, null); + + final String ROLE3 = "role3"; + + createRole(ROLE3); + + allPrivileges = sentryStore.getAllRolesPrivileges(); + + // Must return 3 roles, 2 roles has 2 privileges each, 1 role has no privileges + assertEquals(3, allPrivileges.size()); + assertEquals(2, allPrivileges.get(ROLE1).size()); + assertTrue(allPrivileges.get(ROLE1).contains(ROLE1_PRIV1)); + assertTrue(allPrivileges.get(ROLE1).contains(ROLE1_PRIV2)); + assertEquals(2, allPrivileges.get(ROLE2).size()); + assertTrue(allPrivileges.get(ROLE2).contains(ROLE2_PRIV1)); + assertTrue(allPrivileges.get(ROLE2).contains(ROLE2_PRIV2)); + assertEquals(0, allPrivileges.get(ROLE3).size()); + } + + @Test + public void testGetAllUsersPrivileges() throws Exception { + Map<String, Set<TSentryPrivilege>> allPrivileges; + + // The map must be empty (no null) if no roles exist on the system yet + allPrivileges = sentryStore.getAllUsersPrivileges(); + assertNotNull(allPrivileges); + assertTrue(allPrivileges.isEmpty()); + + final String GRANTOR = "g1"; + + final String USER1 = "user1"; + final TSentryPrivilege USER1_PRIV1 = + toTSentryPrivilege("ALL", "TABLE", "server1", "db1", "table1"); + final TSentryPrivilege USER1_PRIV2 = + toTSentryPrivilege("SELECT", "TABLE", "server1", "db1", "table2"); + + createUser(USER1); + sentryStore.alterSentryGrantPrivilege(GRANTOR, SentryEntityType.USER, USER1, USER1_PRIV1, null); + sentryStore.alterSentryGrantPrivilege(GRANTOR, SentryEntityType.USER,USER1, USER1_PRIV2, null); + + final String USER2 = "user2"; + final TSentryPrivilege USER2_PRIV1 = + toTSentryPrivilege("INSERT", "DATABASE", "server1", "db1", ""); + final TSentryPrivilege USER2_PRIV2 = + toTSentryPrivilege("ALL", "SERVER", "server1", "", ""); + + createUser(USER2); + sentryStore.alterSentryGrantPrivilege(GRANTOR, SentryEntityType.USER,USER2, USER2_PRIV1, null); + sentryStore.alterSentryGrantPrivilege(GRANTOR, SentryEntityType.USER,USER2, USER2_PRIV2, null); + + final String USER3 = "user3"; + + createUser(USER3); + + allPrivileges = sentryStore.getAllUsersPrivileges(); + + // Must return 3 roles, 2 roles has 2 privileges each, 1 role has no privileges + assertEquals(3, allPrivileges.size()); + assertEquals(2, allPrivileges.get(USER1).size()); + assertTrue(allPrivileges.get(USER1).contains(USER1_PRIV1)); + assertTrue(allPrivileges.get(USER1).contains(USER1_PRIV2)); + assertEquals(2, allPrivileges.get(USER2).size()); + assertTrue(allPrivileges.get(USER2).contains(USER2_PRIV1)); + assertTrue(allPrivileges.get(USER2).contains(USER2_PRIV2)); + assertEquals(0, allPrivileges.get(USER3).size()); + } + + private TSentryPrivilege toTSentryPrivilege(String action, String scope, String server, + String dbName, String tableName) { + TSentryPrivilege privilege = new TSentryPrivilege(); + privilege.setPrivilegeScope(scope); + privilege.setServerName(server); + privilege.setDbName(dbName); + privilege.setTableName(tableName); + privilege.setAction(action); + privilege.setCreateTime(System.currentTimeMillis()); + + return privilege; + } }
