From fe79c38ccb37ad35c40ab63a0ded443b6ffa03b9 Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Thu, 9 Apr 2026 22:16:59 +0800 Subject: [PATCH 01/10] Add Elasticsearch Java client plugin for 7.x-9.x Add plugin for co.elastic.clients:elasticsearch-java, the modern Elasticsearch Java client that replaces the deprecated REST High Level Client. Covers both 7.x (RestClientTransport.performRequest) and 8.x/9.x (ElasticsearchTransportBase.performRequest) code paths using witness classes for version detection. Tested versions: 7.17.22, 8.5.3, 8.12.2, 8.17.0, 9.0.0. Local verification passed for 8.17.0. --- .github/workflows/plugins-test.2.yaml | 1 + CHANGES.md | 1 + .../elasticsearch-java-plugin/pom.xml | 48 ++++++ ...ticsearchTransportBaseInstrumentation.java | 81 ++++++++++ .../RestClientTransportInstrumentation.java | 97 ++++++++++++ ...ClientTransportConstructorInterceptor.java | 43 ++++++ .../TransportPerformRequestInterceptor.java | 73 +++++++++ .../src/main/resources/skywalking-plugin.def | 19 +++ apm-sniffer/apm-sdk-plugin/pom.xml | 1 + .../service-agent/java-agent/Plugin-list.md | 1 + .../java-agent/Supported-list.md | 1 + .../bin/startup.sh | 21 +++ .../config/expectedData.yaml | 113 ++++++++++++++ .../configuration.yml | 34 +++++ .../elasticsearch-java-scenario/pom.xml | 138 ++++++++++++++++++ .../src/main/assembly/assembly.xml | 41 ++++++ .../testcase/elasticsearch/Application.java | 29 ++++ .../controller/CaseController.java | 96 ++++++++++++ .../src/main/resources/application.yaml | 21 +++ .../src/main/resources/log4j2.xml | 30 ++++ .../support-version.list | 25 ++++ 21 files changed, 914 insertions(+) create mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/pom.xml create mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/ElasticsearchTransportBaseInstrumentation.java create mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportInstrumentation.java create mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/RestClientTransportConstructorInterceptor.java create mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java create mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/bin/startup.sh create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/configuration.yml create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/pom.xml create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/src/main/assembly/assembly.xml create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/src/main/resources/application.yaml create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/src/main/resources/log4j2.xml create mode 100644 test/plugin/scenarios/elasticsearch-java-scenario/support-version.list diff --git a/.github/workflows/plugins-test.2.yaml b/.github/workflows/plugins-test.2.yaml index 5fe28c244f..1bbf07ef31 100644 --- a/.github/workflows/plugins-test.2.yaml +++ b/.github/workflows/plugins-test.2.yaml @@ -97,6 +97,7 @@ jobs: - nacos-client-2.x-scenario - rocketmq-scenario - rocketmq-5-grpc-scenario + - elasticsearch-java-scenario steps: - uses: actions/checkout@v2 with: diff --git a/CHANGES.md b/CHANGES.md index ad1e3f6c51..237ce9ff0c 100644 --- a/CHANGES.md +++ b/CHANGES.md @@ -21,6 +21,7 @@ Release Notes. * Enhance test/plugin/run.sh to support extra Maven properties per version in support-version.list (format: version,key=value). * Add MariaDB 3.x plugin (all classes renamed in 3.x). * Extend Jedis 4.x plugin to support Jedis 5.x (fix witness method for 5.x compatibility). +* Add Elasticsearch Java client (co.elastic.clients:elasticsearch-java) plugin for 7.x-9.x. All issues and pull requests are [here](https://github.com/apache/skywalking/milestone/249?closed=1) diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/pom.xml b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/pom.xml new file mode 100644 index 0000000000..0126147e82 --- /dev/null +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/pom.xml @@ -0,0 +1,48 @@ + + + + + 4.0.0 + + + apm-sdk-plugin + org.apache.skywalking + 9.7.0-SNAPSHOT + + + apm-elasticsearch-java-plugin + jar + + elasticsearch-java-plugin + + + 8.17.0 + + + + + co.elastic.clients + elasticsearch-java + ${elasticsearch-java.version} + provided + + + diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/ElasticsearchTransportBaseInstrumentation.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/ElasticsearchTransportBaseInstrumentation.java new file mode 100644 index 0000000000..6ac75f023c --- /dev/null +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/ElasticsearchTransportBaseInstrumentation.java @@ -0,0 +1,81 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.plugin.elasticsearch.java.define; + +import net.bytebuddy.description.method.MethodDescription; +import net.bytebuddy.matcher.ElementMatcher; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.ConstructorInterceptPoint; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.InstanceMethodsInterceptPoint; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.ClassInstanceMethodsEnhancePluginDefine; +import org.apache.skywalking.apm.agent.core.plugin.match.ClassMatch; + +import static net.bytebuddy.matcher.ElementMatchers.named; +import static org.apache.skywalking.apm.agent.core.plugin.match.NameMatch.byName; + +/** + * Enhance {@code co.elastic.clients.transport.ElasticsearchTransportBase} + * which exists in elasticsearch-java 8.x+. The performRequest method + * moved from RestClientTransport to this base class in 8.x. + *

+ * The peer is propagated from RestClientTransport (subclass) via dynamic field. + */ +public class ElasticsearchTransportBaseInstrumentation extends ClassInstanceMethodsEnhancePluginDefine { + + private static final String ENHANCE_CLASS = "co.elastic.clients.transport.ElasticsearchTransportBase"; + + private static final String PERFORM_REQUEST_INTERCEPTOR = + "org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor.TransportPerformRequestInterceptor"; + + @Override + protected String[] witnessClasses() { + return new String[] {ENHANCE_CLASS}; + } + + @Override + protected ClassMatch enhanceClass() { + return byName(ENHANCE_CLASS); + } + + @Override + public ConstructorInterceptPoint[] getConstructorsInterceptPoints() { + return new ConstructorInterceptPoint[0]; + } + + @Override + public InstanceMethodsInterceptPoint[] getInstanceMethodsInterceptPoints() { + return new InstanceMethodsInterceptPoint[] { + new InstanceMethodsInterceptPoint() { + @Override + public ElementMatcher getMethodsMatcher() { + return named("performRequest"); + } + + @Override + public String getMethodsInterceptor() { + return PERFORM_REQUEST_INTERCEPTOR; + } + + @Override + public boolean isOverrideArgs() { + return false; + } + } + }; + } +} diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportInstrumentation.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportInstrumentation.java new file mode 100644 index 0000000000..e5dacab15f --- /dev/null +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportInstrumentation.java @@ -0,0 +1,97 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.plugin.elasticsearch.java.define; + +import net.bytebuddy.description.method.MethodDescription; +import net.bytebuddy.matcher.ElementMatcher; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.ConstructorInterceptPoint; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.InstanceMethodsInterceptPoint; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.ClassInstanceMethodsEnhancePluginDefine; +import org.apache.skywalking.apm.agent.core.plugin.match.ClassMatch; + +import static net.bytebuddy.matcher.ElementMatchers.named; +import static org.apache.skywalking.apm.agent.core.plugin.bytebuddy.ArgumentTypeNameMatch.takesArgumentWithType; +import static org.apache.skywalking.apm.agent.core.plugin.match.NameMatch.byName; + +/** + * Enhance {@code co.elastic.clients.transport.rest_client.RestClientTransport} + * for the Elasticsearch Java client (co.elastic.clients:elasticsearch-java). + *

+ * Covers both 7.x (performRequest on RestClientTransport) and 8.x+ + * (performRequest inherited from ElasticsearchTransportBase, but constructor on RestClientTransport). + */ +public class RestClientTransportInstrumentation extends ClassInstanceMethodsEnhancePluginDefine { + + private static final String ENHANCE_CLASS = "co.elastic.clients.transport.rest_client.RestClientTransport"; + + private static final String CONSTRUCTOR_INTERCEPTOR = + "org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor.RestClientTransportConstructorInterceptor"; + + private static final String PERFORM_REQUEST_INTERCEPTOR = + "org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor.TransportPerformRequestInterceptor"; + + @Override + protected String[] witnessClasses() { + return new String[] {ENHANCE_CLASS}; + } + + @Override + protected ClassMatch enhanceClass() { + return byName(ENHANCE_CLASS); + } + + @Override + public ConstructorInterceptPoint[] getConstructorsInterceptPoints() { + return new ConstructorInterceptPoint[] { + new ConstructorInterceptPoint() { + @Override + public ElementMatcher getConstructorMatcher() { + return takesArgumentWithType(0, "org.elasticsearch.client.RestClient"); + } + + @Override + public String getConstructorInterceptor() { + return CONSTRUCTOR_INTERCEPTOR; + } + } + }; + } + + @Override + public InstanceMethodsInterceptPoint[] getInstanceMethodsInterceptPoints() { + return new InstanceMethodsInterceptPoint[] { + new InstanceMethodsInterceptPoint() { + @Override + public ElementMatcher getMethodsMatcher() { + return named("performRequest"); + } + + @Override + public String getMethodsInterceptor() { + return PERFORM_REQUEST_INTERCEPTOR; + } + + @Override + public boolean isOverrideArgs() { + return false; + } + } + }; + } +} diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/RestClientTransportConstructorInterceptor.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/RestClientTransportConstructorInterceptor.java new file mode 100644 index 0000000000..e96932ace3 --- /dev/null +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/RestClientTransportConstructorInterceptor.java @@ -0,0 +1,43 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor; + +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceConstructorInterceptor; +import org.elasticsearch.client.Node; +import org.elasticsearch.client.RestClient; + +import java.util.List; +import java.util.stream.Collectors; + +/** + * Intercept RestClientTransport constructor to extract peer address from RestClient nodes. + */ +public class RestClientTransportConstructorInterceptor implements InstanceConstructorInterceptor { + + @Override + public void onConstruct(EnhancedInstance objInst, Object[] allArguments) { + RestClient restClient = (RestClient) allArguments[0]; + List nodes = restClient.getNodes(); + String peers = nodes.stream() + .map(node -> node.getHost().toHostString()) + .collect(Collectors.joining(",")); + objInst.setSkyWalkingDynamicField(peers); + } +} diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java new file mode 100644 index 0000000000..aadf7ed9ca --- /dev/null +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java @@ -0,0 +1,73 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor; + +import co.elastic.clients.transport.Endpoint; +import org.apache.skywalking.apm.agent.core.context.ContextManager; +import org.apache.skywalking.apm.agent.core.context.tag.Tags; +import org.apache.skywalking.apm.agent.core.context.trace.AbstractSpan; +import org.apache.skywalking.apm.agent.core.context.trace.SpanLayer; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult; +import org.apache.skywalking.apm.network.trace.component.ComponentsDefine; + +import java.lang.reflect.Method; + +/** + * Intercept ElasticsearchTransport.performRequest() to create exit spans. + *

+ * Args: [0] request, [1] endpoint (Endpoint), [2] options (TransportOptions) + * The endpoint.id() provides the operation name (e.g., "search", "index", "bulk"). + */ +public class TransportPerformRequestInterceptor implements InstanceMethodsAroundInterceptor { + + private static final String DB_TYPE = "Elasticsearch"; + + @Override + public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, + Class[] argumentsTypes, MethodInterceptResult result) throws Throwable { + Endpoint endpoint = (Endpoint) allArguments[1]; + String operationName = "Elasticsearch/" + endpoint.id(); + + String peers = (String) objInst.getSkyWalkingDynamicField(); + if (peers == null || peers.isEmpty()) { + peers = "Unknown"; + } + + AbstractSpan span = ContextManager.createExitSpan(operationName, peers); + span.setComponent(ComponentsDefine.REST_HIGH_LEVEL_CLIENT); + Tags.DB_TYPE.set(span, DB_TYPE); + SpanLayer.asDB(span); + } + + @Override + public Object afterMethod(EnhancedInstance objInst, Method method, Object[] allArguments, + Class[] argumentsTypes, Object ret) throws Throwable { + ContextManager.stopSpan(); + return ret; + } + + @Override + public void handleMethodException(EnhancedInstance objInst, Method method, Object[] allArguments, + Class[] argumentsTypes, Throwable t) { + ContextManager.activeSpan().log(t); + ContextManager.activeSpan().errorOccurred(); + } +} diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def new file mode 100644 index 0000000000..6b564b22eb --- /dev/null +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def @@ -0,0 +1,19 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# Elasticsearch Java client (co.elastic.clients:elasticsearch-java) 7.x-9.x +elasticsearch-java=org.apache.skywalking.apm.plugin.elasticsearch.java.define.RestClientTransportInstrumentation +elasticsearch-java=org.apache.skywalking.apm.plugin.elasticsearch.java.define.ElasticsearchTransportBaseInstrumentation diff --git a/apm-sniffer/apm-sdk-plugin/pom.xml b/apm-sniffer/apm-sdk-plugin/pom.xml index 775ec34e12..5d09bd0957 100644 --- a/apm-sniffer/apm-sdk-plugin/pom.xml +++ b/apm-sniffer/apm-sdk-plugin/pom.xml @@ -71,6 +71,7 @@ elasticsearch-5.x-plugin elasticsearch-6.x-plugin elasticsearch-7.x-plugin + elasticsearch-java-plugin undertow-plugins rabbitmq-plugin dubbo-conflict-patch diff --git a/docs/en/setup/service-agent/java-agent/Plugin-list.md b/docs/en/setup/service-agent/java-agent/Plugin-list.md index 2bfd58f872..ed16dc1f85 100644 --- a/docs/en/setup/service-agent/java-agent/Plugin-list.md +++ b/docs/en/setup/service-agent/java-agent/Plugin-list.md @@ -25,6 +25,7 @@ - elasticsearch-5.x - elasticsearch-6.x - elasticsearch-7.x +- elasticsearch-java - fastjson-1.2.x - feign-default-http-9.x - feign-pathvar-9.x diff --git a/docs/en/setup/service-agent/java-agent/Supported-list.md b/docs/en/setup/service-agent/java-agent/Supported-list.md index 772f169c39..ca6f481f06 100644 --- a/docs/en/setup/service-agent/java-agent/Supported-list.md +++ b/docs/en/setup/service-agent/java-agent/Supported-list.md @@ -101,6 +101,7 @@ metrics based on the tracing data. * [transport-client](https://github.com/elastic/elasticsearch/tree/7.0/client/transport) 7.0.0-7.5.2 * [rest-high-level-client](https://www.elastic.co/guide/en/elasticsearch/client/java-rest/6.7/index.html) 6.7.1-6.8.4 * [rest-high-level-client](https://www.elastic.co/guide/en/elasticsearch/client/java-rest/7.0/java-rest-high.html) 7.x + * [elasticsearch-java](https://www.elastic.co/guide/en/elasticsearch/client/java-api-client/current/index.html) 7.17.x-9.x * [Solr](https://github.com/apache/solr/) * [SolrJ](https://github.com/apache/solr/tree/main/solr/solrj) 7.x * [Cassandra](https://github.com/apache/cassandra) 3.x diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/bin/startup.sh b/test/plugin/scenarios/elasticsearch-java-scenario/bin/startup.sh new file mode 100644 index 0000000000..eb5ce9db9e --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/bin/startup.sh @@ -0,0 +1,21 @@ +#!/bin/bash +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +home="$(cd "$(dirname $0)"; pwd)" + +java -jar ${agent_opts} -Dskywalking.plugin.elasticsearch.trace_dsl=true ${home}/../libs/elasticsearch-java-scenario.jar & diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml new file mode 100644 index 0000000000..0dfcc9e205 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml @@ -0,0 +1,113 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +segmentItems: +- serviceName: elasticsearch-java-scenario + segmentSize: ge 2 + segments: + - segmentId: not null + spans: + - operationName: Elasticsearch/es/indices.create + parentSpanId: 0 + spanId: 1 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/index + parentSpanId: 0 + spanId: 2 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/get + parentSpanId: 0 + spanId: 3 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/search + parentSpanId: 0 + spanId: 4 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/delete + parentSpanId: 0 + spanId: 5 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/indices.delete + parentSpanId: 0 + spanId: 6 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: GET:/elasticsearch-java-case/case/elasticsearch + parentSpanId: -1 + spanId: 0 + startTime: nq 0 + endTime: nq 0 + spanLayer: Http + isError: false + spanType: Entry + componentId: 1 + tags: + - {key: url, value: not null} + - {key: http.method, value: GET} + - {key: http.status_code, value: '200'} + skipAnalysis: 'false' diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/configuration.yml b/test/plugin/scenarios/elasticsearch-java-scenario/configuration.yml new file mode 100644 index 0000000000..a6b201e828 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/configuration.yml @@ -0,0 +1,34 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +type: jvm +entryService: http://localhost:8080/elasticsearch-java-case/case/elasticsearch +healthCheck: http://localhost:8080/elasticsearch-java-case/case/healthCheck +startScript: ./bin/startup.sh +environment: +- elasticsearch.server=elasticsearch-server:9200 +dependencies: + elasticsearch-server: + image: docker.elastic.co/elasticsearch/elasticsearch:8.17.0 + hostname: elasticsearch-server + removeOnExit: true + expose: + - 9200 + environment: + - cluster.name=docker-node + - xpack.security.enabled=false + - "ES_JAVA_OPTS=-Xms512m -Xmx512m" + - discovery.type=single-node diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/pom.xml b/test/plugin/scenarios/elasticsearch-java-scenario/pom.xml new file mode 100644 index 0000000000..275b963cd2 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/pom.xml @@ -0,0 +1,138 @@ + + + + + org.apache.skywalking.apm.testcase + elasticsearch-java-scenario + 1.0.0 + jar + + 4.0.0 + + + UTF-8 + 1.8 + 3.8.1 + + 8.12.0 + + 2.1.6.RELEASE + + + skywalking-elasticsearch-java-scenario + + + + + org.springframework.boot + spring-boot-dependencies + ${spring.boot.version} + pom + import + + + + + + + org.springframework.boot + spring-boot-starter-web + + + org.springframework.boot + spring-boot-starter-logging + + + + + org.springframework.boot + spring-boot-starter-log4j2 + + + jul-to-slf4j + org.slf4j + + + + + + co.elastic.clients + elasticsearch-java + ${test.framework.version} + + + + org.elasticsearch.client + elasticsearch-rest-client + ${test.framework.version} + + + com.fasterxml.jackson.core + jackson-databind + + + + + elasticsearch-java-scenario + + + org.springframework.boot + spring-boot-maven-plugin + ${spring.boot.version} + + + + repackage + + + + + + maven-compiler-plugin + ${maven-compiler-plugin.version} + + ${compiler.version} + ${compiler.version} + ${project.build.sourceEncoding} + + + + org.apache.maven.plugins + maven-assembly-plugin + + + assemble + package + + single + + + + src/main/assembly/assembly.xml + + ./target/ + + + + + + + diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/src/main/assembly/assembly.xml b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/assembly/assembly.xml new file mode 100644 index 0000000000..20d778c34c --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/assembly/assembly.xml @@ -0,0 +1,41 @@ + + + + + zip + + + + + ./bin + 0775 + + + + + + ${project.build.directory}/elasticsearch-java-scenario.jar + ./libs + 0775 + + + diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java new file mode 100644 index 0000000000..2cf2b3e563 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java @@ -0,0 +1,29 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.testcase.elasticsearch; + +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +@SpringBootApplication +public class Application { + public static void main(String[] args) { + SpringApplication.run(Application.class, args); + } +} diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java new file mode 100644 index 0000000000..3f2be16239 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java @@ -0,0 +1,96 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.testcase.elasticsearch.controller; + +import co.elastic.clients.elasticsearch.ElasticsearchClient; +import co.elastic.clients.elasticsearch.core.IndexResponse; +import co.elastic.clients.elasticsearch.core.GetResponse; +import co.elastic.clients.elasticsearch.core.SearchResponse; +import co.elastic.clients.elasticsearch.core.DeleteResponse; +import co.elastic.clients.elasticsearch.indices.CreateIndexResponse; +import co.elastic.clients.elasticsearch.indices.DeleteIndexResponse; +import co.elastic.clients.json.jackson.JacksonJsonpMapper; +import co.elastic.clients.transport.rest_client.RestClientTransport; +import org.apache.http.HttpHost; +import org.elasticsearch.client.RestClient; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +import java.io.IOException; +import java.util.HashMap; +import java.util.Map; + +@RestController +@RequestMapping("/elasticsearch-java-case/case") +public class CaseController { + + @Value("${elasticsearch.server}") + private String elasticsearchServer; + + @GetMapping("/healthCheck") + public String healthCheck() throws IOException { + RestClient restClient = RestClient.builder(HttpHost.create(elasticsearchServer)).build(); + RestClientTransport transport = new RestClientTransport(restClient, new JacksonJsonpMapper()); + ElasticsearchClient client = new ElasticsearchClient(transport); + try { + client.info(); + return "Success"; + } finally { + restClient.close(); + } + } + + @GetMapping("/elasticsearch") + public String elasticsearch() throws IOException { + RestClient restClient = RestClient.builder(HttpHost.create(elasticsearchServer)).build(); + RestClientTransport transport = new RestClientTransport(restClient, new JacksonJsonpMapper()); + ElasticsearchClient client = new ElasticsearchClient(transport); + try { + + // Create index + CreateIndexResponse createResp = client.indices().create(c -> c.index("test-index")); + + // Index document + Map doc = new HashMap<>(); + doc.put("name", "test"); + doc.put("value", "skywalking"); + IndexResponse indexResp = client.index(i -> i.index("test-index").id("1").document(doc)); + + // Get document + GetResponse getResp = client.get(g -> g.index("test-index").id("1"), Map.class); + + // Search + SearchResponse searchResp = client.search(s -> s + .index("test-index") + .query(q -> q.match(m -> m.field("name").query("test"))), Map.class); + + // Delete document + DeleteResponse deleteResp = client.delete(d -> d.index("test-index").id("1")); + + // Delete index + DeleteIndexResponse deleteIndexResp = client.indices().delete(d -> d.index("test-index")); + + return "Success"; + } finally { + restClient.close(); + } + } +} diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/src/main/resources/application.yaml b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/resources/application.yaml new file mode 100644 index 0000000000..ba18cc1c03 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/resources/application.yaml @@ -0,0 +1,21 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +# +server: + port: 8080 +logging: + config: classpath:log4j2.xml \ No newline at end of file diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/src/main/resources/log4j2.xml b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/resources/log4j2.xml new file mode 100644 index 0000000000..9849ed5a8a --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/resources/log4j2.xml @@ -0,0 +1,30 @@ + + + + + + + + + + + + + + \ No newline at end of file diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list new file mode 100644 index 0000000000..d2d5621211 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list @@ -0,0 +1,25 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# co.elastic.clients:elasticsearch-java +# ES server fixed at 8.17.0 (backward compatible with 7.x/8.x/9.x clients) +# 7.x: RestClientTransport.performRequest directly +# 8.x/9.x: ElasticsearchTransportBase.performRequest +7.17.22 +8.5.3 +8.12.2 +8.17.0 +9.0.0 From d1c9bc7bade2f6fa2e17fe7627495201a3057859 Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Thu, 9 Apr 2026 23:08:42 +0800 Subject: [PATCH 02/10] Split elasticsearch-java 9.x test to JDK 17 scenario elasticsearch-java 9.0.0 is compiled for JDK 17 (class version 61), so it cannot be tested in the JDK 8 test container. Split into a separate elasticsearch-java-9.x-scenario using Spring Boot 3.x and JDK 17 compiler target, added to plugins-jdk17-test.1.yaml. --- .github/workflows/plugins-jdk17-test.1.yaml | 1 + .../bin/startup.sh | 21 +++ .../config/expectedData.yaml | 113 ++++++++++++++ .../configuration.yml | 34 +++++ .../elasticsearch-java-9.x-scenario/pom.xml | 138 ++++++++++++++++++ .../src/main/assembly/assembly.xml | 41 ++++++ .../testcase/elasticsearch/Application.java | 29 ++++ .../controller/CaseController.java | 96 ++++++++++++ .../src/main/resources/application.yaml | 21 +++ .../src/main/resources/log4j2.xml | 30 ++++ .../support-version.list | 19 +++ .../support-version.list | 1 - 12 files changed, 543 insertions(+), 1 deletion(-) create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/bin/startup.sh create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/configuration.yml create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/pom.xml create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/assembly/assembly.xml create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/resources/application.yaml create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/resources/log4j2.xml create mode 100644 test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list diff --git a/.github/workflows/plugins-jdk17-test.1.yaml b/.github/workflows/plugins-jdk17-test.1.yaml index 939393713b..ed6efcfef4 100644 --- a/.github/workflows/plugins-jdk17-test.1.yaml +++ b/.github/workflows/plugins-jdk17-test.1.yaml @@ -81,6 +81,7 @@ jobs: - spring-scheduled-6.x-scenario - caffeine-3.x-scenario - lettuce-webflux-6x-scenario + - elasticsearch-java-9.x-scenario steps: - uses: actions/checkout@v2 with: diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/bin/startup.sh b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/bin/startup.sh new file mode 100644 index 0000000000..e054a8dc76 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/bin/startup.sh @@ -0,0 +1,21 @@ +#!/bin/bash +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +home="$(cd "$(dirname $0)"; pwd)" + +java -jar ${agent_opts} -Dskywalking.plugin.elasticsearch.trace_dsl=true ${home}/../libs/elasticsearch-java-9.x-scenario.jar & diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml new file mode 100644 index 0000000000..7c19a02e6e --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml @@ -0,0 +1,113 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +segmentItems: +- serviceName: elasticsearch-java-9.x-scenario + segmentSize: ge 2 + segments: + - segmentId: not null + spans: + - operationName: Elasticsearch/es/indices.create + parentSpanId: 0 + spanId: 1 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/index + parentSpanId: 0 + spanId: 2 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/get + parentSpanId: 0 + spanId: 3 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/search + parentSpanId: 0 + spanId: 4 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/delete + parentSpanId: 0 + spanId: 5 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/es/indices.delete + parentSpanId: 0 + spanId: 6 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: GET:/elasticsearch-java-case/case/elasticsearch + parentSpanId: -1 + spanId: 0 + startTime: nq 0 + endTime: nq 0 + spanLayer: Http + isError: false + spanType: Entry + componentId: 1 + tags: + - {key: url, value: not null} + - {key: http.method, value: GET} + - {key: http.status_code, value: '200'} + skipAnalysis: 'false' diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/configuration.yml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/configuration.yml new file mode 100644 index 0000000000..a6b201e828 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/configuration.yml @@ -0,0 +1,34 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +type: jvm +entryService: http://localhost:8080/elasticsearch-java-case/case/elasticsearch +healthCheck: http://localhost:8080/elasticsearch-java-case/case/healthCheck +startScript: ./bin/startup.sh +environment: +- elasticsearch.server=elasticsearch-server:9200 +dependencies: + elasticsearch-server: + image: docker.elastic.co/elasticsearch/elasticsearch:8.17.0 + hostname: elasticsearch-server + removeOnExit: true + expose: + - 9200 + environment: + - cluster.name=docker-node + - xpack.security.enabled=false + - "ES_JAVA_OPTS=-Xms512m -Xmx512m" + - discovery.type=single-node diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/pom.xml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/pom.xml new file mode 100644 index 0000000000..8ca30a4aa0 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/pom.xml @@ -0,0 +1,138 @@ + + + + + org.apache.skywalking.apm.testcase + elasticsearch-java-9.x-scenario + 1.0.0 + jar + + 4.0.0 + + + UTF-8 + 17 + 3.8.1 + + 9.0.0 + + 3.0.13 + + + skywalking-elasticsearch-java-9.x-scenario + + + + + org.springframework.boot + spring-boot-dependencies + ${spring.boot.version} + pom + import + + + + + + + org.springframework.boot + spring-boot-starter-web + + + org.springframework.boot + spring-boot-starter-logging + + + + + org.springframework.boot + spring-boot-starter-log4j2 + + + jul-to-slf4j + org.slf4j + + + + + + co.elastic.clients + elasticsearch-java + ${test.framework.version} + + + + org.elasticsearch.client + elasticsearch-rest-client + ${test.framework.version} + + + com.fasterxml.jackson.core + jackson-databind + + + + + elasticsearch-java-9.x-scenario + + + org.springframework.boot + spring-boot-maven-plugin + ${spring.boot.version} + + + + repackage + + + + + + maven-compiler-plugin + ${maven-compiler-plugin.version} + + ${compiler.version} + ${compiler.version} + ${project.build.sourceEncoding} + + + + org.apache.maven.plugins + maven-assembly-plugin + + + assemble + package + + single + + + + src/main/assembly/assembly.xml + + ./target/ + + + + + + + diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/assembly/assembly.xml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/assembly/assembly.xml new file mode 100644 index 0000000000..20d778c34c --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/assembly/assembly.xml @@ -0,0 +1,41 @@ + + + + + zip + + + + + ./bin + 0775 + + + + + + ${project.build.directory}/elasticsearch-java-scenario.jar + ./libs + 0775 + + + diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java new file mode 100644 index 0000000000..2cf2b3e563 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java @@ -0,0 +1,29 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.testcase.elasticsearch; + +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +@SpringBootApplication +public class Application { + public static void main(String[] args) { + SpringApplication.run(Application.class, args); + } +} diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java new file mode 100644 index 0000000000..3f2be16239 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java @@ -0,0 +1,96 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.testcase.elasticsearch.controller; + +import co.elastic.clients.elasticsearch.ElasticsearchClient; +import co.elastic.clients.elasticsearch.core.IndexResponse; +import co.elastic.clients.elasticsearch.core.GetResponse; +import co.elastic.clients.elasticsearch.core.SearchResponse; +import co.elastic.clients.elasticsearch.core.DeleteResponse; +import co.elastic.clients.elasticsearch.indices.CreateIndexResponse; +import co.elastic.clients.elasticsearch.indices.DeleteIndexResponse; +import co.elastic.clients.json.jackson.JacksonJsonpMapper; +import co.elastic.clients.transport.rest_client.RestClientTransport; +import org.apache.http.HttpHost; +import org.elasticsearch.client.RestClient; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +import java.io.IOException; +import java.util.HashMap; +import java.util.Map; + +@RestController +@RequestMapping("/elasticsearch-java-case/case") +public class CaseController { + + @Value("${elasticsearch.server}") + private String elasticsearchServer; + + @GetMapping("/healthCheck") + public String healthCheck() throws IOException { + RestClient restClient = RestClient.builder(HttpHost.create(elasticsearchServer)).build(); + RestClientTransport transport = new RestClientTransport(restClient, new JacksonJsonpMapper()); + ElasticsearchClient client = new ElasticsearchClient(transport); + try { + client.info(); + return "Success"; + } finally { + restClient.close(); + } + } + + @GetMapping("/elasticsearch") + public String elasticsearch() throws IOException { + RestClient restClient = RestClient.builder(HttpHost.create(elasticsearchServer)).build(); + RestClientTransport transport = new RestClientTransport(restClient, new JacksonJsonpMapper()); + ElasticsearchClient client = new ElasticsearchClient(transport); + try { + + // Create index + CreateIndexResponse createResp = client.indices().create(c -> c.index("test-index")); + + // Index document + Map doc = new HashMap<>(); + doc.put("name", "test"); + doc.put("value", "skywalking"); + IndexResponse indexResp = client.index(i -> i.index("test-index").id("1").document(doc)); + + // Get document + GetResponse getResp = client.get(g -> g.index("test-index").id("1"), Map.class); + + // Search + SearchResponse searchResp = client.search(s -> s + .index("test-index") + .query(q -> q.match(m -> m.field("name").query("test"))), Map.class); + + // Delete document + DeleteResponse deleteResp = client.delete(d -> d.index("test-index").id("1")); + + // Delete index + DeleteIndexResponse deleteIndexResp = client.indices().delete(d -> d.index("test-index")); + + return "Success"; + } finally { + restClient.close(); + } + } +} diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/resources/application.yaml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/resources/application.yaml new file mode 100644 index 0000000000..ba18cc1c03 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/resources/application.yaml @@ -0,0 +1,21 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +# +server: + port: 8080 +logging: + config: classpath:log4j2.xml \ No newline at end of file diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/resources/log4j2.xml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/resources/log4j2.xml new file mode 100644 index 0000000000..9849ed5a8a --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/resources/log4j2.xml @@ -0,0 +1,30 @@ + + + + + + + + + + + + + + \ No newline at end of file diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list new file mode 100644 index 0000000000..0cee0b38be --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list @@ -0,0 +1,19 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# co.elastic.clients:elasticsearch-java 9.x (requires JDK 17) +# 9.x: ElasticsearchTransportBase.performRequest +9.0.0 diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list index d2d5621211..a6cb986f27 100644 --- a/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list +++ b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list @@ -22,4 +22,3 @@ 8.5.3 8.12.2 8.17.0 -9.0.0 From 5182014c0611767509b04150d3ccc1951f8620ef Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Fri, 10 Apr 2026 00:04:00 +0800 Subject: [PATCH 03/10] Fix elasticsearch-java-9.x-scenario assembly and CI config Fix jar name in assembly.xml, correct support-version.list, and add to plugins-jdk17-test.1.yaml instead of replacing the JDK 8 scenario entry. --- .github/workflows/plugins-jdk17-test.1.yaml | 2 +- .../src/main/assembly/assembly.xml | 2 +- .../elasticsearch-java-9.x-scenario/support-version.list | 1 - 3 files changed, 2 insertions(+), 3 deletions(-) diff --git a/.github/workflows/plugins-jdk17-test.1.yaml b/.github/workflows/plugins-jdk17-test.1.yaml index ed6efcfef4..7367ed88a5 100644 --- a/.github/workflows/plugins-jdk17-test.1.yaml +++ b/.github/workflows/plugins-jdk17-test.1.yaml @@ -81,7 +81,7 @@ jobs: - spring-scheduled-6.x-scenario - caffeine-3.x-scenario - lettuce-webflux-6x-scenario - - elasticsearch-java-9.x-scenario + - elasticsearch-java-scenario steps: - uses: actions/checkout@v2 with: diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/assembly/assembly.xml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/assembly/assembly.xml index 20d778c34c..42a1323949 100644 --- a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/assembly/assembly.xml +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/assembly/assembly.xml @@ -33,7 +33,7 @@ - ${project.build.directory}/elasticsearch-java-scenario.jar + ${project.build.directory}/elasticsearch-java-9.x-scenario.jar ./libs 0775 diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list index 0cee0b38be..4d24a00891 100644 --- a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list @@ -15,5 +15,4 @@ # limitations under the License. # co.elastic.clients:elasticsearch-java 9.x (requires JDK 17) -# 9.x: ElasticsearchTransportBase.performRequest 9.0.0 From 5012790d5d08b1a3959f202d3502ebc294a8b087 Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Fri, 10 Apr 2026 00:21:23 +0800 Subject: [PATCH 04/10] Fix elasticsearch-java-9.x-scenario: use ES 9.0.0 server, exclude autoconfig - Use ES 9.0.0 server image instead of 8.17.0 for the 9.x scenario - Exclude ElasticsearchClientAutoConfiguration to avoid Spring Boot auto-config conflict with ES Java client constructor changes - Verified locally: 9.0.0 passed --- .../elasticsearch-java-9.x-scenario/configuration.yml | 2 +- .../skywalking/apm/testcase/elasticsearch/Application.java | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/configuration.yml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/configuration.yml index a6b201e828..f660224a0f 100644 --- a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/configuration.yml +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/configuration.yml @@ -22,7 +22,7 @@ environment: - elasticsearch.server=elasticsearch-server:9200 dependencies: elasticsearch-server: - image: docker.elastic.co/elasticsearch/elasticsearch:8.17.0 + image: docker.elastic.co/elasticsearch/elasticsearch:9.0.0 hostname: elasticsearch-server removeOnExit: true expose: diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java index 2cf2b3e563..3ce49f987a 100644 --- a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java @@ -20,8 +20,9 @@ import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.boot.autoconfigure.elasticsearch.ElasticsearchClientAutoConfiguration; -@SpringBootApplication +@SpringBootApplication(exclude = ElasticsearchClientAutoConfiguration.class) public class Application { public static void main(String[] args) { SpringApplication.run(Application.class, args); From 63257dade064b1fbb80233d83a139703172cf9e3 Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Fri, 10 Apr 2026 09:06:29 +0800 Subject: [PATCH 05/10] Expand elasticsearch-java test coverage to all minor versions Cover every minor version per test policy: - 7.x: 7.15.2, 7.16.3, 7.17.29 (library started at 7.15) - 8.x: 8.0.1 through 8.19.14 (all 20 minors) - 9.x: 9.0.11, 9.1.12, 9.2.8, 9.3.4 --- .../support-version.list | 5 +++- .../support-version.list | 27 ++++++++++++++++--- 2 files changed, 27 insertions(+), 5 deletions(-) diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list index 4d24a00891..044fe4a0fa 100644 --- a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list @@ -15,4 +15,7 @@ # limitations under the License. # co.elastic.clients:elasticsearch-java 9.x (requires JDK 17) -9.0.0 +9.0.11 +9.1.12 +9.2.8 +9.3.4 diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list index a6cb986f27..2c7b07f965 100644 --- a/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list +++ b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list @@ -15,10 +15,29 @@ # limitations under the License. # co.elastic.clients:elasticsearch-java -# ES server fixed at 8.17.0 (backward compatible with 7.x/8.x/9.x clients) +# ES server fixed at 8.17.0 (backward compatible with 7.x/8.x clients) # 7.x: RestClientTransport.performRequest directly -# 8.x/9.x: ElasticsearchTransportBase.performRequest -7.17.22 +# 8.x: ElasticsearchTransportBase.performRequest +7.15.2 +7.16.3 +7.17.29 +8.0.1 +8.1.3 +8.2.3 +8.3.3 +8.4.3 8.5.3 +8.6.2 +8.7.1 +8.8.2 +8.9.2 +8.10.4 +8.11.4 8.12.2 -8.17.0 +8.13.4 +8.14.3 +8.15.5 +8.16.7 +8.17.11 +8.18.8 +8.19.14 From c020951b11e57c235e59358f16839fbb930948fa Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Fri, 10 Apr 2026 10:01:54 +0800 Subject: [PATCH 06/10] Add elasticsearch-java 7.15.x support and fix CI - Add RestClientTransportV1Instrumentation for 7.15.x where RestClientTransport is in co.elastic.clients.base.rest_client (moved to co.elastic.clients.transport.rest_client in 7.16+) - Add TransportPerformRequestV1Interceptor that derives operation names from request class names since Endpoint.id() doesn't exist in 7.15.x - Add separate elasticsearch-java-7.15.x-scenario test (JDK 8) - Remove 7.15.x from main scenario (incompatible imports) - Fix JDK17 workflow: run elasticsearch-java-9.x-scenario instead of duplicating the main scenario --- .github/workflows/plugins-jdk17-test.1.yaml | 2 +- .github/workflows/plugins-test.2.yaml | 1 + .../RestClientTransportV1Instrumentation.java | 96 ++++++++++++ .../TransportPerformRequestV1Interceptor.java | 98 +++++++++++++ .../src/main/resources/skywalking-plugin.def | 3 +- .../bin/startup.sh | 21 +++ .../config/expectedData.yaml | 113 ++++++++++++++ .../configuration.yml | 34 +++++ .../pom.xml | 138 ++++++++++++++++++ .../src/main/assembly/assembly.xml | 41 ++++++ .../testcase/elasticsearch/Application.java | 29 ++++ .../controller/CaseController.java | 96 ++++++++++++ .../src/main/resources/application.yaml | 21 +++ .../src/main/resources/log4j2.xml | 30 ++++ .../support-version.list | 21 +++ .../support-version.list | 3 +- 16 files changed, 743 insertions(+), 4 deletions(-) create mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportV1Instrumentation.java create mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/bin/startup.sh create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/configuration.yml create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/pom.xml create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/assembly/assembly.xml create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/application.yaml create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/log4j2.xml create mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/support-version.list diff --git a/.github/workflows/plugins-jdk17-test.1.yaml b/.github/workflows/plugins-jdk17-test.1.yaml index 7367ed88a5..ed6efcfef4 100644 --- a/.github/workflows/plugins-jdk17-test.1.yaml +++ b/.github/workflows/plugins-jdk17-test.1.yaml @@ -81,7 +81,7 @@ jobs: - spring-scheduled-6.x-scenario - caffeine-3.x-scenario - lettuce-webflux-6x-scenario - - elasticsearch-java-scenario + - elasticsearch-java-9.x-scenario steps: - uses: actions/checkout@v2 with: diff --git a/.github/workflows/plugins-test.2.yaml b/.github/workflows/plugins-test.2.yaml index 1bbf07ef31..367e547477 100644 --- a/.github/workflows/plugins-test.2.yaml +++ b/.github/workflows/plugins-test.2.yaml @@ -98,6 +98,7 @@ jobs: - rocketmq-scenario - rocketmq-5-grpc-scenario - elasticsearch-java-scenario + - elasticsearch-java-7.15.x-scenario steps: - uses: actions/checkout@v2 with: diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportV1Instrumentation.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportV1Instrumentation.java new file mode 100644 index 0000000000..4e942fa16c --- /dev/null +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportV1Instrumentation.java @@ -0,0 +1,96 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.plugin.elasticsearch.java.define; + +import net.bytebuddy.description.method.MethodDescription; +import net.bytebuddy.matcher.ElementMatcher; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.ConstructorInterceptPoint; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.InstanceMethodsInterceptPoint; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.ClassInstanceMethodsEnhancePluginDefine; +import org.apache.skywalking.apm.agent.core.plugin.match.ClassMatch; + +import static net.bytebuddy.matcher.ElementMatchers.named; +import static org.apache.skywalking.apm.agent.core.plugin.bytebuddy.ArgumentTypeNameMatch.takesArgumentWithType; +import static org.apache.skywalking.apm.agent.core.plugin.match.NameMatch.byName; + +/** + * Enhance {@code co.elastic.clients.base.rest_client.RestClientTransport} + * for elasticsearch-java 7.15.x where RestClientTransport was in the + * {@code co.elastic.clients.base.rest_client} package (moved to + * {@code co.elastic.clients.transport.rest_client} in 7.16.0+). + */ +public class RestClientTransportV1Instrumentation extends ClassInstanceMethodsEnhancePluginDefine { + + private static final String ENHANCE_CLASS = "co.elastic.clients.base.rest_client.RestClientTransport"; + + private static final String CONSTRUCTOR_INTERCEPTOR = + "org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor.RestClientTransportConstructorInterceptor"; + + private static final String PERFORM_REQUEST_INTERCEPTOR = + "org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor.TransportPerformRequestV1Interceptor"; + + @Override + protected String[] witnessClasses() { + return new String[] {ENHANCE_CLASS}; + } + + @Override + protected ClassMatch enhanceClass() { + return byName(ENHANCE_CLASS); + } + + @Override + public ConstructorInterceptPoint[] getConstructorsInterceptPoints() { + return new ConstructorInterceptPoint[] { + new ConstructorInterceptPoint() { + @Override + public ElementMatcher getConstructorMatcher() { + return takesArgumentWithType(0, "org.elasticsearch.client.RestClient"); + } + + @Override + public String getConstructorInterceptor() { + return CONSTRUCTOR_INTERCEPTOR; + } + } + }; + } + + @Override + public InstanceMethodsInterceptPoint[] getInstanceMethodsInterceptPoints() { + return new InstanceMethodsInterceptPoint[] { + new InstanceMethodsInterceptPoint() { + @Override + public ElementMatcher getMethodsMatcher() { + return named("performRequest"); + } + + @Override + public String getMethodsInterceptor() { + return PERFORM_REQUEST_INTERCEPTOR; + } + + @Override + public boolean isOverrideArgs() { + return false; + } + } + }; + } +} diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java new file mode 100644 index 0000000000..d27323c26e --- /dev/null +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java @@ -0,0 +1,98 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor; + +import org.apache.skywalking.apm.agent.core.context.ContextManager; +import org.apache.skywalking.apm.agent.core.context.tag.Tags; +import org.apache.skywalking.apm.agent.core.context.trace.AbstractSpan; +import org.apache.skywalking.apm.agent.core.context.trace.SpanLayer; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor; +import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult; +import org.apache.skywalking.apm.network.trace.component.ComponentsDefine; + +import java.lang.reflect.Method; + +/** + * Intercept {@code co.elastic.clients.base.rest_client.RestClientTransport.performRequest()} + * for elasticsearch-java 7.15.x. + *

+ * In 7.15.x, the Endpoint interface ({@code co.elastic.clients.base.Endpoint}) does not have + * an {@code id()} method, so the operation name is derived from the request class name. + * E.g., {@code IndexRequest} → {@code Elasticsearch/index}. + *

+ * Args: [0] request, [1] endpoint (co.elastic.clients.base.Endpoint) + */ +public class TransportPerformRequestV1Interceptor implements InstanceMethodsAroundInterceptor { + + private static final String DB_TYPE = "Elasticsearch"; + private static final String REQUEST_SUFFIX = "Request"; + + @Override + public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, + Class[] argumentsTypes, MethodInterceptResult result) throws Throwable { + Object request = allArguments[0]; + String operationName = "Elasticsearch/" + deriveOperationName(request); + + String peers = (String) objInst.getSkyWalkingDynamicField(); + if (peers == null || peers.isEmpty()) { + peers = "Unknown"; + } + + AbstractSpan span = ContextManager.createExitSpan(operationName, peers); + span.setComponent(ComponentsDefine.REST_HIGH_LEVEL_CLIENT); + Tags.DB_TYPE.set(span, DB_TYPE); + SpanLayer.asDB(span); + } + + @Override + public Object afterMethod(EnhancedInstance objInst, Method method, Object[] allArguments, + Class[] argumentsTypes, Object ret) throws Throwable { + ContextManager.stopSpan(); + return ret; + } + + @Override + public void handleMethodException(EnhancedInstance objInst, Method method, Object[] allArguments, + Class[] argumentsTypes, Throwable t) { + ContextManager.activeSpan().log(t); + ContextManager.activeSpan().errorOccurred(); + } + + /** + * Derive operation name from request class simple name. + * E.g., IndexRequest → index, SearchRequest → search, CreateIndexRequest → create_index + */ + private String deriveOperationName(Object request) { + String className = request.getClass().getSimpleName(); + if (className.endsWith(REQUEST_SUFFIX)) { + className = className.substring(0, className.length() - REQUEST_SUFFIX.length()); + } + // Convert PascalCase to snake_case + StringBuilder sb = new StringBuilder(); + for (int i = 0; i < className.length(); i++) { + char c = className.charAt(i); + if (Character.isUpperCase(c) && i > 0) { + sb.append('_'); + } + sb.append(Character.toLowerCase(c)); + } + return sb.toString(); + } +} diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def index 6b564b22eb..d084f44872 100644 --- a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def @@ -14,6 +14,7 @@ # See the License for the specific language governing permissions and # limitations under the License. -# Elasticsearch Java client (co.elastic.clients:elasticsearch-java) 7.x-9.x +# Elasticsearch Java client (co.elastic.clients:elasticsearch-java) 7.15.x-9.x +elasticsearch-java=org.apache.skywalking.apm.plugin.elasticsearch.java.define.RestClientTransportV1Instrumentation elasticsearch-java=org.apache.skywalking.apm.plugin.elasticsearch.java.define.RestClientTransportInstrumentation elasticsearch-java=org.apache.skywalking.apm.plugin.elasticsearch.java.define.ElasticsearchTransportBaseInstrumentation diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/bin/startup.sh b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/bin/startup.sh new file mode 100644 index 0000000000..e064be3c62 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/bin/startup.sh @@ -0,0 +1,21 @@ +#!/bin/bash +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +home="$(cd "$(dirname $0)"; pwd)" + +java -jar ${agent_opts} -Dskywalking.plugin.elasticsearch.trace_dsl=true ${home}/../libs/elasticsearch-java-7.15.x-scenario.jar & diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml new file mode 100644 index 0000000000..a059935df4 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml @@ -0,0 +1,113 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +segmentItems: +- serviceName: elasticsearch-java-7.15.x-scenario + segmentSize: ge 2 + segments: + - segmentId: not null + spans: + - operationName: Elasticsearch/create_index + parentSpanId: 0 + spanId: 1 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/index + parentSpanId: 0 + spanId: 2 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/get + parentSpanId: 0 + spanId: 3 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/search + parentSpanId: 0 + spanId: 4 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/delete + parentSpanId: 0 + spanId: 5 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: Elasticsearch/delete_index + parentSpanId: 0 + spanId: 6 + spanLayer: Database + startTime: nq 0 + endTime: nq 0 + componentId: 77 + isError: false + spanType: Exit + peer: not null + skipAnalysis: false + tags: + - {key: db.type, value: Elasticsearch} + - operationName: GET:/elasticsearch-java-case/case/elasticsearch + parentSpanId: -1 + spanId: 0 + startTime: nq 0 + endTime: nq 0 + spanLayer: Http + isError: false + spanType: Entry + componentId: 1 + tags: + - {key: url, value: not null} + - {key: http.method, value: GET} + - {key: http.status_code, value: '200'} + skipAnalysis: 'false' diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/configuration.yml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/configuration.yml new file mode 100644 index 0000000000..a239f57fdf --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/configuration.yml @@ -0,0 +1,34 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +type: jvm +entryService: http://localhost:8080/elasticsearch-java-case/case/elasticsearch +healthCheck: http://localhost:8080/elasticsearch-java-case/case/healthCheck +startScript: ./bin/startup.sh +environment: +- elasticsearch.server=elasticsearch-server:9200 +dependencies: + elasticsearch-server: + image: docker.elastic.co/elasticsearch/elasticsearch:7.17.0 + hostname: elasticsearch-server + removeOnExit: true + expose: + - 9200 + environment: + - cluster.name=docker-node + - xpack.security.enabled=false + - "ES_JAVA_OPTS=-Xms512m -Xmx512m" + - discovery.type=single-node diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/pom.xml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/pom.xml new file mode 100644 index 0000000000..0f291ce566 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/pom.xml @@ -0,0 +1,138 @@ + + + + + org.apache.skywalking.apm.testcase + elasticsearch-java-7.15.x-scenario + 1.0.0 + jar + + 4.0.0 + + + UTF-8 + 1.8 + 3.8.1 + + 7.15.2 + + 2.1.6.RELEASE + + + skywalking-elasticsearch-java-7.15.x-scenario + + + + + org.springframework.boot + spring-boot-dependencies + ${spring.boot.version} + pom + import + + + + + + + org.springframework.boot + spring-boot-starter-web + + + org.springframework.boot + spring-boot-starter-logging + + + + + org.springframework.boot + spring-boot-starter-log4j2 + + + jul-to-slf4j + org.slf4j + + + + + + co.elastic.clients + elasticsearch-java + ${test.framework.version} + + + + org.elasticsearch.client + elasticsearch-rest-client + ${test.framework.version} + + + com.fasterxml.jackson.core + jackson-databind + + + + + elasticsearch-java-7.15.x-scenario + + + org.springframework.boot + spring-boot-maven-plugin + ${spring.boot.version} + + + + repackage + + + + + + maven-compiler-plugin + ${maven-compiler-plugin.version} + + ${compiler.version} + ${compiler.version} + ${project.build.sourceEncoding} + + + + org.apache.maven.plugins + maven-assembly-plugin + + + assemble + package + + single + + + + src/main/assembly/assembly.xml + + ./target/ + + + + + + + diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/assembly/assembly.xml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/assembly/assembly.xml new file mode 100644 index 0000000000..41fa4c4206 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/assembly/assembly.xml @@ -0,0 +1,41 @@ + + + + + zip + + + + + ./bin + 0775 + + + + + + ${project.build.directory}/elasticsearch-java-7.15.x-scenario.jar + ./libs + 0775 + + + diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java new file mode 100644 index 0000000000..2cf2b3e563 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java @@ -0,0 +1,29 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.testcase.elasticsearch; + +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +@SpringBootApplication +public class Application { + public static void main(String[] args) { + SpringApplication.run(Application.class, args); + } +} diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java new file mode 100644 index 0000000000..8ef247ed7c --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java @@ -0,0 +1,96 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.testcase.elasticsearch.controller; + +import co.elastic.clients.elasticsearch.ElasticsearchClient; +import co.elastic.clients.elasticsearch.core.IndexResponse; +import co.elastic.clients.elasticsearch.core.GetResponse; +import co.elastic.clients.elasticsearch.core.SearchResponse; +import co.elastic.clients.elasticsearch.core.DeleteResponse; +import co.elastic.clients.elasticsearch.indices.CreateIndexResponse; +import co.elastic.clients.elasticsearch.indices.DeleteIndexResponse; +import co.elastic.clients.json.jackson.JacksonJsonpMapper; +import co.elastic.clients.base.rest_client.RestClientTransport; +import org.apache.http.HttpHost; +import org.elasticsearch.client.RestClient; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +import java.io.IOException; +import java.util.HashMap; +import java.util.Map; + +@RestController +@RequestMapping("/elasticsearch-java-case/case") +public class CaseController { + + @Value("${elasticsearch.server}") + private String elasticsearchServer; + + @GetMapping("/healthCheck") + public String healthCheck() throws IOException { + RestClient restClient = RestClient.builder(HttpHost.create(elasticsearchServer)).build(); + RestClientTransport transport = new RestClientTransport(restClient, new JacksonJsonpMapper()); + ElasticsearchClient client = new ElasticsearchClient(transport); + try { + client.info(); + return "Success"; + } finally { + restClient.close(); + } + } + + @GetMapping("/elasticsearch") + public String elasticsearch() throws IOException { + RestClient restClient = RestClient.builder(HttpHost.create(elasticsearchServer)).build(); + RestClientTransport transport = new RestClientTransport(restClient, new JacksonJsonpMapper()); + ElasticsearchClient client = new ElasticsearchClient(transport); + try { + + // Create index + CreateIndexResponse createResp = client.indices().create(c -> c.index("test-index")); + + // Index document + Map doc = new HashMap<>(); + doc.put("name", "test"); + doc.put("value", "skywalking"); + IndexResponse indexResp = client.index(i -> i.index("test-index").id("1").document(doc)); + + // Get document + GetResponse getResp = client.get(g -> g.index("test-index").id("1"), Map.class); + + // Search + SearchResponse searchResp = client.search(s -> s + .index("test-index") + .query(q -> q.match(m -> m.field("name").query("test"))), Map.class); + + // Delete document + DeleteResponse deleteResp = client.delete(d -> d.index("test-index").id("1")); + + // Delete index + DeleteIndexResponse deleteIndexResp = client.indices().delete(d -> d.index("test-index")); + + return "Success"; + } finally { + restClient.close(); + } + } +} diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/application.yaml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/application.yaml new file mode 100644 index 0000000000..ba18cc1c03 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/application.yaml @@ -0,0 +1,21 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +# +server: + port: 8080 +logging: + config: classpath:log4j2.xml \ No newline at end of file diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/log4j2.xml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/log4j2.xml new file mode 100644 index 0000000000..9849ed5a8a --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/log4j2.xml @@ -0,0 +1,30 @@ + + + + + + + + + + + + + + \ No newline at end of file diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/support-version.list new file mode 100644 index 0000000000..243dded2f8 --- /dev/null +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/support-version.list @@ -0,0 +1,21 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# co.elastic.clients:elasticsearch-java 7.15.x +# RestClientTransport in co.elastic.clients.base.rest_client (moved to transport package in 7.16) +7.15.0 +7.15.1 +7.15.2 diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list index 2c7b07f965..ba501af654 100644 --- a/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list +++ b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list @@ -16,9 +16,8 @@ # co.elastic.clients:elasticsearch-java # ES server fixed at 8.17.0 (backward compatible with 7.x/8.x clients) -# 7.x: RestClientTransport.performRequest directly +# 7.16+: co.elastic.clients.transport.rest_client.RestClientTransport # 8.x: ElasticsearchTransportBase.performRequest -7.15.2 7.16.3 7.17.29 8.0.1 From 5ee6f146ebd0ae637140cfc952ea17dba417c237 Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Fri, 10 Apr 2026 10:54:04 +0800 Subject: [PATCH 07/10] Fix test scenario compatibility issues - Use FieldValue.of() instead of query(String) for 7.x compatibility (query(String) shorthand only exists in 8.0+) - Fix 8.16/8.17 versions: use 8.16.6/8.17.10 to match available elasticsearch-rest-client versions - Fix 9.x versions: use 9.0.8/9.1.10/9.2.8/9.3.3 to match available elasticsearch-rest-client versions - All 29 versions verified locally against Maven Central --- .../elasticsearch-java-9.x-scenario/support-version.list | 7 ++++--- .../testcase/elasticsearch/controller/CaseController.java | 3 ++- .../elasticsearch-java-scenario/support-version.list | 4 ++-- 3 files changed, 8 insertions(+), 6 deletions(-) diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list index 044fe4a0fa..2f8cf94b33 100644 --- a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/support-version.list @@ -15,7 +15,8 @@ # limitations under the License. # co.elastic.clients:elasticsearch-java 9.x (requires JDK 17) -9.0.11 -9.1.12 +# Versions must match elasticsearch-rest-client available versions +9.0.8 +9.1.10 9.2.8 -9.3.4 +9.3.3 diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java index 3f2be16239..66180bfcd9 100644 --- a/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java +++ b/test/plugin/scenarios/elasticsearch-java-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java @@ -25,6 +25,7 @@ import co.elastic.clients.elasticsearch.core.DeleteResponse; import co.elastic.clients.elasticsearch.indices.CreateIndexResponse; import co.elastic.clients.elasticsearch.indices.DeleteIndexResponse; +import co.elastic.clients.elasticsearch._types.FieldValue; import co.elastic.clients.json.jackson.JacksonJsonpMapper; import co.elastic.clients.transport.rest_client.RestClientTransport; import org.apache.http.HttpHost; @@ -80,7 +81,7 @@ public String elasticsearch() throws IOException { // Search SearchResponse searchResp = client.search(s -> s .index("test-index") - .query(q -> q.match(m -> m.field("name").query("test"))), Map.class); + .query(q -> q.match(m -> m.field("name").query(FieldValue.of("test")))), Map.class); // Delete document DeleteResponse deleteResp = client.delete(d -> d.index("test-index").id("1")); diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list index ba501af654..114e16d1bf 100644 --- a/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list +++ b/test/plugin/scenarios/elasticsearch-java-scenario/support-version.list @@ -36,7 +36,7 @@ 8.13.4 8.14.3 8.15.5 -8.16.7 -8.17.11 +8.16.6 +8.17.10 8.18.8 8.19.14 From 5a7c89b91add8b3295f65bf44467492573988100 Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Fri, 10 Apr 2026 11:07:41 +0800 Subject: [PATCH 08/10] Add db.instance tag with index name to align with existing ES plugins - Extract index name from Endpoint.requestUrl() and set as db.instance tag - Aligns with existing elasticsearch-5.x/6.x/7.x plugins that capture db.type, db.instance, and db.statement tags - Update all three scenario expectedData.yaml files --- .../TransportPerformRequestInterceptor.java | 31 ++++++++++++++++++- .../TransportPerformRequestV1Interceptor.java | 16 ++++++++++ .../config/expectedData.yaml | 6 ++++ .../config/expectedData.yaml | 6 ++++ .../config/expectedData.yaml | 6 ++++ 5 files changed, 64 insertions(+), 1 deletion(-) diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java index aadf7ed9ca..a059e71d88 100644 --- a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java @@ -41,9 +41,10 @@ public class TransportPerformRequestInterceptor implements InstanceMethodsAround private static final String DB_TYPE = "Elasticsearch"; @Override + @SuppressWarnings("unchecked") public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class[] argumentsTypes, MethodInterceptResult result) throws Throwable { - Endpoint endpoint = (Endpoint) allArguments[1]; + Endpoint endpoint = (Endpoint) allArguments[1]; String operationName = "Elasticsearch/" + endpoint.id(); String peers = (String) objInst.getSkyWalkingDynamicField(); @@ -55,6 +56,12 @@ public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allAr span.setComponent(ComponentsDefine.REST_HIGH_LEVEL_CLIENT); Tags.DB_TYPE.set(span, DB_TYPE); SpanLayer.asDB(span); + + String requestUrl = endpoint.requestUrl(allArguments[0]); + String index = extractIndex(requestUrl); + if (index != null) { + span.tag(Tags.ofKey("db.instance"), index); + } } @Override @@ -70,4 +77,26 @@ public void handleMethodException(EnhancedInstance objInst, Method method, Objec ContextManager.activeSpan().log(t); ContextManager.activeSpan().errorOccurred(); } + + /** + * Extract index name from request URL. + * E.g., "/test-index/_doc/1" → "test-index", "/_bulk" → null + */ + static String extractIndex(String requestUrl) { + if (requestUrl == null || requestUrl.isEmpty()) { + return null; + } + // Remove leading slash + String path = requestUrl.startsWith("/") ? requestUrl.substring(1) : requestUrl; + if (path.isEmpty()) { + return null; + } + // First segment before '/' or '_' prefix means no index + int slashIdx = path.indexOf('/'); + String firstSegment = slashIdx > 0 ? path.substring(0, slashIdx) : path; + if (firstSegment.startsWith("_")) { + return null; + } + return firstSegment; + } } diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java index d27323c26e..668a462658 100644 --- a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java @@ -22,6 +22,8 @@ import org.apache.skywalking.apm.agent.core.context.tag.Tags; import org.apache.skywalking.apm.agent.core.context.trace.AbstractSpan; import org.apache.skywalking.apm.agent.core.context.trace.SpanLayer; +import org.apache.skywalking.apm.agent.core.logging.api.ILog; +import org.apache.skywalking.apm.agent.core.logging.api.LogManager; import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance; import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor; import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult; @@ -41,6 +43,7 @@ */ public class TransportPerformRequestV1Interceptor implements InstanceMethodsAroundInterceptor { + private static final ILog LOGGER = LogManager.getLogger(TransportPerformRequestV1Interceptor.class); private static final String DB_TYPE = "Elasticsearch"; private static final String REQUEST_SUFFIX = "Request"; @@ -48,6 +51,7 @@ public class TransportPerformRequestV1Interceptor implements InstanceMethodsArou public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class[] argumentsTypes, MethodInterceptResult result) throws Throwable { Object request = allArguments[0]; + Object endpoint = allArguments[1]; String operationName = "Elasticsearch/" + deriveOperationName(request); String peers = (String) objInst.getSkyWalkingDynamicField(); @@ -59,6 +63,18 @@ public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allAr span.setComponent(ComponentsDefine.REST_HIGH_LEVEL_CLIENT); Tags.DB_TYPE.set(span, DB_TYPE); SpanLayer.asDB(span); + + try { + Method requestUrlMethod = endpoint.getClass().getMethod("requestUrl", Object.class); + requestUrlMethod.setAccessible(true); + String requestUrl = (String) requestUrlMethod.invoke(endpoint, request); + String index = TransportPerformRequestInterceptor.extractIndex(requestUrl); + if (index != null) { + span.tag(Tags.ofKey("db.instance"), index); + } + } catch (Exception e) { + LOGGER.warn("Failed to extract index from request URL", e); + } } @Override diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml index a059935df4..854a80bdd8 100644 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml @@ -32,6 +32,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/index parentSpanId: 0 spanId: 2 @@ -45,6 +46,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/get parentSpanId: 0 spanId: 3 @@ -58,6 +60,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/search parentSpanId: 0 spanId: 4 @@ -71,6 +74,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/delete parentSpanId: 0 spanId: 5 @@ -84,6 +88,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/delete_index parentSpanId: 0 spanId: 6 @@ -97,6 +102,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: GET:/elasticsearch-java-case/case/elasticsearch parentSpanId: -1 spanId: 0 diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml index 7c19a02e6e..1a2c2dbdf3 100644 --- a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml @@ -32,6 +32,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/index parentSpanId: 0 spanId: 2 @@ -45,6 +46,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/get parentSpanId: 0 spanId: 3 @@ -58,6 +60,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/search parentSpanId: 0 spanId: 4 @@ -71,6 +74,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/delete parentSpanId: 0 spanId: 5 @@ -84,6 +88,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/indices.delete parentSpanId: 0 spanId: 6 @@ -97,6 +102,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: GET:/elasticsearch-java-case/case/elasticsearch parentSpanId: -1 spanId: 0 diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml index 0dfcc9e205..0dbd9df66b 100644 --- a/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml +++ b/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml @@ -32,6 +32,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/index parentSpanId: 0 spanId: 2 @@ -45,6 +46,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/get parentSpanId: 0 spanId: 3 @@ -58,6 +60,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/search parentSpanId: 0 spanId: 4 @@ -71,6 +74,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/delete parentSpanId: 0 spanId: 5 @@ -84,6 +88,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: Elasticsearch/es/indices.delete parentSpanId: 0 spanId: 6 @@ -97,6 +102,7 @@ segmentItems: skipAnalysis: false tags: - {key: db.type, value: Elasticsearch} + - {key: db.instance, value: test-index} - operationName: GET:/elasticsearch-java-case/case/elasticsearch parentSpanId: -1 spanId: 0 From b18199948d9b3a32ed6a0b1517b668500bfc343e Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Fri, 10 Apr 2026 11:22:48 +0800 Subject: [PATCH 09/10] Add db.statement tag with DSL tracing support - Add ElasticsearchPluginConfig with TRACE_DSL and ELASTICSEARCH_DSL_LENGTH_THRESHOLD (same config keys as existing elasticsearch plugins: plugin.elasticsearch.trace_dsl) - Capture request body via RequestBase.toString() which serializes to JSON, same approach as existing ES 6.x/7.x plugins - Guarded by TRACE_DSL config (default false), with length threshold - Update all three scenario expectedData.yaml files --- .../java/ElasticsearchPluginConfig.java | 35 +++++++++++++++++++ .../TransportPerformRequestInterceptor.java | 14 +++++++- .../TransportPerformRequestV1Interceptor.java | 11 ++++++ .../config/expectedData.yaml | 6 ++++ .../config/expectedData.yaml | 6 ++++ .../config/expectedData.yaml | 6 ++++ 6 files changed, 77 insertions(+), 1 deletion(-) create mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/ElasticsearchPluginConfig.java diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/ElasticsearchPluginConfig.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/ElasticsearchPluginConfig.java new file mode 100644 index 0000000000..c435f439a8 --- /dev/null +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/ElasticsearchPluginConfig.java @@ -0,0 +1,35 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +package org.apache.skywalking.apm.plugin.elasticsearch.java; + +import org.apache.skywalking.apm.agent.core.boot.PluginConfig; + +public class ElasticsearchPluginConfig { + public static class Plugin { + @PluginConfig(root = ElasticsearchPluginConfig.class) + public static class Elasticsearch { + /** + * If true, trace all the DSL(Domain Specific Language) in ElasticSearch access, default is false + */ + public static boolean TRACE_DSL = false; + + public static int ELASTICSEARCH_DSL_LENGTH_THRESHOLD = 1024; + } + } +} diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java index a059e71d88..ebf8ec6d41 100644 --- a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestInterceptor.java @@ -27,6 +27,7 @@ import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor; import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult; import org.apache.skywalking.apm.network.trace.component.ComponentsDefine; +import org.apache.skywalking.apm.plugin.elasticsearch.java.ElasticsearchPluginConfig; import java.lang.reflect.Method; @@ -57,11 +58,22 @@ public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allAr Tags.DB_TYPE.set(span, DB_TYPE); SpanLayer.asDB(span); - String requestUrl = endpoint.requestUrl(allArguments[0]); + Object request = allArguments[0]; + String requestUrl = endpoint.requestUrl(request); String index = extractIndex(requestUrl); if (index != null) { span.tag(Tags.ofKey("db.instance"), index); } + if (ElasticsearchPluginConfig.Plugin.Elasticsearch.TRACE_DSL) { + String dsl = request.toString(); + if (dsl != null && !dsl.isEmpty()) { + int maxLen = ElasticsearchPluginConfig.Plugin.Elasticsearch.ELASTICSEARCH_DSL_LENGTH_THRESHOLD; + if (maxLen > 0 && dsl.length() > maxLen) { + dsl = dsl.substring(0, maxLen) + "..."; + } + Tags.DB_STATEMENT.set(span, dsl); + } + } } @Override diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java index 668a462658..f8b28cd7a9 100644 --- a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java @@ -28,6 +28,7 @@ import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor; import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult; import org.apache.skywalking.apm.network.trace.component.ComponentsDefine; +import org.apache.skywalking.apm.plugin.elasticsearch.java.ElasticsearchPluginConfig; import java.lang.reflect.Method; @@ -75,6 +76,16 @@ public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allAr } catch (Exception e) { LOGGER.warn("Failed to extract index from request URL", e); } + if (ElasticsearchPluginConfig.Plugin.Elasticsearch.TRACE_DSL) { + String dsl = request.toString(); + if (dsl != null && !dsl.isEmpty()) { + int maxLen = ElasticsearchPluginConfig.Plugin.Elasticsearch.ELASTICSEARCH_DSL_LENGTH_THRESHOLD; + if (maxLen > 0 && dsl.length() > maxLen) { + dsl = dsl.substring(0, maxLen) + "..."; + } + Tags.DB_STATEMENT.set(span, dsl); + } + } } @Override diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml index 854a80bdd8..00a8488ec3 100644 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml +++ b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml @@ -33,6 +33,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/index parentSpanId: 0 spanId: 2 @@ -47,6 +48,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/get parentSpanId: 0 spanId: 3 @@ -61,6 +63,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/search parentSpanId: 0 spanId: 4 @@ -75,6 +78,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/delete parentSpanId: 0 spanId: 5 @@ -89,6 +93,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/delete_index parentSpanId: 0 spanId: 6 @@ -103,6 +108,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: GET:/elasticsearch-java-case/case/elasticsearch parentSpanId: -1 spanId: 0 diff --git a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml index 1a2c2dbdf3..b9af4b71cc 100644 --- a/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml +++ b/test/plugin/scenarios/elasticsearch-java-9.x-scenario/config/expectedData.yaml @@ -33,6 +33,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/index parentSpanId: 0 spanId: 2 @@ -47,6 +48,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/get parentSpanId: 0 spanId: 3 @@ -61,6 +63,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/search parentSpanId: 0 spanId: 4 @@ -75,6 +78,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/delete parentSpanId: 0 spanId: 5 @@ -89,6 +93,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/indices.delete parentSpanId: 0 spanId: 6 @@ -103,6 +108,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: GET:/elasticsearch-java-case/case/elasticsearch parentSpanId: -1 spanId: 0 diff --git a/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml index 0dbd9df66b..0d79dbce45 100644 --- a/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml +++ b/test/plugin/scenarios/elasticsearch-java-scenario/config/expectedData.yaml @@ -33,6 +33,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/index parentSpanId: 0 spanId: 2 @@ -47,6 +48,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/get parentSpanId: 0 spanId: 3 @@ -61,6 +63,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/search parentSpanId: 0 spanId: 4 @@ -75,6 +78,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/delete parentSpanId: 0 spanId: 5 @@ -89,6 +93,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: Elasticsearch/es/indices.delete parentSpanId: 0 spanId: 6 @@ -103,6 +108,7 @@ segmentItems: tags: - {key: db.type, value: Elasticsearch} - {key: db.instance, value: test-index} + - {key: db.statement, value: not null} - operationName: GET:/elasticsearch-java-case/case/elasticsearch parentSpanId: -1 spanId: 0 From 0290c949b59606ffb95931b713d528418989f688 Mon Sep 17 00:00:00 2001 From: Wu Sheng Date: Fri, 10 Apr 2026 11:41:33 +0800 Subject: [PATCH 10/10] Remove elasticsearch-java 7.15.x support 7.15.x (Sep 2021) had unstable API with different package structure (_core vs core, base.rest_client vs transport.rest_client). The API stabilized from 7.16.0+. Plugin now covers 7.16.x-9.x. All remaining versions verified locally. --- .github/workflows/plugins-test.2.yaml | 1 - .../RestClientTransportV1Instrumentation.java | 96 ------------ .../TransportPerformRequestV1Interceptor.java | 125 ---------------- .../src/main/resources/skywalking-plugin.def | 3 +- .../bin/startup.sh | 21 --- .../config/expectedData.yaml | 125 ---------------- .../configuration.yml | 34 ----- .../pom.xml | 138 ------------------ .../src/main/assembly/assembly.xml | 41 ------ .../testcase/elasticsearch/Application.java | 29 ---- .../controller/CaseController.java | 96 ------------ .../src/main/resources/application.yaml | 21 --- .../src/main/resources/log4j2.xml | 30 ---- .../support-version.list | 21 --- 14 files changed, 1 insertion(+), 780 deletions(-) delete mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportV1Instrumentation.java delete mode 100644 apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/bin/startup.sh delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/configuration.yml delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/pom.xml delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/assembly/assembly.xml delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/application.yaml delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/log4j2.xml delete mode 100644 test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/support-version.list diff --git a/.github/workflows/plugins-test.2.yaml b/.github/workflows/plugins-test.2.yaml index 367e547477..1bbf07ef31 100644 --- a/.github/workflows/plugins-test.2.yaml +++ b/.github/workflows/plugins-test.2.yaml @@ -98,7 +98,6 @@ jobs: - rocketmq-scenario - rocketmq-5-grpc-scenario - elasticsearch-java-scenario - - elasticsearch-java-7.15.x-scenario steps: - uses: actions/checkout@v2 with: diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportV1Instrumentation.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportV1Instrumentation.java deleted file mode 100644 index 4e942fa16c..0000000000 --- a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/define/RestClientTransportV1Instrumentation.java +++ /dev/null @@ -1,96 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - */ - -package org.apache.skywalking.apm.plugin.elasticsearch.java.define; - -import net.bytebuddy.description.method.MethodDescription; -import net.bytebuddy.matcher.ElementMatcher; -import org.apache.skywalking.apm.agent.core.plugin.interceptor.ConstructorInterceptPoint; -import org.apache.skywalking.apm.agent.core.plugin.interceptor.InstanceMethodsInterceptPoint; -import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.ClassInstanceMethodsEnhancePluginDefine; -import org.apache.skywalking.apm.agent.core.plugin.match.ClassMatch; - -import static net.bytebuddy.matcher.ElementMatchers.named; -import static org.apache.skywalking.apm.agent.core.plugin.bytebuddy.ArgumentTypeNameMatch.takesArgumentWithType; -import static org.apache.skywalking.apm.agent.core.plugin.match.NameMatch.byName; - -/** - * Enhance {@code co.elastic.clients.base.rest_client.RestClientTransport} - * for elasticsearch-java 7.15.x where RestClientTransport was in the - * {@code co.elastic.clients.base.rest_client} package (moved to - * {@code co.elastic.clients.transport.rest_client} in 7.16.0+). - */ -public class RestClientTransportV1Instrumentation extends ClassInstanceMethodsEnhancePluginDefine { - - private static final String ENHANCE_CLASS = "co.elastic.clients.base.rest_client.RestClientTransport"; - - private static final String CONSTRUCTOR_INTERCEPTOR = - "org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor.RestClientTransportConstructorInterceptor"; - - private static final String PERFORM_REQUEST_INTERCEPTOR = - "org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor.TransportPerformRequestV1Interceptor"; - - @Override - protected String[] witnessClasses() { - return new String[] {ENHANCE_CLASS}; - } - - @Override - protected ClassMatch enhanceClass() { - return byName(ENHANCE_CLASS); - } - - @Override - public ConstructorInterceptPoint[] getConstructorsInterceptPoints() { - return new ConstructorInterceptPoint[] { - new ConstructorInterceptPoint() { - @Override - public ElementMatcher getConstructorMatcher() { - return takesArgumentWithType(0, "org.elasticsearch.client.RestClient"); - } - - @Override - public String getConstructorInterceptor() { - return CONSTRUCTOR_INTERCEPTOR; - } - } - }; - } - - @Override - public InstanceMethodsInterceptPoint[] getInstanceMethodsInterceptPoints() { - return new InstanceMethodsInterceptPoint[] { - new InstanceMethodsInterceptPoint() { - @Override - public ElementMatcher getMethodsMatcher() { - return named("performRequest"); - } - - @Override - public String getMethodsInterceptor() { - return PERFORM_REQUEST_INTERCEPTOR; - } - - @Override - public boolean isOverrideArgs() { - return false; - } - } - }; - } -} diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java deleted file mode 100644 index f8b28cd7a9..0000000000 --- a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/java/org/apache/skywalking/apm/plugin/elasticsearch/java/interceptor/TransportPerformRequestV1Interceptor.java +++ /dev/null @@ -1,125 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - */ - -package org.apache.skywalking.apm.plugin.elasticsearch.java.interceptor; - -import org.apache.skywalking.apm.agent.core.context.ContextManager; -import org.apache.skywalking.apm.agent.core.context.tag.Tags; -import org.apache.skywalking.apm.agent.core.context.trace.AbstractSpan; -import org.apache.skywalking.apm.agent.core.context.trace.SpanLayer; -import org.apache.skywalking.apm.agent.core.logging.api.ILog; -import org.apache.skywalking.apm.agent.core.logging.api.LogManager; -import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance; -import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor; -import org.apache.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult; -import org.apache.skywalking.apm.network.trace.component.ComponentsDefine; -import org.apache.skywalking.apm.plugin.elasticsearch.java.ElasticsearchPluginConfig; - -import java.lang.reflect.Method; - -/** - * Intercept {@code co.elastic.clients.base.rest_client.RestClientTransport.performRequest()} - * for elasticsearch-java 7.15.x. - *

- * In 7.15.x, the Endpoint interface ({@code co.elastic.clients.base.Endpoint}) does not have - * an {@code id()} method, so the operation name is derived from the request class name. - * E.g., {@code IndexRequest} → {@code Elasticsearch/index}. - *

- * Args: [0] request, [1] endpoint (co.elastic.clients.base.Endpoint) - */ -public class TransportPerformRequestV1Interceptor implements InstanceMethodsAroundInterceptor { - - private static final ILog LOGGER = LogManager.getLogger(TransportPerformRequestV1Interceptor.class); - private static final String DB_TYPE = "Elasticsearch"; - private static final String REQUEST_SUFFIX = "Request"; - - @Override - public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, - Class[] argumentsTypes, MethodInterceptResult result) throws Throwable { - Object request = allArguments[0]; - Object endpoint = allArguments[1]; - String operationName = "Elasticsearch/" + deriveOperationName(request); - - String peers = (String) objInst.getSkyWalkingDynamicField(); - if (peers == null || peers.isEmpty()) { - peers = "Unknown"; - } - - AbstractSpan span = ContextManager.createExitSpan(operationName, peers); - span.setComponent(ComponentsDefine.REST_HIGH_LEVEL_CLIENT); - Tags.DB_TYPE.set(span, DB_TYPE); - SpanLayer.asDB(span); - - try { - Method requestUrlMethod = endpoint.getClass().getMethod("requestUrl", Object.class); - requestUrlMethod.setAccessible(true); - String requestUrl = (String) requestUrlMethod.invoke(endpoint, request); - String index = TransportPerformRequestInterceptor.extractIndex(requestUrl); - if (index != null) { - span.tag(Tags.ofKey("db.instance"), index); - } - } catch (Exception e) { - LOGGER.warn("Failed to extract index from request URL", e); - } - if (ElasticsearchPluginConfig.Plugin.Elasticsearch.TRACE_DSL) { - String dsl = request.toString(); - if (dsl != null && !dsl.isEmpty()) { - int maxLen = ElasticsearchPluginConfig.Plugin.Elasticsearch.ELASTICSEARCH_DSL_LENGTH_THRESHOLD; - if (maxLen > 0 && dsl.length() > maxLen) { - dsl = dsl.substring(0, maxLen) + "..."; - } - Tags.DB_STATEMENT.set(span, dsl); - } - } - } - - @Override - public Object afterMethod(EnhancedInstance objInst, Method method, Object[] allArguments, - Class[] argumentsTypes, Object ret) throws Throwable { - ContextManager.stopSpan(); - return ret; - } - - @Override - public void handleMethodException(EnhancedInstance objInst, Method method, Object[] allArguments, - Class[] argumentsTypes, Throwable t) { - ContextManager.activeSpan().log(t); - ContextManager.activeSpan().errorOccurred(); - } - - /** - * Derive operation name from request class simple name. - * E.g., IndexRequest → index, SearchRequest → search, CreateIndexRequest → create_index - */ - private String deriveOperationName(Object request) { - String className = request.getClass().getSimpleName(); - if (className.endsWith(REQUEST_SUFFIX)) { - className = className.substring(0, className.length() - REQUEST_SUFFIX.length()); - } - // Convert PascalCase to snake_case - StringBuilder sb = new StringBuilder(); - for (int i = 0; i < className.length(); i++) { - char c = className.charAt(i); - if (Character.isUpperCase(c) && i > 0) { - sb.append('_'); - } - sb.append(Character.toLowerCase(c)); - } - return sb.toString(); - } -} diff --git a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def index d084f44872..b13b674473 100644 --- a/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def +++ b/apm-sniffer/apm-sdk-plugin/elasticsearch-java-plugin/src/main/resources/skywalking-plugin.def @@ -14,7 +14,6 @@ # See the License for the specific language governing permissions and # limitations under the License. -# Elasticsearch Java client (co.elastic.clients:elasticsearch-java) 7.15.x-9.x -elasticsearch-java=org.apache.skywalking.apm.plugin.elasticsearch.java.define.RestClientTransportV1Instrumentation +# Elasticsearch Java client (co.elastic.clients:elasticsearch-java) 7.16.x-9.x elasticsearch-java=org.apache.skywalking.apm.plugin.elasticsearch.java.define.RestClientTransportInstrumentation elasticsearch-java=org.apache.skywalking.apm.plugin.elasticsearch.java.define.ElasticsearchTransportBaseInstrumentation diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/bin/startup.sh b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/bin/startup.sh deleted file mode 100644 index e064be3c62..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/bin/startup.sh +++ /dev/null @@ -1,21 +0,0 @@ -#!/bin/bash -# -# Licensed to the Apache Software Foundation (ASF) under one -# or more contributor license agreements. See the NOTICE file -# distributed with this work for additional information -# regarding copyright ownership. The ASF licenses this file -# to you under the Apache License, Version 2.0 (the -# "License"); you may not use this file except in compliance -# with the License. You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -home="$(cd "$(dirname $0)"; pwd)" - -java -jar ${agent_opts} -Dskywalking.plugin.elasticsearch.trace_dsl=true ${home}/../libs/elasticsearch-java-7.15.x-scenario.jar & diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml deleted file mode 100644 index 00a8488ec3..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/config/expectedData.yaml +++ /dev/null @@ -1,125 +0,0 @@ -# Licensed to the Apache Software Foundation (ASF) under one -# or more contributor license agreements. See the NOTICE file -# distributed with this work for additional information -# regarding copyright ownership. The ASF licenses this file -# to you under the Apache License, Version 2.0 (the -# "License"); you may not use this file except in compliance -# with the License. You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -segmentItems: -- serviceName: elasticsearch-java-7.15.x-scenario - segmentSize: ge 2 - segments: - - segmentId: not null - spans: - - operationName: Elasticsearch/create_index - parentSpanId: 0 - spanId: 1 - spanLayer: Database - startTime: nq 0 - endTime: nq 0 - componentId: 77 - isError: false - spanType: Exit - peer: not null - skipAnalysis: false - tags: - - {key: db.type, value: Elasticsearch} - - {key: db.instance, value: test-index} - - {key: db.statement, value: not null} - - operationName: Elasticsearch/index - parentSpanId: 0 - spanId: 2 - spanLayer: Database - startTime: nq 0 - endTime: nq 0 - componentId: 77 - isError: false - spanType: Exit - peer: not null - skipAnalysis: false - tags: - - {key: db.type, value: Elasticsearch} - - {key: db.instance, value: test-index} - - {key: db.statement, value: not null} - - operationName: Elasticsearch/get - parentSpanId: 0 - spanId: 3 - spanLayer: Database - startTime: nq 0 - endTime: nq 0 - componentId: 77 - isError: false - spanType: Exit - peer: not null - skipAnalysis: false - tags: - - {key: db.type, value: Elasticsearch} - - {key: db.instance, value: test-index} - - {key: db.statement, value: not null} - - operationName: Elasticsearch/search - parentSpanId: 0 - spanId: 4 - spanLayer: Database - startTime: nq 0 - endTime: nq 0 - componentId: 77 - isError: false - spanType: Exit - peer: not null - skipAnalysis: false - tags: - - {key: db.type, value: Elasticsearch} - - {key: db.instance, value: test-index} - - {key: db.statement, value: not null} - - operationName: Elasticsearch/delete - parentSpanId: 0 - spanId: 5 - spanLayer: Database - startTime: nq 0 - endTime: nq 0 - componentId: 77 - isError: false - spanType: Exit - peer: not null - skipAnalysis: false - tags: - - {key: db.type, value: Elasticsearch} - - {key: db.instance, value: test-index} - - {key: db.statement, value: not null} - - operationName: Elasticsearch/delete_index - parentSpanId: 0 - spanId: 6 - spanLayer: Database - startTime: nq 0 - endTime: nq 0 - componentId: 77 - isError: false - spanType: Exit - peer: not null - skipAnalysis: false - tags: - - {key: db.type, value: Elasticsearch} - - {key: db.instance, value: test-index} - - {key: db.statement, value: not null} - - operationName: GET:/elasticsearch-java-case/case/elasticsearch - parentSpanId: -1 - spanId: 0 - startTime: nq 0 - endTime: nq 0 - spanLayer: Http - isError: false - spanType: Entry - componentId: 1 - tags: - - {key: url, value: not null} - - {key: http.method, value: GET} - - {key: http.status_code, value: '200'} - skipAnalysis: 'false' diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/configuration.yml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/configuration.yml deleted file mode 100644 index a239f57fdf..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/configuration.yml +++ /dev/null @@ -1,34 +0,0 @@ -# Licensed to the Apache Software Foundation (ASF) under one -# or more contributor license agreements. See the NOTICE file -# distributed with this work for additional information -# regarding copyright ownership. The ASF licenses this file -# to you under the Apache License, Version 2.0 (the -# "License"); you may not use this file except in compliance -# with the License. You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -type: jvm -entryService: http://localhost:8080/elasticsearch-java-case/case/elasticsearch -healthCheck: http://localhost:8080/elasticsearch-java-case/case/healthCheck -startScript: ./bin/startup.sh -environment: -- elasticsearch.server=elasticsearch-server:9200 -dependencies: - elasticsearch-server: - image: docker.elastic.co/elasticsearch/elasticsearch:7.17.0 - hostname: elasticsearch-server - removeOnExit: true - expose: - - 9200 - environment: - - cluster.name=docker-node - - xpack.security.enabled=false - - "ES_JAVA_OPTS=-Xms512m -Xmx512m" - - discovery.type=single-node diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/pom.xml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/pom.xml deleted file mode 100644 index 0f291ce566..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/pom.xml +++ /dev/null @@ -1,138 +0,0 @@ - - - - - org.apache.skywalking.apm.testcase - elasticsearch-java-7.15.x-scenario - 1.0.0 - jar - - 4.0.0 - - - UTF-8 - 1.8 - 3.8.1 - - 7.15.2 - - 2.1.6.RELEASE - - - skywalking-elasticsearch-java-7.15.x-scenario - - - - - org.springframework.boot - spring-boot-dependencies - ${spring.boot.version} - pom - import - - - - - - - org.springframework.boot - spring-boot-starter-web - - - org.springframework.boot - spring-boot-starter-logging - - - - - org.springframework.boot - spring-boot-starter-log4j2 - - - jul-to-slf4j - org.slf4j - - - - - - co.elastic.clients - elasticsearch-java - ${test.framework.version} - - - - org.elasticsearch.client - elasticsearch-rest-client - ${test.framework.version} - - - com.fasterxml.jackson.core - jackson-databind - - - - - elasticsearch-java-7.15.x-scenario - - - org.springframework.boot - spring-boot-maven-plugin - ${spring.boot.version} - - - - repackage - - - - - - maven-compiler-plugin - ${maven-compiler-plugin.version} - - ${compiler.version} - ${compiler.version} - ${project.build.sourceEncoding} - - - - org.apache.maven.plugins - maven-assembly-plugin - - - assemble - package - - single - - - - src/main/assembly/assembly.xml - - ./target/ - - - - - - - diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/assembly/assembly.xml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/assembly/assembly.xml deleted file mode 100644 index 41fa4c4206..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/assembly/assembly.xml +++ /dev/null @@ -1,41 +0,0 @@ - - - - - zip - - - - - ./bin - 0775 - - - - - - ${project.build.directory}/elasticsearch-java-7.15.x-scenario.jar - ./libs - 0775 - - - diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java deleted file mode 100644 index 2cf2b3e563..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/Application.java +++ /dev/null @@ -1,29 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - */ - -package org.apache.skywalking.apm.testcase.elasticsearch; - -import org.springframework.boot.SpringApplication; -import org.springframework.boot.autoconfigure.SpringBootApplication; - -@SpringBootApplication -public class Application { - public static void main(String[] args) { - SpringApplication.run(Application.class, args); - } -} diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java deleted file mode 100644 index 8ef247ed7c..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/java/org/apache/skywalking/apm/testcase/elasticsearch/controller/CaseController.java +++ /dev/null @@ -1,96 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - * - */ - -package org.apache.skywalking.apm.testcase.elasticsearch.controller; - -import co.elastic.clients.elasticsearch.ElasticsearchClient; -import co.elastic.clients.elasticsearch.core.IndexResponse; -import co.elastic.clients.elasticsearch.core.GetResponse; -import co.elastic.clients.elasticsearch.core.SearchResponse; -import co.elastic.clients.elasticsearch.core.DeleteResponse; -import co.elastic.clients.elasticsearch.indices.CreateIndexResponse; -import co.elastic.clients.elasticsearch.indices.DeleteIndexResponse; -import co.elastic.clients.json.jackson.JacksonJsonpMapper; -import co.elastic.clients.base.rest_client.RestClientTransport; -import org.apache.http.HttpHost; -import org.elasticsearch.client.RestClient; -import org.springframework.beans.factory.annotation.Value; -import org.springframework.web.bind.annotation.GetMapping; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RestController; - -import java.io.IOException; -import java.util.HashMap; -import java.util.Map; - -@RestController -@RequestMapping("/elasticsearch-java-case/case") -public class CaseController { - - @Value("${elasticsearch.server}") - private String elasticsearchServer; - - @GetMapping("/healthCheck") - public String healthCheck() throws IOException { - RestClient restClient = RestClient.builder(HttpHost.create(elasticsearchServer)).build(); - RestClientTransport transport = new RestClientTransport(restClient, new JacksonJsonpMapper()); - ElasticsearchClient client = new ElasticsearchClient(transport); - try { - client.info(); - return "Success"; - } finally { - restClient.close(); - } - } - - @GetMapping("/elasticsearch") - public String elasticsearch() throws IOException { - RestClient restClient = RestClient.builder(HttpHost.create(elasticsearchServer)).build(); - RestClientTransport transport = new RestClientTransport(restClient, new JacksonJsonpMapper()); - ElasticsearchClient client = new ElasticsearchClient(transport); - try { - - // Create index - CreateIndexResponse createResp = client.indices().create(c -> c.index("test-index")); - - // Index document - Map doc = new HashMap<>(); - doc.put("name", "test"); - doc.put("value", "skywalking"); - IndexResponse indexResp = client.index(i -> i.index("test-index").id("1").document(doc)); - - // Get document - GetResponse getResp = client.get(g -> g.index("test-index").id("1"), Map.class); - - // Search - SearchResponse searchResp = client.search(s -> s - .index("test-index") - .query(q -> q.match(m -> m.field("name").query("test"))), Map.class); - - // Delete document - DeleteResponse deleteResp = client.delete(d -> d.index("test-index").id("1")); - - // Delete index - DeleteIndexResponse deleteIndexResp = client.indices().delete(d -> d.index("test-index")); - - return "Success"; - } finally { - restClient.close(); - } - } -} diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/application.yaml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/application.yaml deleted file mode 100644 index ba18cc1c03..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/application.yaml +++ /dev/null @@ -1,21 +0,0 @@ -# -# Licensed to the Apache Software Foundation (ASF) under one or more -# contributor license agreements. See the NOTICE file distributed with -# this work for additional information regarding copyright ownership. -# The ASF licenses this file to You under the Apache License, Version 2.0 -# (the "License"); you may not use this file except in compliance with -# the License. You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. -# -# -server: - port: 8080 -logging: - config: classpath:log4j2.xml \ No newline at end of file diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/log4j2.xml b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/log4j2.xml deleted file mode 100644 index 9849ed5a8a..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/src/main/resources/log4j2.xml +++ /dev/null @@ -1,30 +0,0 @@ - - - - - - - - - - - - - - \ No newline at end of file diff --git a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/support-version.list b/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/support-version.list deleted file mode 100644 index 243dded2f8..0000000000 --- a/test/plugin/scenarios/elasticsearch-java-7.15.x-scenario/support-version.list +++ /dev/null @@ -1,21 +0,0 @@ -# Licensed to the Apache Software Foundation (ASF) under one -# or more contributor license agreements. See the NOTICE file -# distributed with this work for additional information -# regarding copyright ownership. The ASF licenses this file -# to you under the Apache License, Version 2.0 (the -# "License"); you may not use this file except in compliance -# with the License. You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -# co.elastic.clients:elasticsearch-java 7.15.x -# RestClientTransport in co.elastic.clients.base.rest_client (moved to transport package in 7.16) -7.15.0 -7.15.1 -7.15.2