Wenyue Li created RANGER-5222: --------------------------------- Summary: The Kafka plugin throws a NoClassDefFoundError due to a missing log4j dependency. Key: RANGER-5222 URL: https://issues.apache.org/jira/browse/RANGER-5222 Project: Ranger Issue Type: Bug Components: audit Affects Versions: 2.1.0 Reporter: Wenyue Li
When I set {{xasecure.audit.destination.elasticsearch}} to {{true}} in the Kafka plugin configuration, if only one Elasticsearch node is online or Elasticsearch is not functioning properly, an exception is thrown during the initialization of the {{RestHighLevelClient}} class, resulting in a {{null}} return value,The code is as follows: {code:java} package org.apache.ranger.audit.destination; public class ElasticSearchAuditDestination extends AuditDestination { private RestHighLevelClient newClient() { try { if (StringUtils.isNotBlank(user) && StringUtils.isNotBlank(password) && password.contains("keytab") && new File(password).exists()) { subject = CredentialsProviderUtil.login(user, password); } RestClientBuilder restClientBuilder = getRestClientBuilder(hosts, protocol, user, password, port); RestHighLevelClient restHighLevelClient = new RestHighLevelClient(restClientBuilder); if (LOG.isDebugEnabled()) { LOG.debug("Initialized client"); } boolean exits = false; try { exits = restHighLevelClient.indices().open(new OpenIndexRequest(this.index), RequestOptions.DEFAULT).isShardsAcknowledged(); } catch (Exception e) { LOG.warn("Error validating index " + this.index); } if(exits) { if (LOG.isDebugEnabled()) { LOG.debug("Index exists"); } } else { LOG.info("Index does not exist"); } return restHighLevelClient; } catch (Throwable t) { lastLoggedAt.updateAndGet(lastLoggedAt -> { long now = System.currentTimeMillis(); long elapsed = now - lastLoggedAt; if (elapsed > TimeUnit.MINUTES.toMillis(1)) { LOG.fatal("Can't connect to ElasticSearch server: " + connectionString(), t); return now; } else { return lastLoggedAt; } }); return null; } } }{code} The root cause of the error is that when the Elasticsearch cluster is running with a single node, the parsed entity is not null, which leads to an exception during the parsing of the BytesRestResponse class because LogManager.getLogger cannot find the log4j dependency. As a result, the RestHighLevelClient is initialized each time an audit log is written, creating a large number of threads and causing thread leaks, eventually preventing the Kafka cluster from functioning properly,The code is as follows: {code:java} package org.elasticsearch.client; protected final ElasticsearchStatusException parseResponseException(ResponseException responseException) { Response response = responseException.getResponse(); HttpEntity entity = response.getEntity(); ElasticsearchStatusException elasticsearchException; RestStatus restStatus = RestStatus.fromCode(response.getStatusLine().getStatusCode()); if (entity == null) { elasticsearchException = new ElasticsearchStatusException( responseException.getMessage(), restStatus, responseException); } else { try { elasticsearchException = parseEntity(entity, BytesRestResponse::errorFromXContent); elasticsearchException.addSuppressed(responseException); } catch (Exception e) { elasticsearchException = new ElasticsearchStatusException("Unable to parse response body", restStatus, responseException); elasticsearchException.addSuppressed(e); } } return elasticsearchException; } {code} {code:java} package org.elasticsearch.rest; private static final Logger SUPPRESSED_ERROR_LOGGER = LogManager.getLogger("rest.suppressed"); {code} Full error attached: {code:java} FATAL Can't connect to ElasticSearch server: User:elastic, http://xxx,xxx,xxx:9201/ranger_audits (org.apache.ranger.audit.destination.ElasticSearchAuditDestination) java.lang.NoClassDefFoundError: org/apache/logging/log4j/LogManager at org.elasticsearch.rest.BytesRestResponse.<clinit>(BytesRestResponse.java:120) at org.elasticsearch.client.RestHighLevelClient.parseEntity(RestHighLevelClient.java:1793) at org.elasticsearch.client.RestHighLevelClient.parseResponseException(RestHighLevelClient.java:1770) at org.elasticsearch.client.RestHighLevelClient.internalPerformRequest(RestHighLevelClient.java:1527) at org.elasticsearch.client.RestHighLevelClient.performRequest(RestHighLevelClient.java:1484) at org.elasticsearch.client.RestHighLevelClient.performRequestAndParseEntity(RestHighLevelClient.java:1454) at org.elasticsearch.client.IndicesClient.open(IndicesClient.java:467) at org.apache.ranger.audit.destination.ElasticSearchAuditDestination.newClient(ElasticSearchAuditDestination.java:253) at org.apache.ranger.audit.destination.ElasticSearchAuditDestination.getClient(ElasticSearchAuditDestination.java:184) at org.apache.ranger.audit.destination.ElasticSearchAuditDestination.init(ElasticSearchAuditDestination.java:98) at org.apache.ranger.audit.provider.AuditProviderFactory.init(AuditProviderFactory.java:181) at org.apache.ranger.plugin.service.RangerBasePlugin.init(RangerBasePlugin.java:175) at org.apache.ranger.authorization.kafka.authorizer.RangerKafkaAuthorizer.configure(RangerKafkaAuthorizer.java:118) at org.apache.ranger.authorization.kafka.authorizer.RangerKafkaAuthorizer.configure(RangerKafkaAuthorizer.java:94) at kafka.security.authorizer.AuthorizerWrapper.configure(AuthorizerWrapper.scala:40) at kafka.server.KafkaServer.$anonfun$startup$4(KafkaServer.scala:297) at kafka.server.KafkaServer.$anonfun$startup$4$adapted(KafkaServer.scala:297) at scala.Option.foreach(Option.scala:437) at kafka.server.KafkaServer.startup(KafkaServer.scala:297) at kafka.server.KafkaServerStartable.startup(KafkaServerStartable.scala:44) at kafka.Kafka$.main(Kafka.scala:84) at kafka.Kafka.main(Kafka.scala) Caused by: java.lang.ClassNotFoundException: org.apache.logging.log4j.LogManager at java.lang.ClassLoader.findClass(ClassLoader.java:530) at org.apache.ranger.plugin.classloader.RangerPluginClassLoader$MyClassLoader.findClass(RangerPluginClassLoader.java:290) at java.lang.ClassLoader.loadClass(ClassLoader.java:424) at java.lang.ClassLoader.loadClass(ClassLoader.java:357) at org.apache.ranger.plugin.classloader.RangerPluginClassLoader.loadClass(RangerPluginClassLoader.java:132) ... 22 more {code} -- This message was sent by Atlassian Jira (v8.20.10#820010)