Skip to content

Commit 4817d1b

Browse files
authored
RANGER-5505: update RangerEmbeddedAuthorizer to support caller provided audit handler (#864)
1 parent a7746d7 commit 4817d1b

7 files changed

Lines changed: 159 additions & 51 deletions

File tree

authz-embedded/src/main/java/org/apache/ranger/authz/embedded/RangerAuthzAuditHandler.java

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -22,20 +22,19 @@
2222
import org.apache.ranger.audit.model.AuthzAuditEvent;
2323
import org.apache.ranger.plugin.audit.RangerDefaultAuditHandler;
2424
import org.apache.ranger.plugin.policyengine.RangerAccessResult;
25-
import org.apache.ranger.plugin.service.RangerBasePlugin;
2625

2726
import java.util.ArrayList;
2827
import java.util.Collection;
2928

3029
public class RangerAuthzAuditHandler extends RangerDefaultAuditHandler implements AutoCloseable {
31-
private final RangerBasePlugin plugin;
30+
private final String appType;
3231
private final Collection<AuthzAuditEvent> auditEvents = new ArrayList<>();
3332
private boolean deniedExists;
3433

35-
public RangerAuthzAuditHandler(RangerBasePlugin plugin) {
34+
public RangerAuthzAuditHandler(String appType) {
3635
super();
3736

38-
this.plugin = plugin;
37+
this.appType = appType;
3938
}
4039

4140
@Override
@@ -44,7 +43,7 @@ public void processResult(RangerAccessResult result) {
4443
AuthzAuditEvent auditEvent = getAuthzEvents(result);
4544

4645
if (auditEvent != null) {
47-
auditEvent.setAgentId(plugin.getAppId());
46+
auditEvent.setAgentId(appType);
4847

4948
if (result.getIsAccessDetermined() && !result.getIsAllowed()) {
5049
deniedExists = true;
@@ -66,4 +65,8 @@ public void processResults(Collection<RangerAccessResult> results) {
6665
public void close() {
6766
auditEvents.forEach(super::logAuthzAudit);
6867
}
68+
69+
protected Collection<AuthzAuditEvent> getAuditEvents() {
70+
return auditEvents;
71+
}
6972
}

authz-embedded/src/main/java/org/apache/ranger/authz/embedded/RangerAuthzConfig.java

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,8 @@
2424
import java.util.Properties;
2525

2626
public class RangerAuthzConfig {
27-
public static final String PROP_PREFIX_INIT_SERVICES = "ranger.authz.init.services";
27+
public static final String PROP_APP_TYPE = "ranger.authz.app.type";
28+
public static final String PROP_INIT_SERVICES = "ranger.authz.init.services";
2829
public static final String PROP_PREFIX_DEFAULT = "ranger.authz.default.";
2930
public static final String PROP_PREFIX_AUDIT = "ranger.authz.audit.";
3031
public static final String PROP_PREFIX_SERVICE = "ranger.authz.service.";
@@ -37,7 +38,7 @@ public RangerAuthzConfig(Properties properties) {
3738
}
3839

3940
public String[] getInitServices() {
40-
String initServices = properties.getProperty(PROP_PREFIX_INIT_SERVICES);
41+
String initServices = properties.getProperty(PROP_INIT_SERVICES);
4142

4243
if (StringUtils.isBlank(initServices)) {
4344
return new String[0];
@@ -46,6 +47,10 @@ public String[] getInitServices() {
4647
return initServices.split(",");
4748
}
4849

50+
public String getAppType() {
51+
return properties.getProperty(PROP_APP_TYPE);
52+
}
53+
4954
public Properties getAuditProperties() {
5055
Properties ret = new Properties();
5156

authz-embedded/src/main/java/org/apache/ranger/authz/embedded/RangerEmbeddedAuthorizer.java

Lines changed: 62 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -48,17 +48,21 @@ public class RangerEmbeddedAuthorizer extends RangerAuthorizer {
4848
private static final Logger LOG = LoggerFactory.getLogger(RangerEmbeddedAuthorizer.class);
4949

5050
private final RangerAuthzConfig config;
51+
private final String appType;
5152
private final Map<String, RangerAuthzPlugin> plugins = new HashMap<>();
5253

5354
public RangerEmbeddedAuthorizer(Properties properties) {
5455
super(properties);
5556

56-
this.config = new RangerAuthzConfig(properties);
57+
this.config = new RangerAuthzConfig(properties);
58+
this.appType = config.getAppType();
5759
}
5860

5961
@Override
6062
public void init() throws RangerAuthzException {
61-
AuditProviderFactory.getInstance().init(config.getAuditProperties(), "ranger-authz");
63+
String appType = StringUtils.isNotBlank(this.appType) ? this.appType : "ranger-authz";
64+
65+
AuditProviderFactory.getInstance().init(config.getAuditProperties(), appType);
6266

6367
String[] initServices = config.getInitServices();
6468

@@ -83,8 +87,9 @@ public RangerAuthzResult authorize(RangerAuthzRequest request) throws RangerAuth
8387
validateRequest(request);
8488

8589
RangerAuthzPlugin plugin = getOrCreatePlugin(request.getContext().getServiceName(), request.getContext().getServiceType());
90+
String appType = StringUtils.isNotBlank(this.appType) ? this.appType : plugin.getPlugin().getAppId();
8691

87-
try (RangerAuthzAuditHandler auditHandler = new RangerAuthzAuditHandler(plugin.getPlugin())) {
92+
try (RangerAuthzAuditHandler auditHandler = new RangerAuthzAuditHandler(appType)) {
8893
return authorize(request, plugin, auditHandler);
8994
}
9095
}
@@ -93,45 +98,28 @@ public RangerAuthzResult authorize(RangerAuthzRequest request) throws RangerAuth
9398
public RangerMultiAuthzResult authorize(RangerMultiAuthzRequest request) throws RangerAuthzException {
9499
validateRequest(request);
95100

96-
RangerAuthzPlugin plugin = getOrCreatePlugin(request.getContext().getServiceName(), request.getContext().getServiceType());
97-
RangerMultiAuthzResult result = new RangerMultiAuthzResult(request.getRequestId());
101+
RangerAuthzPlugin plugin = getOrCreatePlugin(request.getContext().getServiceName(), request.getContext().getServiceType());
102+
String appType = StringUtils.isNotBlank(this.appType) ? this.appType : plugin.getPlugin().getAppId();
98103

99-
if (request.getAccesses() != null) {
100-
int allowedCount = 0;
101-
int deniedCount = 0;
102-
int notDeterminedCount = 0;
104+
try (RangerAuthzAuditHandler auditHandler = new RangerAuthzAuditHandler(appType)) {
105+
return authorize(request, plugin, auditHandler);
106+
}
107+
}
103108

104-
result.setAccesses(new ArrayList<>(request.getAccesses().size()));
109+
public RangerAuthzResult authorize(RangerAuthzRequest request, RangerAuthzAuditHandler auditHandler) throws RangerAuthzException {
110+
validateRequest(request);
105111

106-
try (RangerAuthzAuditHandler auditHandler = new RangerAuthzAuditHandler(plugin.getPlugin())) {
107-
for (RangerAccessInfo accessInfo : request.getAccesses()) {
108-
RangerAuthzRequest authzRequest = new RangerAuthzRequest(null, request.getUser(), accessInfo, request.getContext());
109-
RangerAuthzResult authzResult = authorize(authzRequest, plugin, auditHandler);
112+
RangerAuthzPlugin plugin = getOrCreatePlugin(request.getContext().getServiceName(), request.getContext().getServiceType());
110113

111-
if (authzResult.getDecision() == AccessDecision.ALLOW) {
112-
allowedCount++;
113-
} else if (authzResult.getDecision() == AccessDecision.DENY) {
114-
deniedCount++;
115-
} else if (authzResult.getDecision() == AccessDecision.NOT_DETERMINED) {
116-
notDeterminedCount++;
117-
}
114+
return authorize(request, plugin, auditHandler);
115+
}
118116

119-
result.getAccesses().add(authzResult);
120-
}
121-
}
117+
public RangerMultiAuthzResult authorize(RangerMultiAuthzRequest request, RangerAuthzAuditHandler auditHandler) throws RangerAuthzException {
118+
validateRequest(request);
122119

123-
if (allowedCount == request.getAccesses().size()) {
124-
result.setDecision(AccessDecision.ALLOW);
125-
} else if (deniedCount == request.getAccesses().size()) {
126-
result.setDecision(AccessDecision.DENY);
127-
} else if (notDeterminedCount == request.getAccesses().size()) {
128-
result.setDecision(AccessDecision.NOT_DETERMINED);
129-
} else {
130-
result.setDecision(AccessDecision.PARTIAL);
131-
}
132-
}
120+
RangerAuthzPlugin plugin = getOrCreatePlugin(request.getContext().getServiceName(), request.getContext().getServiceType());
133121

134-
return result;
122+
return authorize(request, plugin, auditHandler);
135123
}
136124

137125
@Override
@@ -179,6 +167,45 @@ private RangerAuthzResult authorize(RangerAuthzRequest request, RangerAuthzPlugi
179167
return plugin.authorize(request, auditHandler);
180168
}
181169

170+
private RangerMultiAuthzResult authorize(RangerMultiAuthzRequest request, RangerAuthzPlugin plugin, RangerAuthzAuditHandler auditHandler) throws RangerAuthzException {
171+
RangerMultiAuthzResult result = new RangerMultiAuthzResult(request.getRequestId());
172+
173+
if (request.getAccesses() != null) {
174+
int allowedCount = 0;
175+
int deniedCount = 0;
176+
int notDeterminedCount = 0;
177+
178+
result.setAccesses(new ArrayList<>(request.getAccesses().size()));
179+
180+
for (RangerAccessInfo accessInfo : request.getAccesses()) {
181+
RangerAuthzRequest authzRequest = new RangerAuthzRequest(null, request.getUser(), accessInfo, request.getContext());
182+
RangerAuthzResult authzResult = authorize(authzRequest, plugin, auditHandler);
183+
184+
if (authzResult.getDecision() == AccessDecision.ALLOW) {
185+
allowedCount++;
186+
} else if (authzResult.getDecision() == AccessDecision.DENY) {
187+
deniedCount++;
188+
} else if (authzResult.getDecision() == AccessDecision.NOT_DETERMINED) {
189+
notDeterminedCount++;
190+
}
191+
192+
result.getAccesses().add(authzResult);
193+
}
194+
195+
if (allowedCount == request.getAccesses().size()) {
196+
result.setDecision(AccessDecision.ALLOW);
197+
} else if (deniedCount == request.getAccesses().size()) {
198+
result.setDecision(AccessDecision.DENY);
199+
} else if (notDeterminedCount == request.getAccesses().size()) {
200+
result.setDecision(AccessDecision.NOT_DETERMINED);
201+
} else {
202+
result.setDecision(AccessDecision.PARTIAL);
203+
}
204+
}
205+
206+
return result;
207+
}
208+
182209
private RangerAuthzPlugin getOrCreatePlugin(String serviceName, String serviceType) throws RangerAuthzException {
183210
RangerAuthzPlugin ret = plugins.get(serviceName);
184211

authz-embedded/src/test/java/org/apache/ranger/authz/embedded/TestEmbeddedAuthorizer.java

Lines changed: 64 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222
import com.fasterxml.jackson.core.type.TypeReference;
2323
import com.fasterxml.jackson.databind.DeserializationFeature;
2424
import com.fasterxml.jackson.databind.ObjectMapper;
25+
import org.apache.ranger.audit.model.AuthzAuditEvent;
2526
import org.apache.ranger.authz.model.RangerAccessContext;
2627
import org.apache.ranger.authz.model.RangerAuthzRequest;
2728
import org.apache.ranger.authz.model.RangerAuthzResult;
@@ -32,6 +33,7 @@
3233
import org.junit.jupiter.api.Test;
3334

3435
import java.io.InputStream;
36+
import java.util.Collection;
3537
import java.util.Collections;
3638
import java.util.List;
3739
import java.util.Properties;
@@ -111,11 +113,21 @@ private void runAuthzTest(String testName) throws Exception {
111113
continue;
112114
}
113115

114-
RangerAuthzRequest request = test.request;
116+
RangerAuthzRequest request = test.request;
115117
RangerAuthzResult expected = test.result;
116-
RangerAuthzResult result = authorizer.authorize(request);
117118

118-
assertEquals(expected, result);
119+
if (test.audits == null) {
120+
RangerAuthzResult result = authorizer.authorize(request);
121+
122+
assertEquals(expected, result);
123+
} else {
124+
try (TestAuthzAuditHandler auditHandler = new TestAuthzAuditHandler("test")) {
125+
RangerAuthzResult result = authorizer.authorize(request, auditHandler);
126+
127+
assertEquals(expected, result);
128+
auditEquals(test.audits, auditHandler.getAuditEvents());
129+
}
130+
}
119131
}
120132
} finally {
121133
if (authorizer != null) {
@@ -142,9 +154,19 @@ private void runMultiAuthzTest(String testName) throws Exception {
142154

143155
RangerMultiAuthzRequest request = test.request;
144156
RangerMultiAuthzResult expected = test.result;
145-
RangerMultiAuthzResult result = authorizer.authorize(request);
146157

147-
assertEquals(expected, result);
158+
if (test.audits == null) {
159+
RangerMultiAuthzResult result = authorizer.authorize(request);
160+
161+
assertEquals(expected, result);
162+
} else {
163+
try (TestAuthzAuditHandler auditHandler = new TestAuthzAuditHandler("test")) {
164+
RangerMultiAuthzResult result = authorizer.authorize(request, auditHandler);
165+
166+
assertEquals(expected, result);
167+
auditEquals(test.audits, auditHandler.getAuditEvents());
168+
}
169+
}
148170
}
149171
} finally {
150172
if (authorizer != null) {
@@ -187,19 +209,54 @@ private List<TestResourcePermissionsData> loadTestResourcePermissionsData(String
187209
}
188210
}
189211

212+
private static void auditEquals(List<AuthzAuditEvent> expected, Collection<AuthzAuditEvent> actual) {
213+
assertEquals(expected.size(), actual.size());
214+
215+
AuthzAuditEvent[] actualAudits = actual.toArray(new AuthzAuditEvent[0]);
216+
217+
for (int i = 0; i < expected.size(); i++) {
218+
auditEquals(expected.get(i), actualAudits[i]);
219+
}
220+
}
221+
222+
private static void auditEquals(AuthzAuditEvent expected, AuthzAuditEvent actual) {
223+
assertEquals(expected.getUser(), actual.getUser());
224+
assertEquals(expected.getAccessType(), actual.getAccessType());
225+
assertEquals(expected.getAction(), actual.getAction());
226+
assertEquals(expected.getRepositoryName(), actual.getRepositoryName());
227+
assertEquals(expected.getResourceType(), actual.getResourceType());
228+
assertEquals(expected.getResourcePath(), actual.getResourcePath());
229+
assertEquals(expected.getAccessResult(), actual.getAccessResult());
230+
assertEquals(expected.getPolicyId(), actual.getPolicyId());
231+
assertEquals(expected.getAgentId(), actual.getAgentId());
232+
assertEquals(expected.getAclEnforcer(), actual.getAclEnforcer());
233+
}
234+
190235
private static class TestAuthzData {
191-
public RangerAuthzRequest request;
192-
public RangerAuthzResult result;
236+
public RangerAuthzRequest request;
237+
public RangerAuthzResult result;
238+
public List<AuthzAuditEvent> audits;
193239
}
194240

195241
private static class TestMultiAuthzData {
196242
public RangerMultiAuthzRequest request;
197243
public RangerMultiAuthzResult result;
244+
public List<AuthzAuditEvent> audits;
198245
}
199246

200247
private static class TestResourcePermissionsData {
201248
public RangerResourceInfo resource;
202249
public RangerAccessContext context;
203250
public RangerResourcePermissions permissions;
204251
}
252+
253+
private static class TestAuthzAuditHandler extends RangerAuthzAuditHandler {
254+
public TestAuthzAuditHandler(String appType) {
255+
super(appType);
256+
}
257+
258+
public Collection<AuthzAuditEvent> getAuditEvents() {
259+
return super.getAuditEvents();
260+
}
261+
}
205262
}

authz-embedded/src/test/java/org/apache/ranger/authz/embedded/TestRangerAuthzConfig.java

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
import java.util.Properties;
2525

2626
import static org.junit.jupiter.api.Assertions.assertEquals;
27+
import static org.junit.jupiter.api.Assertions.assertNull;
2728
import static org.junit.jupiter.api.Assertions.assertTrue;
2829

2930
public class TestRangerAuthzConfig {
@@ -35,6 +36,7 @@ public void testEmptyConfig() {
3536
assertTrue(config.getServiceProperties("prod_hive", "hive").isEmpty());
3637
assertTrue(config.getServiceProperties("dev_hdfs", "hdfs").isEmpty());
3738
assertTrue(config.getAuditProperties().isEmpty());
39+
assertNull(config.getAppType());
3840
}
3941

4042
@Test
@@ -44,6 +46,7 @@ public void testDefaultConfigs() {
4446
validateDevHiveProperties(config.getServiceProperties("dev_hive", "hive"));
4547
validateProdHiveProperties(config.getServiceProperties("prod_hive", "hive"));
4648
validateDevHdfsProperties(config.getServiceProperties("dev_hdfs", "hdfs"));
49+
assertEquals("ranger-pdp", config.getAppType());
4750
}
4851

4952
@Test
@@ -75,6 +78,7 @@ public void testAllAuthzConfigs() {
7578
validateDevHdfsProperties(config.getServiceProperties("dev_hdfs", "hdfs"));
7679
validateAuditConfigV2(config.getAuditProperties());
7780
validateAuditConfigV3(config.getAuditProperties());
81+
assertEquals("ranger-pdp", config.getAppType());
7882
}
7983

8084
private void validateDevHiveProperties(Properties prop) {
@@ -156,6 +160,8 @@ private void validateAuditConfigV3(Properties props) {
156160
private static Properties createDefaultProperties() {
157161
Properties props = new Properties();
158162

163+
props.setProperty("ranger.authz.app.type", "ranger-pdp");
164+
159165
props.setProperty("ranger.authz.default.policy.source.impl", "org.apache.ranger.admin.client.RangerAdminRESTClient");
160166
props.setProperty("ranger.authz.default.policy.rest.url", "http://localhost:6080");
161167
props.setProperty("ranger.authz.default.policy.rest.ssl.config.file", "/etc/hive/conf/ranger-policymgr-ssl.xml");

authz-embedded/src/test/resources/test_hive/tests_authz.json

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,12 @@
1515
"permissions": {
1616
"select": { "permission": "select", "access": { "decision": "ALLOW", "policy": { "id": 1, "version": 1 } } }
1717
}
18-
}
18+
},
19+
"audits": [
20+
{
21+
"reqUser": "tbl1-r-user", "access": "select", "action": "select", "repo": "dev_hive", "resType": "table", "resource": "mydb/tbl1", "result": 1, "policy": 1, "agent": "test", "enforcer": "ranger-acl"
22+
}
23+
]
1924
},
2025
{
2126
"request": {

0 commit comments

Comments
 (0)