From e4ba9fe27ba9047238ecfaff58b55b885ebe5261 Mon Sep 17 00:00:00 2001 From: Albert Zaharovits Date: Fri, 15 Nov 2019 08:44:09 -0500 Subject: [PATCH] Audit log filter and marker (#49145) This adds a log marker and a marker filter for the audit log. Closes #47251 --- .../audit/logfile/LoggingAuditTrail.java | 61 ++++++++++++------- .../audit/logfile/LoggingAuditTrailTests.java | 2 +- 2 files changed, 40 insertions(+), 23 deletions(-) diff --git a/x-pack/plugin/security/src/main/java/org/elasticsearch/xpack/security/audit/logfile/LoggingAuditTrail.java b/x-pack/plugin/security/src/main/java/org/elasticsearch/xpack/security/audit/logfile/LoggingAuditTrail.java index b7ccdeac68624..fc49e36419c98 100644 --- a/x-pack/plugin/security/src/main/java/org/elasticsearch/xpack/security/audit/logfile/LoggingAuditTrail.java +++ b/x-pack/plugin/security/src/main/java/org/elasticsearch/xpack/security/audit/logfile/LoggingAuditTrail.java @@ -6,6 +6,11 @@ package org.elasticsearch.xpack.security.audit.logfile; import org.apache.logging.log4j.Logger; +import org.apache.logging.log4j.Marker; +import org.apache.logging.log4j.MarkerManager; +import org.apache.logging.log4j.core.Filter.Result; +import org.apache.logging.log4j.core.LoggerContext; +import org.apache.logging.log4j.core.filter.MarkerFilter; import org.apache.logging.log4j.message.StringMapMessage; import org.elasticsearch.action.IndicesRequest; import org.elasticsearch.cluster.ClusterChangedEvent; @@ -15,6 +20,7 @@ import org.elasticsearch.common.Nullable; import org.elasticsearch.common.Strings; import org.elasticsearch.common.collect.MapBuilder; +import org.elasticsearch.common.logging.Loggers; import org.elasticsearch.common.network.NetworkAddress; import org.elasticsearch.common.settings.Setting; import org.elasticsearch.common.settings.Setting.Property; @@ -32,6 +38,7 @@ import org.elasticsearch.xpack.core.security.user.SystemUser; import org.elasticsearch.xpack.core.security.user.User; import org.elasticsearch.xpack.core.security.user.XPackUser; +import org.elasticsearch.xpack.security.Security; import org.elasticsearch.xpack.security.audit.AuditLevel; import org.elasticsearch.xpack.security.audit.AuditTrail; import org.elasticsearch.xpack.core.security.authz.AuthorizationEngine.AuthorizationInfo; @@ -151,6 +158,8 @@ public class LoggingAuditTrail implements AuditTrail, ClusterStateListener { "indices", (key) -> Setting.listSetting(key, Collections.singletonList("*"), Function.identity(), Property.NodeScope, Property.Dynamic)); + private static final Marker AUDIT_MARKER = MarkerManager.getMarker("org.elasticsearch.xpack.security.audit"); + private final Logger logger; private final ThreadContext threadContext; final EventFilterPolicyRegistry eventFilterPolicyRegistry; @@ -166,7 +175,7 @@ public String name() { } public LoggingAuditTrail(Settings settings, ClusterService clusterService, ThreadPool threadPool) { - this(settings, clusterService, LogManager.getLogger(), threadPool.getThreadContext()); + this(settings, clusterService, LogManager.getLogger(LoggingAuditTrail.class), threadPool.getThreadContext()); } LoggingAuditTrail(Settings settings, ClusterService clusterService, Logger logger, ThreadContext threadContext) { @@ -207,6 +216,14 @@ public LoggingAuditTrail(Settings settings, ClusterService clusterService, Threa final EventFilterPolicy newPolicy = policy.orElse(new EventFilterPolicy(policyName, settings)).changeIndicesFilter(filtersList); this.eventFilterPolicyRegistry.set(policyName, newPolicy); }, (policyName, filtersList) -> EventFilterPolicy.parsePredicate(filtersList)); + // this log filter ensures that audit events are not filtered out because of the log level + final LoggerContext ctx = LoggerContext.getContext(false); + MarkerFilter auditMarkerFilter = MarkerFilter.createFilter(AUDIT_MARKER.getName(), Result.ACCEPT, Result.NEUTRAL); + ctx.addFilter(auditMarkerFilter); + ctx.updateLoggers(); + clusterService.getClusterSettings().addSettingsUpdateConsumer(ignored -> { + LogManager.getLogger(Security.class).warn("Changing log level for [" + LoggingAuditTrail.class.getName() + "] has no effect"); + }, Collections.singletonList(Loggers.LOG_LEVEL_SETTING.getConcreteSettingForNamespace(LoggingAuditTrail.class.getName()))); } @Override @@ -225,7 +242,7 @@ public void authenticationSuccess(String requestId, String realm, User user, Res .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } @@ -248,7 +265,7 @@ public void authenticationSuccess(String requestId, String realm, User user, Str .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -270,7 +287,7 @@ public void anonymousAccessDenied(String requestId, String action, TransportMess .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -289,7 +306,7 @@ public void anonymousAccessDenied(String requestId, RestRequest request) { .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } @@ -311,7 +328,7 @@ public void authenticationFailed(String requestId, AuthenticationToken token, St .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -329,7 +346,7 @@ public void authenticationFailed(String requestId, RestRequest request) { .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } @@ -350,7 +367,7 @@ public void authenticationFailed(String requestId, String action, TransportMessa .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -370,7 +387,7 @@ public void authenticationFailed(String requestId, AuthenticationToken token, Re .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } @@ -393,7 +410,7 @@ public void authenticationFailed(String requestId, String realm, AuthenticationT .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -414,7 +431,7 @@ public void authenticationFailed(String requestId, String realm, AuthenticationT .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } @@ -440,7 +457,7 @@ public void accessGranted(String requestId, Authentication authentication, Strin .withXForwardedFor(threadContext) .with(authorizationInfo.asMap()) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -480,7 +497,7 @@ public void explicitIndexAccessEvent(String requestId, AuditLevel eventType, Aut .with(ORIGIN_TYPE_FIELD_NAME, TRANSPORT_ORIGIN_FIELD_VALUE) .with(ORIGIN_ADDRESS_FIELD_NAME, NetworkAddress.format(remoteAddress.address())); } - logger.info(logEntryBuilder.build()); + logger.info(AUDIT_MARKER, logEntryBuilder.build()); } } } @@ -505,7 +522,7 @@ public void accessDenied(String requestId, Authentication authentication, String .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -523,7 +540,7 @@ public void tamperedRequest(String requestId, RestRequest request) { .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } @@ -544,7 +561,7 @@ public void tamperedRequest(String requestId, String action, TransportMessage me .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -567,7 +584,7 @@ public void tamperedRequest(String requestId, User user, String action, Transpor .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -586,7 +603,7 @@ public void connectionGranted(InetAddress inetAddress, String profile, SecurityI .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } @@ -604,7 +621,7 @@ public void connectionDenied(InetAddress inetAddress, String profile, SecurityIp .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } @@ -628,7 +645,7 @@ public void runAsGranted(String requestId, Authentication authentication, String .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -653,7 +670,7 @@ public void runAsDenied(String requestId, Authentication authentication, String .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } } @@ -675,7 +692,7 @@ public void runAsDenied(String requestId, Authentication authentication, RestReq .withOpaqueId(threadContext) .withXForwardedFor(threadContext) .build(); - logger.info(logEntry); + logger.info(AUDIT_MARKER, logEntry); } } diff --git a/x-pack/plugin/security/src/test/java/org/elasticsearch/xpack/security/audit/logfile/LoggingAuditTrailTests.java b/x-pack/plugin/security/src/test/java/org/elasticsearch/xpack/security/audit/logfile/LoggingAuditTrailTests.java index fa383ab03fc07..0eed26860bb64 100644 --- a/x-pack/plugin/security/src/test/java/org/elasticsearch/xpack/security/audit/logfile/LoggingAuditTrailTests.java +++ b/x-pack/plugin/security/src/test/java/org/elasticsearch/xpack/security/audit/logfile/LoggingAuditTrailTests.java @@ -198,7 +198,7 @@ public void init() throws Exception { threadContext.putHeader(AuditTrail.X_FORWARDED_FOR_HEADER, randomFrom("2001:db8:85a3:8d3:1319:8a2e:370:7348", "203.0.113.195", "203.0.113.195, 70.41.3.18, 150.172.238.178")); } - logger = CapturingLogger.newCapturingLogger(Level.INFO, patternLayout); + logger = CapturingLogger.newCapturingLogger(randomFrom(Level.OFF, Level.FATAL, Level.ERROR, Level.WARN, Level.INFO), patternLayout); auditTrail = new LoggingAuditTrail(settings, clusterService, logger, threadContext); }