SentryPolicyStoreProcessor implements SentryPolicyService.Iface { @Override public TListSentryPrivilegesByAuthUserResponse list_sentry_privileges_by_authorizable_and_user( TListSentryPrivilegesByAuthUserRequest request) throws TException { final Timer.Context timerContext = sentryMetrics.listPrivilegesByAuthorizableAndUserTimer.time(); TListSentryPrivilegesByAuthUserResponse response = new TListSentryPrivilegesByAuthUserResponse(); String requestor = request.getRequestorUserName(); String principalName = request.getUser(); TSentryResponseStatus status = checkRequiredParameter(requestor, "requestor parameter must not be null"); status = status != null ? status : checkRequiredParameter(principalName, "user parameter must not be null"); if (status != null) { response.setStatus(status); return response; } principalName = principalName.trim(); Map<TSentryAuthorizable, Set<TSentryPrivilege>> authMap = Maps.newHashMap(); try { validateClientVersion(request.getProtocol_version()); Set<String> requestorGroups = getRequestorGroups(requestor); Boolean admin = inAdminGroups(requestorGroups); if(!admin && !principalName.equalsIgnoreCase(requestor)) { throw new SentryAccessDeniedException("Access denied to " + requestor); } Set<String> principalGroups; if (principalName.equals(requestor)) { principalGroups = requestorGroups; } else { principalGroups = getRequestorGroups(principalName); } Set<String> principalUsers = new HashSet<>(); principalUsers.add(principalName); for (TSentryAuthorizable authorizable : request.getAuthorizableSet()) { Set<TSentryPrivilege> privileges = new HashSet(); TSentryPrivilegeMap groupMap = sentryStore.listSentryPrivilegesByAuthorizable( principalGroups, null, authorizable, false); if (groupMap.getPrivilegeMap() != null) { for (Set<TSentryPrivilege> groupPrivilege : groupMap.getPrivilegeMap().values()) { privileges.addAll(groupPrivilege); } } TSentryPrivilegeMap userMap = sentryStore.listSentryPrivilegesByAuthorizableForUser( principalUsers, authorizable, false); if (userMap.getPrivilegeMap() != null) { for (Set<TSentryPrivilege> userPrivilege : userMap.getPrivilegeMap().values()) { privileges.addAll(userPrivilege); } } authMap.put(authorizable, privileges); } response.setPrivilegesMapByAuth(authMap); response.setStatus(Status.OK()); } catch (SentryAccessDeniedException e) { LOGGER.error(e.getMessage(), e); response.setStatus(Status.AccessDenied(e.getMessage(), e)); } catch (SentryGroupNotFoundException e) { LOGGER.error(e.getMessage(), e); response.setStatus(Status.AccessDenied(e.getMessage(), e)); } catch (SentryThriftAPIMismatchException e) { LOGGER.error(e.getMessage(), e); response.setStatus(Status.THRIFT_VERSION_MISMATCH(e.getMessage(), e)); } catch (SentryInvalidInputException e) { LOGGER.error(e.getMessage(), e); response.setStatus(Status.InvalidInput(e.getMessage(), e)); } catch (Exception e) { String msg = "Unknown error for request: " + request + ", message: " + e.getMessage(); LOGGER.error(msg, e); response.setStatus(Status.RuntimeError(msg, e)); } finally { timerContext.stop(); } return response; } SentryPolicyStoreProcessor(String name,
        Configuration conf, SentryStoreInterface store); void stop(); void registerPlugin(SentryPolicyStorePlugin plugin); @VisibleForTesting Configuration getSentryStoreConf(); @Override TIsSentryAdminResponse is_sentry_admin(TIsSentryAdminRequest request); @Override TCreateSentryRoleResponse create_sentry_role(
    TCreateSentryRoleRequest request); @Override TAlterSentryRoleGrantPrivilegeResponse alter_sentry_role_grant_privilege(TAlterSentryRoleGrantPrivilegeRequest request); @Override TAlterSentryRoleRevokePrivilegeResponse alter_sentry_role_revoke_privilege(TAlterSentryRoleRevokePrivilegeRequest request); @Override TDropSentryRoleResponse drop_sentry_role(
    TDropSentryRoleRequest request); @Override TAlterSentryRoleAddGroupsResponse alter_sentry_role_add_groups(
    TAlterSentryRoleAddGroupsRequest request); @Override TAlterSentryRoleAddUsersResponse alter_sentry_role_add_users(
      TAlterSentryRoleAddUsersRequest request); @Override TAlterSentryRoleDeleteUsersResponse alter_sentry_role_delete_users(
      TAlterSentryRoleDeleteUsersRequest request); @Override TAlterSentryRoleDeleteGroupsResponse alter_sentry_role_delete_groups(
    TAlterSentryRoleDeleteGroupsRequest request); @Override TListSentryRolesResponse list_sentry_roles_by_group(
    TListSentryRolesRequest request); TListSentryRolesResponse list_sentry_roles_by_user(TListSentryRolesForUserRequest request); @Override TListSentryPrivilegesResponse list_sentry_privileges_by_role(
      TListSentryPrivilegesRequest request); @Override TListSentryPrivilegesResponse list_sentry_privileges_by_user(
    TListSentryPrivilegesRequest request); @Override TListSentryPrivilegesResponse list_sentry_privileges_by_user_and_itsgroups(
          TListSentryPrivilegesRequest request); @Override TListSentryPrivilegesForProviderResponse list_sentry_privileges_for_provider(
      TListSentryPrivilegesForProviderRequest request); static Set<String> getGroupsFromUserName(Configuration conf,
      String userName); @Override TDropPrivilegesResponse drop_sentry_privilege(
      TDropPrivilegesRequest request); @Override TRenamePrivilegesResponse rename_sentry_privilege(
      TRenamePrivilegesRequest request); @Override TListSentryPrivilegesByAuthResponse list_sentry_privileges_by_authorizable(
      TListSentryPrivilegesByAuthRequest request); @Override TListSentryPrivilegesByAuthUserResponse list_sentry_privileges_by_authorizable_and_user(
      TListSentryPrivilegesByAuthUserRequest request); @Override TSentryConfigValueResponse get_sentry_config_value(
          TSentryConfigValueRequest request); @Override @SuppressWarnings("PMD.AvoidBranchingStatementAsLastInLoop") TSentryExportMappingDataResponse export_sentry_mapping_data(
      TSentryExportMappingDataRequest request); @Override TSentryImportMappingDataResponse import_sentry_mapping_data(
      TSentryImportMappingDataRequest request); @Override TSentrySyncIDResponse sentry_sync_notifications(TSentrySyncIDRequest request); @Override TSentryHmsEventNotificationResponse sentry_notify_hms_event(TSentryHmsEventNotification request); @Override TSentryPrivilegesResponse list_roles_privileges(TSentryPrivilegesRequest request); @Override TSentryPrivilegesResponse list_users_privileges(TSentryPrivilegesRequest request);  }
@Test public void testListPrivilegesByAuthorizableAndUser() throws Exception { MockGroupMappingService.addUserGroupMapping("admin", Sets.newHashSet("admin")); String user1 = "user1"; String g1 = "g1"; MockGroupMappingService.addUserGroupMapping(user1, Sets.newHashSet(g1)); Configuration conf = new Configuration(); conf.set(ServerConfig.SENTRY_STORE_GROUP_MAPPING, "org.apache.sentry.api.service.thrift.MockGroupMappingService"); conf.set(ServerConfig.ADMIN_GROUPS, "admin"); SentryPolicyStoreProcessor policyStoreProcessor = new SentryPolicyStoreProcessor( ApiConstants.SentryPolicyServiceConstants.SENTRY_POLICY_SERVICE_NAME, conf, sentryStore); TListSentryPrivilegesByAuthUserResponse returnedResp; TListSentryPrivilegesByAuthUserResponse expectedResp; returnedResp = policyStoreProcessor.list_sentry_privileges_by_authorizable_and_user( newAuthRequest("admin", null, null)); expectedResp = new TListSentryPrivilegesByAuthUserResponse(); expectedResp.setStatus(Status.InvalidInput("user parameter must not be null", new SentryInvalidInputException("user parameter must not be null"))); Assert.assertEquals(expectedResp.getStatus().getValue(), returnedResp.getStatus().getValue()); TSentryAuthorizable requestedAuthorizable = new TSentryAuthorizable(); requestedAuthorizable.setServer("server1"); requestedAuthorizable.setDb("db1"); Set<TSentryAuthorizable> requestedAuthorizables = new HashSet<>(); requestedAuthorizables.add(requestedAuthorizable); Set<String> users = new HashSet<>(); users.add(user1); Set<String> groups = new HashSet<>(); groups.add(g1); returnedResp = policyStoreProcessor.list_sentry_privileges_by_authorizable_and_user( newAuthRequest("unknown_user", requestedAuthorizables, user1)); expectedResp = new TListSentryPrivilegesByAuthUserResponse(); expectedResp.setStatus(Status.AccessDenied("Access denied to unknown_user", new SentryAccessDeniedException("Access denied to unknown_user"))); Assert.assertEquals(expectedResp.getStatus().getValue(), returnedResp.getStatus().getValue()); Set<TSentryPrivilege> user1Privileges = Sets.newHashSet( newSentryPrivilege("database", "db1", "t1", "*"), newSentryPrivilege("database", "db1", "t2", "*")); Map<String, Set<TSentryPrivilege>> user1PrivilegesMap = Maps.newTreeMap(); user1PrivilegesMap.put(user1, user1Privileges); Mockito.when(sentryStore.listSentryPrivilegesByAuthorizableForUser( users, requestedAuthorizable, false)).thenReturn( new TSentryPrivilegeMap(user1PrivilegesMap)); Mockito.when(sentryStore.listSentryPrivilegesByAuthorizable( groups, null, requestedAuthorizable, false)).thenReturn( new TSentryPrivilegeMap()); returnedResp = policyStoreProcessor.list_sentry_privileges_by_authorizable_and_user( newAuthRequest("admin", requestedAuthorizables, user1)); Assert.assertEquals(1, returnedResp.getPrivilegesMapByAuthSize()); Assert.assertEquals(2, returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).size()); Assert.assertEquals(Status.OK(), returnedResp.getStatus()); assertTrue("User1 should have ALL privileges in db1.t1", returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).contains( newSentryPrivilege("database", "db1", "t1", "*"))); assertTrue("User1 should have ALL privileges in db1.t2", returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).contains( newSentryPrivilege("database", "db1", "t2", "*"))); returnedResp = policyStoreProcessor.list_sentry_privileges_by_authorizable_and_user( newAuthRequest(user1, requestedAuthorizables, user1)); Assert.assertEquals(1, returnedResp.getPrivilegesMapByAuthSize()); Assert.assertEquals(2, returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).size()); Assert.assertEquals(Status.OK(), returnedResp.getStatus()); assertTrue("User1 should have ALL privileges in db1.t1", returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).contains( newSentryPrivilege("database", "db1", "t1", "*"))); assertTrue("User1 should have ALL privileges in db1.t2", returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).contains( newSentryPrivilege("database", "db1", "t2", "*"))); returnedResp = policyStoreProcessor.list_sentry_privileges_by_authorizable_and_user( newAuthRequest("bad_user", requestedAuthorizables, user1)); Assert.assertEquals(Status.ACCESS_DENIED.getCode(), returnedResp.getStatus().getValue()); assertNull(returnedResp.getPrivilegesMapByAuth()); Set<TSentryPrivilege> g1Privileges = Sets.newHashSet( newSentryPrivilege("database", "db1", "t3", "*")); Map<String, Set<TSentryPrivilege>> g1PrivilegesMap = Maps.newTreeMap(); g1PrivilegesMap.put(g1, g1Privileges); Mockito.when(sentryStore.listSentryPrivilegesByAuthorizable( groups, null, requestedAuthorizable, false)).thenReturn( new TSentryPrivilegeMap(g1PrivilegesMap)); returnedResp = policyStoreProcessor.list_sentry_privileges_by_authorizable_and_user( newAuthRequest(user1, requestedAuthorizables, user1)); Assert.assertEquals(1, returnedResp.getPrivilegesMapByAuthSize()); Assert.assertEquals(3, returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).size()); Assert.assertEquals(Status.OK(), returnedResp.getStatus()); assertTrue("User1 should have ALL privileges in db1.t1", returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).contains( newSentryPrivilege("database", "db1", "t1", "*"))); assertTrue("User1 should have ALL privileges in db1.t2", returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).contains( newSentryPrivilege("database", "db1", "t2", "*"))); assertTrue("User1 should have ALL privileges in db1.t3", returnedResp.getPrivilegesMapByAuth().get(requestedAuthorizable).contains( newSentryPrivilege("database", "db1", "t3", "*"))); }