Fix operationName of entry span didn’t reset. And optimize interceptor initialization.
This commit is contained in:
parent
b3fe61aefe
commit
701b6afa12
|
|
@ -95,7 +95,7 @@ public class TracingContext implements AbstractTracerContext {
|
|||
@Override
|
||||
public AbstractSpan createEntrySpan(final String operationName) {
|
||||
AbstractTracingSpan entrySpan;
|
||||
AbstractTracingSpan parentSpan = peek();
|
||||
final AbstractTracingSpan parentSpan = peek();
|
||||
final int parentSpanId = parentSpan == null ? -1 : parentSpan.getSpanId();
|
||||
if (parentSpan == null) {
|
||||
entrySpan = (AbstractTracingSpan)DictionaryManager.findOperationNameCodeSection()
|
||||
|
|
@ -112,7 +112,18 @@ public class TracingContext implements AbstractTracerContext {
|
|||
entrySpan.start();
|
||||
return push(entrySpan);
|
||||
} else if (parentSpan.isEntry()) {
|
||||
return parentSpan.start();
|
||||
entrySpan = (AbstractTracingSpan)DictionaryManager.findOperationNameCodeSection()
|
||||
.find(segment.getApplicationId(), operationName)
|
||||
.doInCondition(new PossibleFound.FoundAndObtain() {
|
||||
@Override public Object doProcess(int operationId) {
|
||||
return parentSpan.setOperationId(operationId);
|
||||
}
|
||||
}, new PossibleFound.NotFoundAndObtain() {
|
||||
@Override public Object doProcess() {
|
||||
return parentSpan.setOperationName(operationName);
|
||||
}
|
||||
});
|
||||
return entrySpan.start();
|
||||
} else {
|
||||
throw new IllegalStateException("The Entry Span can't be the child of Non-Entry Span");
|
||||
}
|
||||
|
|
|
|||
|
|
@ -113,6 +113,16 @@ public abstract class AbstractTracingSpan implements AbstractSpan {
|
|||
return this;
|
||||
}
|
||||
|
||||
public AbstractTracingSpan setOperationName(String operationName) {
|
||||
this.operationName = operationName;
|
||||
return this;
|
||||
}
|
||||
|
||||
public AbstractTracingSpan setOperationId(int operationId) {
|
||||
this.operationId = operationId;
|
||||
return this;
|
||||
}
|
||||
|
||||
public int getSpanId() {
|
||||
return spanId;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -104,7 +104,7 @@ public abstract class ClassEnhancePluginDefine extends AbstractClassEnhancePlugi
|
|||
for (ConstructorInterceptPoint constructorInterceptPoint : constructorInterceptPoints) {
|
||||
newClassBuilder = newClassBuilder.constructor(ElementMatchers.<MethodDescription>any()).intercept(SuperMethodCall.INSTANCE
|
||||
.andThen(MethodDelegation.withDefaultConfiguration()
|
||||
.to(new ConstructorInter(constructorInterceptPoint.getConstructorInterceptor()))
|
||||
.to(new ConstructorInter(constructorInterceptPoint.getConstructorInterceptor(), classLoader))
|
||||
)
|
||||
);
|
||||
}
|
||||
|
|
@ -135,7 +135,7 @@ public abstract class ClassEnhancePluginDefine extends AbstractClassEnhancePlugi
|
|||
newClassBuilder.method(not(isStatic()).and(instanceMethodsInterceptPoint.getMethodsMatcher()))
|
||||
.intercept(
|
||||
MethodDelegation.withDefaultConfiguration()
|
||||
.to(new InstMethodsInter(interceptor))
|
||||
.to(new InstMethodsInter(interceptor, classLoader))
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,9 +1,11 @@
|
|||
package org.skywalking.apm.agent.core.plugin.interceptor.enhance;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import net.bytebuddy.implementation.bind.annotation.AllArguments;
|
||||
import net.bytebuddy.implementation.bind.annotation.FieldProxy;
|
||||
import net.bytebuddy.implementation.bind.annotation.RuntimeType;
|
||||
import net.bytebuddy.implementation.bind.annotation.This;
|
||||
import org.skywalking.apm.agent.core.plugin.PluginException;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.loader.InterceptorInstanceLoader;
|
||||
import org.skywalking.apm.logging.ILog;
|
||||
import org.skywalking.apm.logging.LogManager;
|
||||
|
|
@ -18,19 +20,21 @@ public class ConstructorInter {
|
|||
private static final ILog logger = LogManager.getLogger(ConstructorInter.class);
|
||||
|
||||
/**
|
||||
* A class full name, and instanceof {@link InstanceConstructorInterceptor}
|
||||
* An {@link InstanceConstructorInterceptor}
|
||||
* This name should only stay in {@link String}, the real {@link Class} type will trigger classloader failure.
|
||||
* If you want to know more, please check on books about Classloader or Classloader appointment mechanism.
|
||||
*/
|
||||
private String constructorInterceptorClassName;
|
||||
private InstanceConstructorInterceptor interceptor;
|
||||
|
||||
/**
|
||||
* Set the name of {@link ConstructorInter#constructorInterceptorClassName}
|
||||
*
|
||||
* @param constructorInterceptorClassName class full name.
|
||||
*/
|
||||
public ConstructorInter(String constructorInterceptorClassName) {
|
||||
this.constructorInterceptorClassName = constructorInterceptorClassName;
|
||||
public ConstructorInter(String constructorInterceptorClassName, ClassLoader classLoader) throws PluginException {
|
||||
try {
|
||||
interceptor = InterceptorInstanceLoader.load(constructorInterceptorClassName, classLoader);
|
||||
} catch (Throwable t) {
|
||||
throw new PluginException("Can't create InstanceConstructorInterceptor.", t);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -43,7 +47,6 @@ public class ConstructorInter {
|
|||
public void intercept(@This Object obj,
|
||||
@AllArguments Object[] allArguments) {
|
||||
try {
|
||||
InstanceConstructorInterceptor interceptor = InterceptorInstanceLoader.load(constructorInterceptorClassName, obj.getClass().getClassLoader());
|
||||
EnhancedInstance targetObject = (EnhancedInstance)obj;
|
||||
|
||||
interceptor.onConstruct(targetObject, allArguments);
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
package org.skywalking.apm.agent.core.plugin.interceptor.enhance;
|
||||
|
||||
import net.bytebuddy.implementation.bind.annotation.*;
|
||||
import org.skywalking.apm.agent.core.plugin.PluginException;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.loader.InterceptorInstanceLoader;
|
||||
import org.skywalking.apm.logging.ILog;
|
||||
import org.skywalking.apm.logging.LogManager;
|
||||
|
|
@ -18,19 +19,21 @@ public class InstMethodsInter {
|
|||
private static final ILog logger = LogManager.getLogger(InstMethodsInter.class);
|
||||
|
||||
/**
|
||||
* A class full name, and instanceof {@link InstanceMethodsAroundInterceptor}
|
||||
* An {@link InstanceMethodsAroundInterceptor}
|
||||
* This name should only stay in {@link String}, the real {@link Class} type will trigger classloader failure.
|
||||
* If you want to know more, please check on books about Classloader or Classloader appointment mechanism.
|
||||
*/
|
||||
private String instanceMethodsAroundInterceptorClassName;
|
||||
private InstanceMethodsAroundInterceptor interceptor;
|
||||
|
||||
/**
|
||||
* Set the name of {@link InstMethodsInter#instanceMethodsAroundInterceptorClassName}
|
||||
*
|
||||
* @param instanceMethodsAroundInterceptorClassName class full name.
|
||||
*/
|
||||
public InstMethodsInter(String instanceMethodsAroundInterceptorClassName) {
|
||||
this.instanceMethodsAroundInterceptorClassName = instanceMethodsAroundInterceptorClassName;
|
||||
public InstMethodsInter(String instanceMethodsAroundInterceptorClassName, ClassLoader classLoader) {
|
||||
try {
|
||||
interceptor = InterceptorInstanceLoader.load(instanceMethodsAroundInterceptorClassName, classLoader);
|
||||
} catch (Throwable t) {
|
||||
throw new PluginException("Can't create InstanceMethodsAroundInterceptor.", t);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -50,8 +53,6 @@ public class InstMethodsInter {
|
|||
@SuperCall Callable<?> zuper,
|
||||
@Origin Method method
|
||||
) throws Throwable {
|
||||
InstanceMethodsAroundInterceptor interceptor = InterceptorInstanceLoader
|
||||
.load(instanceMethodsAroundInterceptorClassName, obj.getClass().getClassLoader());
|
||||
EnhancedInstance targetObject = (EnhancedInstance)obj;
|
||||
|
||||
MethodInterceptResult result = new MethodInterceptResult();
|
||||
|
|
|
|||
|
|
@ -7,6 +7,7 @@ import net.bytebuddy.implementation.bind.annotation.Morph;
|
|||
import net.bytebuddy.implementation.bind.annotation.Origin;
|
||||
import net.bytebuddy.implementation.bind.annotation.RuntimeType;
|
||||
import net.bytebuddy.implementation.bind.annotation.This;
|
||||
import org.skywalking.apm.agent.core.plugin.PluginException;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.loader.InterceptorInstanceLoader;
|
||||
import org.skywalking.apm.logging.ILog;
|
||||
import org.skywalking.apm.logging.LogManager;
|
||||
|
|
@ -21,19 +22,21 @@ public class InstMethodsInterWithOverrideArgs {
|
|||
private static final ILog logger = LogManager.getLogger(InstMethodsInterWithOverrideArgs.class);
|
||||
|
||||
/**
|
||||
* A class full name, and instanceof {@link InstanceMethodsAroundInterceptor}
|
||||
* An {@link InstanceMethodsAroundInterceptor}
|
||||
* This name should only stay in {@link String}, the real {@link Class} type will trigger classloader failure.
|
||||
* If you want to know more, please check on books about Classloader or Classloader appointment mechanism.
|
||||
*/
|
||||
private String instanceMethodsAroundInterceptorClassName;
|
||||
private InstanceMethodsAroundInterceptor interceptor;
|
||||
|
||||
/**
|
||||
* Set the name of {@link InstMethodsInterWithOverrideArgs#instanceMethodsAroundInterceptorClassName}
|
||||
*
|
||||
* @param instanceMethodsAroundInterceptorClassName class full name.
|
||||
*/
|
||||
public InstMethodsInterWithOverrideArgs(String instanceMethodsAroundInterceptorClassName) {
|
||||
this.instanceMethodsAroundInterceptorClassName = instanceMethodsAroundInterceptorClassName;
|
||||
public InstMethodsInterWithOverrideArgs(String instanceMethodsAroundInterceptorClassName, ClassLoader classLoader) {
|
||||
try {
|
||||
interceptor = InterceptorInstanceLoader.load(instanceMethodsAroundInterceptorClassName, classLoader);
|
||||
} catch (Throwable t) {
|
||||
throw new PluginException("Can't create InstanceMethodsAroundInterceptor.", t);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -53,8 +56,6 @@ public class InstMethodsInterWithOverrideArgs {
|
|||
@Origin Method method,
|
||||
@Morph(defaultMethod = true) OverrideCallable zuper
|
||||
) throws Throwable {
|
||||
InstanceMethodsAroundInterceptor interceptor = InterceptorInstanceLoader
|
||||
.load(instanceMethodsAroundInterceptorClassName, obj.getClass().getClassLoader());
|
||||
EnhancedInstance targetObject = (EnhancedInstance)obj;
|
||||
|
||||
MethodInterceptResult result = new MethodInterceptResult();
|
||||
|
|
|
|||
|
|
@ -38,6 +38,9 @@ public class InterceptorInstanceLoader {
|
|||
|
||||
public static <T> T load(String className, ClassLoader targetClassLoader)
|
||||
throws InvocationTargetException, IllegalAccessException, InstantiationException, ClassNotFoundException {
|
||||
if (targetClassLoader == null) {
|
||||
targetClassLoader = InterceptorInstanceLoader.class.getClassLoader();
|
||||
}
|
||||
String instanceKey = className + "_OF_" + targetClassLoader.getClass().getName() + "@" + Integer.toHexString(targetClassLoader.hashCode());
|
||||
Object inst = INSTANCE_CACHE.get(instanceKey);
|
||||
if (inst == null) {
|
||||
|
|
@ -66,14 +69,14 @@ public class InterceptorInstanceLoader {
|
|||
}
|
||||
}
|
||||
|
||||
return (T) inst;
|
||||
return (T)inst;
|
||||
}
|
||||
|
||||
/**
|
||||
* load class from class binary files.
|
||||
* Most likely all the interceptor implementations should be loaded by this.
|
||||
*
|
||||
* @param className interceptor class name.
|
||||
* @param className interceptor class name.
|
||||
* @param targetClassLoader the classloader, which should load the interceptor.
|
||||
* @param <T>
|
||||
* @return interceptor instance.
|
||||
|
|
@ -82,7 +85,7 @@ public class InterceptorInstanceLoader {
|
|||
* @throws InstantiationException
|
||||
*/
|
||||
private static <T> T loadBinary(String className,
|
||||
ClassLoader targetClassLoader) throws InvocationTargetException, IllegalAccessException, InstantiationException {
|
||||
ClassLoader targetClassLoader) throws InvocationTargetException, IllegalAccessException, InstantiationException {
|
||||
String path = "/" + className.replace('.', '/').concat(".class");
|
||||
byte[] data = null;
|
||||
BufferedInputStream is = null;
|
||||
|
|
@ -122,21 +125,21 @@ public class InterceptorInstanceLoader {
|
|||
}
|
||||
defineClassMethod.setAccessible(true);
|
||||
logger.debug("load binary code of {} to classloader {}", className, targetClassLoader);
|
||||
Class<?> type = (Class<?>) defineClassMethod.invoke(targetClassLoader, className, data, 0, data.length, null);
|
||||
return (T) type.newInstance();
|
||||
Class<?> type = (Class<?>)defineClassMethod.invoke(targetClassLoader, className, data, 0, data.length, null);
|
||||
return (T)type.newInstance();
|
||||
}
|
||||
|
||||
/**
|
||||
* Find loaded class in the current classloader.
|
||||
* Just in case some classes have already been loaded for some reason.
|
||||
*
|
||||
* @param className interceptor class name.
|
||||
* @param className interceptor class name.
|
||||
* @param targetClassLoader the classloader, which should load the interceptor.
|
||||
* @param <T>
|
||||
* @return interceptor instance.
|
||||
*/
|
||||
private static <T> T findLoadedClass(String className,
|
||||
ClassLoader targetClassLoader) throws InvocationTargetException, IllegalAccessException, InstantiationException {
|
||||
ClassLoader targetClassLoader) throws InvocationTargetException, IllegalAccessException, InstantiationException {
|
||||
Method defineClassMethod = null;
|
||||
Class<?> targetClassLoaderType = targetClassLoader.getClass();
|
||||
while (defineClassMethod == null && targetClassLoaderType != null) {
|
||||
|
|
@ -147,10 +150,10 @@ public class InterceptorInstanceLoader {
|
|||
}
|
||||
}
|
||||
defineClassMethod.setAccessible(true);
|
||||
Class<?> type = (Class<?>) defineClassMethod.invoke(targetClassLoader, className);
|
||||
Class<?> type = (Class<?>)defineClassMethod.invoke(targetClassLoader, className);
|
||||
if (type == null) {
|
||||
return null;
|
||||
}
|
||||
return (T) type.newInstance();
|
||||
return (T)type.newInstance();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue