|
3 | 3 | */ |
4 | 4 | package com.sap.cds.feature.auditlog.ng; |
5 | 5 |
|
| 6 | +import static java.util.Objects.*; |
| 7 | +import static org.slf4j.LoggerFactory.*; |
| 8 | + |
6 | 9 | import java.time.Instant; |
7 | 10 | import java.util.Collection; |
8 | | -import static java.util.Objects.requireNonNull; |
| 11 | +import java.util.Map; |
9 | 12 | import java.util.UUID; |
10 | 13 | import java.util.stream.Collectors; |
11 | 14 |
|
12 | 15 | import org.slf4j.Logger; |
13 | | -import static org.slf4j.LoggerFactory.getLogger; |
14 | 16 |
|
15 | | -import com.fasterxml.jackson.core.JsonParseException; |
16 | 17 | import com.fasterxml.jackson.core.JsonProcessingException; |
17 | 18 | import com.fasterxml.jackson.databind.ObjectMapper; |
18 | 19 | import com.fasterxml.jackson.databind.node.ArrayNode; |
19 | 20 | import com.fasterxml.jackson.databind.node.ObjectNode; |
| 21 | +import com.sap.cds.services.EventContext; |
20 | 22 | import com.sap.cds.services.auditlog.Access; |
21 | 23 | import com.sap.cds.services.auditlog.Attachment; |
22 | 24 | import com.sap.cds.services.auditlog.Attribute; |
@@ -62,22 +64,66 @@ public class AuditLogNGHandler implements EventHandler { |
62 | 64 | } |
63 | 65 |
|
64 | 66 | @On |
65 | | - public void handleSecurityEvent(SecurityLogContext context) { |
| 67 | + public void handleGeneralEvent(EventContext context) { |
66 | 68 | try { |
67 | | - ArrayNode alsEvents = createSecurityEvent(context); |
68 | | - communicator.sendBulkRequest(alsEvents); |
69 | | - } catch (JsonParseException e) { |
70 | | - LOGGER.error("Audit Log write exception occurred for security event", e); |
| 69 | + if (context instanceof SecurityLogContext || context.getEvent().equals("securityLog")) { |
| 70 | + LOGGER.debug("Handling security log event"); |
| 71 | + handleSecurityEvent(context.as(SecurityLogContext.class)); |
| 72 | + return; |
| 73 | + } else if (context instanceof DataAccessLogContext || context.getEvent().equals("dataAccessLog")) { |
| 74 | + LOGGER.debug("Handling data access log event"); |
| 75 | + handleDataAccessEvent(context.as(DataAccessLogContext.class)); |
| 76 | + return; |
| 77 | + } else if (context instanceof ConfigChangeLogContext || context.getEvent().equals("configChangeLog")) { |
| 78 | + LOGGER.debug("Handling configuration change log event"); |
| 79 | + handleConfigChangeEvent(context.as(ConfigChangeLogContext.class)); |
| 80 | + return; |
| 81 | + } else if (context instanceof DataModificationLogContext || context.getEvent().equals("dataModificationLog")) { |
| 82 | + LOGGER.debug("Handling data modification log event"); |
| 83 | + handleDataModificationEvent(context.as(DataModificationLogContext.class)); |
| 84 | + return; |
| 85 | + } else { |
| 86 | + ArrayNode alsEvents = createGeneralEvent(context); |
| 87 | + communicator.sendBulkRequest(alsEvents); |
| 88 | + } |
| 89 | + } catch (JsonProcessingException e) { |
| 90 | + LOGGER.error("Audit Log write exception occurred", e); |
71 | 91 | throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_INVALID_MESSAGE, e); |
72 | 92 | } catch (ErrorStatusException e) { |
73 | | - LOGGER.error("Audit Log service not available for security event", e); |
| 93 | + LOGGER.error("Audit Log service not available", e); |
74 | 94 | throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_NOT_AVAILABLE, e); |
75 | | - } catch (Exception e) { |
76 | | - LOGGER.error("Unexpected exception while handling security event", e); |
| 95 | + } catch (Exception e) { |
| 96 | + LOGGER.error("Unexpected exception", e); |
77 | 97 | throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_INVALID_MESSAGE, e); |
78 | 98 | } |
79 | 99 | } |
80 | 100 |
|
| 101 | + private ArrayNode createGeneralEvent(EventContext context) throws JsonProcessingException { |
| 102 | + UserInfo userInfo = requireNonNull(context.getUserInfo(), "UserInfo in EventContext must not be null"); |
| 103 | + String eventType = requireNonNull((String) context.getEvent(), "EventType in EventContext must not be null"); |
| 104 | + Map<String, Object> data = (Map<String, Object>) context.get("data"); |
| 105 | + String eventJson = (String) data.get("event"); |
| 106 | + |
| 107 | + ObjectNode eventEnvelope = buildEventEnvelope(OBJECT_MAPPER, eventType, userInfo); |
| 108 | + ObjectNode metadata = buildEventMetadata(); |
| 109 | + ObjectNode parsedEventNode = (ObjectNode) OBJECT_MAPPER.readTree(eventJson); |
| 110 | + ObjectNode wrappedDataNode = OBJECT_MAPPER.createObjectNode(); |
| 111 | + wrappedDataNode.set(eventType, parsedEventNode); |
| 112 | + ObjectNode alsData = buildAuditLogEventData(metadata, wrappedDataNode); |
| 113 | + eventEnvelope.set("data", alsData); |
| 114 | + |
| 115 | + ArrayNode result = OBJECT_MAPPER.createArrayNode(); |
| 116 | + result.add(eventEnvelope); |
| 117 | + |
| 118 | + LOGGER.debug("Created general event for Audit Log NG: {}", result.toString()); |
| 119 | + return result; |
| 120 | + } |
| 121 | + |
| 122 | + public void handleSecurityEvent(SecurityLogContext context) throws JsonProcessingException { |
| 123 | + ArrayNode alsEvents = createSecurityEvent(context); |
| 124 | + communicator.sendBulkRequest(alsEvents); |
| 125 | + } |
| 126 | + |
81 | 127 | /** |
82 | 128 | * Creates an ArrayNode representing security events for the Audit Log service. |
83 | 129 | * |
@@ -141,21 +187,9 @@ private ObjectNode createLegacySecurityOrigEvent(UserInfo userInfo, SecurityLog |
141 | 187 | return envelop; |
142 | 188 | } |
143 | 189 |
|
144 | | - @On |
145 | | - public void handleDataAccessEvent(DataAccessLogContext context) { |
146 | | - try { |
147 | | - ArrayNode alsEvents = createAlsDataAccessEvents(context); |
148 | | - communicator.sendBulkRequest(alsEvents); |
149 | | - } catch (JsonParseException e) { |
150 | | - LOGGER.error("Audit Log write exception occurred for data access event", e); |
151 | | - throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_INVALID_MESSAGE, e); |
152 | | - } catch (ErrorStatusException e) { |
153 | | - LOGGER.error("Audit Log service not available for data access event", e); |
154 | | - throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_NOT_AVAILABLE, e); |
155 | | - } catch (Exception e) { |
156 | | - LOGGER.error("Unexpected exception while handling data access event", e); |
157 | | - throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_INVALID_MESSAGE, e); |
158 | | - } |
| 190 | + public void handleDataAccessEvent(DataAccessLogContext context) throws JsonProcessingException { |
| 191 | + ArrayNode alsEvents = createAlsDataAccessEvents(context); |
| 192 | + communicator.sendBulkRequest(alsEvents); |
159 | 193 | } |
160 | 194 |
|
161 | 195 | /** |
@@ -221,21 +255,9 @@ private void addAttributeAccessEvents(UserInfo userInfo, ArrayNode eventArray, A |
221 | 255 | } |
222 | 256 | } |
223 | 257 |
|
224 | | - @On |
225 | | - public void handleConfigChangeEvent(ConfigChangeLogContext context) { |
226 | | - try { |
227 | | - ArrayNode alsEvents = createAlsConfigChangeEvents(context); |
228 | | - communicator.sendBulkRequest(alsEvents); |
229 | | - } catch (JsonParseException e) { |
230 | | - LOGGER.error("Audit Log write exception occurred for configuration change event", e); |
231 | | - throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_INVALID_MESSAGE, e); |
232 | | - } catch (ErrorStatusException e) { |
233 | | - LOGGER.error("Audit Log service not available for configuration change event", e); |
234 | | - throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_NOT_AVAILABLE, e); |
235 | | - } catch (Exception e) { |
236 | | - LOGGER.error("Unexpected exception while handling configuration change event", e); |
237 | | - throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_INVALID_MESSAGE, e); |
238 | | - } |
| 258 | + public void handleConfigChangeEvent(ConfigChangeLogContext context) throws JsonProcessingException { |
| 259 | + ArrayNode alsEvents = createAlsConfigChangeEvents(context); |
| 260 | + communicator.sendBulkRequest(alsEvents); |
239 | 261 | } |
240 | 262 |
|
241 | 263 | /** |
@@ -280,21 +302,9 @@ private ObjectNode buildConfigChangeEvent(UserInfo userInfo, ConfigChange config |
280 | 302 | return buildAlsEvent("configurationChange", userInfo, metadata, "configurationChange", changeNode); |
281 | 303 | } |
282 | 304 |
|
283 | | - @On |
284 | | - public void handleDataModificationEvent(DataModificationLogContext context) { |
285 | | - try { |
286 | | - ArrayNode alsEvents = createAlsDataModificationEvents(context); |
287 | | - communicator.sendBulkRequest(alsEvents); |
288 | | - } catch (JsonParseException e) { |
289 | | - LOGGER.error("Audit Log write exception occurred for data modification event", e); |
290 | | - throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_INVALID_MESSAGE, e); |
291 | | - } catch (ErrorStatusException e) { |
292 | | - LOGGER.error("Audit Log service not available for data modification event", e); |
293 | | - throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_NOT_AVAILABLE, e); |
294 | | - } catch (Exception e) { |
295 | | - LOGGER.error("Unexpected exception while handling data modification event", e); |
296 | | - throw new ErrorStatusException(CdsErrorStatuses.AUDITLOG_SERVICE_INVALID_MESSAGE, e); |
297 | | - } |
| 305 | + public void handleDataModificationEvent(DataModificationLogContext context) throws JsonProcessingException { |
| 306 | + ArrayNode alsEvents = createAlsDataModificationEvents(context); |
| 307 | + communicator.sendBulkRequest(alsEvents); |
298 | 308 | } |
299 | 309 |
|
300 | 310 | /** |
@@ -473,9 +483,8 @@ private ObjectNode buildDataAccessNode(Access access, String attribute, String a |
473 | 483 | */ |
474 | 484 | private void addValueDetails(ObjectNode node, ChangedAttribute attribute, String fieldName) { |
475 | 485 | String attributeName = requireNonNull(attribute.getName(), "ChangedAttribute.getName() is null"); |
476 | | - String newValue = requireNonNull(attribute.getNewValue(), "ChangedAttribute.getNewValue() is null"); |
477 | 486 | node.put(fieldName, attributeName); |
478 | | - node.put("newValue", newValue); |
| 487 | + node.put("newValue", attribute.getNewValue() != null ? attribute.getNewValue() : "null"); |
479 | 488 | node.put("oldValue", attribute.getOldValue() != null ? attribute.getOldValue() : "null"); |
480 | 489 | } |
481 | 490 |
|
|
0 commit comments