This commit is contained in:
Jaehong Kim
2015-11-12 10:40:42 +09:00
27 changed files with 282 additions and 115 deletions
@@ -19,11 +19,11 @@ package com.navercorp.pinpoint.bootstrap.plugin;
*
*/
public abstract class ObjectRecipe {
public abstract class ObjectFactory {
private final String className;
private final Object[] arguments;
private ObjectRecipe(String className, Object[] arguments) {
private ObjectFactory(String className, Object[] arguments) {
this.className = className;
this.arguments = arguments;
}
@@ -37,22 +37,22 @@ public abstract class ObjectRecipe {
}
public static ObjectRecipe byConstructor(String className, Object... args) {
public static ObjectFactory byConstructor(String className, Object... args) {
return new ByConstructor(className, args);
}
public static ObjectRecipe byStaticFactory(String className, String factoryMethodName, Object... args) {
public static ObjectFactory byStaticFactory(String className, String factoryMethodName, Object... args) {
return new ByStaticFactoryMethod(className, factoryMethodName, args);
}
public static class ByConstructor extends ObjectRecipe {
public static class ByConstructor extends ObjectFactory {
public ByConstructor(String className, Object[] arguments) {
super(className, arguments);
}
}
public static class ByStaticFactoryMethod extends ObjectRecipe {
public static class ByStaticFactoryMethod extends ObjectFactory {
private final String factoryMethodName;
public ByStaticFactoryMethod(String className, String factoryMethodName, Object[] arguments) {
@@ -65,17 +65,17 @@ public abstract class ObjectRecipe {
}
}
public static class ByFactoryObject extends ObjectRecipe {
private final ObjectRecipe recipe;
public static class ByFactoryObject extends ObjectFactory {
private final ObjectFactory recipe;
private final String factoryMethod;
public ByFactoryObject(String className, ObjectRecipe recipe, String factoryMethod, Object[] arguments) {
public ByFactoryObject(String className, ObjectFactory recipe, String factoryMethod, Object[] arguments) {
super(className, arguments);
this.recipe = recipe;
this.factoryMethod = factoryMethod;
}
public ObjectRecipe getRecipe() {
public ObjectFactory getRecipe() {
return recipe;
}
@@ -14,6 +14,7 @@
*/
package com.navercorp.pinpoint.plugin.arcus.interceptor;
import java.net.InetAddress;
import java.net.InetSocketAddress;
import java.net.SocketAddress;
import java.util.concurrent.Future;
@@ -126,15 +127,14 @@ public class ApiInterceptor implements AroundInterceptor {
// find the target node
if (result instanceof Future && result instanceof OperationAccessor) {
Operation op = ((OperationAccessor)result)._$PINPOINT$_getOperation();
final Operation op = ((OperationAccessor)result)._$PINPOINT$_getOperation();
if (op != null) {
MemcachedNode handlingNode = op.getHandlingNode();
SocketAddress socketAddress = handlingNode.getSocketAddress();
if (socketAddress instanceof InetSocketAddress) {
InetSocketAddress address = (InetSocketAddress) socketAddress;
recorder.recordEndPoint(address.getHostName() + ":" + address.getPort());
final MemcachedNode handlingNode = op.getHandlingNode();
if (handlingNode != null) {
final String endPoint = getEndPoint(handlingNode);
if (endPoint != null) {
recorder.recordEndPoint(endPoint);
}
}
} else {
logger.info("operation not found");
@@ -179,6 +179,40 @@ public class ApiInterceptor implements AroundInterceptor {
}
}
private String getEndPoint(MemcachedNode handlingNode) {
// TODO duplicated code : ApiInterceptor, FutureGetInterceptor
final SocketAddress socketAddress = handlingNode.getSocketAddress();
if (socketAddress instanceof InetSocketAddress) {
final InetSocketAddress inetSocketAddress = (InetSocketAddress) socketAddress;
final String hostAddress = getHostAddress(inetSocketAddress);
if (hostAddress == null) {
// TODO return "Unknown Host"; ?
logger.debug("hostAddress is null");
return null;
}
return hostAddress + ":" + inetSocketAddress.getPort();
} else {
if (logger.isDebugEnabled()) {
logger.debug("invalid socketAddress:{}", socketAddress);
}
return null;
}
}
private String getHostAddress(InetSocketAddress inetSocketAddress) {
if (inetSocketAddress == null) {
return null;
}
// TODO JDK 1.7 InetSocketAddress.getHostString();
// Warning : Avoid unnecessary DNS lookup (warning:InetSocketAddress.getHostName())
final InetAddress inetAddress = inetSocketAddress.getAddress();
if (inetAddress == null) {
return null;
}
return inetAddress.getHostAddress();
}
private boolean isAsynchronousInvocation(final Object target, final Object[] args, Object result, Throwable throwable) {
if (throwable != null || result == null) {
return false;
@@ -14,6 +14,7 @@
*/
package com.navercorp.pinpoint.plugin.arcus.interceptor;
import java.net.InetAddress;
import java.net.InetSocketAddress;
import java.net.SocketAddress;
@@ -64,13 +65,14 @@ public class FutureGetInterceptor extends SpanAsyncEventSimpleAroundInterceptor
}
recorder.recordException(op.getException());
MemcachedNode handlingNode = op.getHandlingNode();
final MemcachedNode handlingNode = op.getHandlingNode();
if (handlingNode != null) {
SocketAddress socketAddress = handlingNode.getSocketAddress();
if (socketAddress instanceof InetSocketAddress) {
InetSocketAddress address = (InetSocketAddress) socketAddress;
recorder.recordEndPoint(address.getHostName() + ":" + address.getPort());
final String endPoint = getEndPoint(handlingNode);
if (endPoint != null) {
recorder.recordEndPoint(endPoint);
}
recorder.recordException(op.getException());
} else {
logger.info("no handling node");
}
@@ -84,4 +86,38 @@ public class FutureGetInterceptor extends SpanAsyncEventSimpleAroundInterceptor
}
}
}
private String getEndPoint(MemcachedNode handlingNode) {
// TODO duplicated code : ApiInterceptor, FutureGetInterceptor
final SocketAddress socketAddress = handlingNode.getSocketAddress();
if (socketAddress instanceof InetSocketAddress) {
final InetSocketAddress inetSocketAddress = (InetSocketAddress) socketAddress;
final String hostAddress = getHostAddress(inetSocketAddress);
if (hostAddress == null) {
// TODO return "Unknown Host";
logger.debug("hostAddress is null");
return null;
}
return hostAddress + ":" + inetSocketAddress.getPort();
} else {
if (logger.isDebugEnabled()) {
logger.debug("invalid socketAddress:{}", socketAddress);
}
return null;
}
}
private String getHostAddress(InetSocketAddress inetSocketAddress) {
if (inetSocketAddress == null) {
return null;
}
// TODO JDK 1.7 InetSocketAddress.getHostString();
// Warning : Avoid unnecessary DNS lookup (warning:InetSocketAddress.getHostName())
final InetAddress inetAddress = inetSocketAddress.getAddress();
if (inetAddress == null) {
return null;
}
return inetAddress.getHostAddress();
}
}
@@ -24,7 +24,7 @@ import com.navercorp.pinpoint.bootstrap.instrument.transformer.TransformTemplate
import com.navercorp.pinpoint.bootstrap.instrument.transformer.TransformTemplateAware;
import com.navercorp.pinpoint.bootstrap.logging.PLogger;
import com.navercorp.pinpoint.bootstrap.logging.PLoggerFactory;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory;
import com.navercorp.pinpoint.bootstrap.plugin.ProfilerPlugin;
import com.navercorp.pinpoint.bootstrap.plugin.ProfilerPluginSetupContext;
@@ -125,8 +125,8 @@ public class OkHttpPlugin implements ProfilerPlugin, TransformTemplateAware {
if (sendRequestMethod != null) {
logger.debug("[OkHttp] Add HttpEngine.sendRequest interceptor.");
final ObjectRecipe objectRecipe = ObjectRecipe.byConstructor("com.navercorp.pinpoint.plugin.okhttp.OkHttpPluginConfig", instrumentContext.getProfilerConfig());
sendRequestMethod.addInterceptor("com.navercorp.pinpoint.plugin.okhttp.interceptor.HttpEngineSendRequestMethodInterceptor", va(objectRecipe));
final ObjectFactory objectFactory = ObjectFactory.byConstructor("com.navercorp.pinpoint.plugin.okhttp.OkHttpPluginConfig", instrumentContext.getProfilerConfig());
sendRequestMethod.addInterceptor("com.navercorp.pinpoint.plugin.okhttp.interceptor.HttpEngineSendRequestMethodInterceptor", va(objectFactory));
}
InstrumentMethod connectMethod = target.getDeclaredMethod("connect");
@@ -23,7 +23,7 @@ import com.navercorp.pinpoint.bootstrap.instrument.Instrumentor;
import com.navercorp.pinpoint.bootstrap.instrument.transformer.TransformCallback;
import com.navercorp.pinpoint.bootstrap.instrument.transformer.TransformTemplate;
import com.navercorp.pinpoint.bootstrap.instrument.transformer.TransformTemplateAware;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory;
import com.navercorp.pinpoint.bootstrap.plugin.ProfilerPlugin;
import com.navercorp.pinpoint.bootstrap.plugin.ProfilerPluginSetupContext;
@@ -50,13 +50,13 @@ public class SpringBeansPlugin implements ProfilerPlugin, TransformTemplateAware
InstrumentClass target = instrumentContext.getInstrumentClass(loader, className, classfileBuffer);
BeanMethodTransformer beanTransformer = new BeanMethodTransformer();
ObjectRecipe beanFilterRecipe = ObjectRecipe.byStaticFactory("com.navercorp.pinpoint.plugin.spring.beans.interceptor.TargetBeanFilter", "of", context.getConfig());
ObjectFactory beanFilterFactory = ObjectFactory.byStaticFactory("com.navercorp.pinpoint.plugin.spring.beans.interceptor.TargetBeanFilter", "of", context.getConfig());
InstrumentMethod createBeanInstance = target.getDeclaredMethod("createBeanInstance", "java.lang.String", "org.springframework.beans.factory.support.RootBeanDefinition", "java.lang.Object[]");
createBeanInstance.addInterceptor("com.navercorp.pinpoint.plugin.spring.beans.interceptor.CreateBeanInstanceInterceptor", va(beanTransformer, beanFilterRecipe));
createBeanInstance.addInterceptor("com.navercorp.pinpoint.plugin.spring.beans.interceptor.CreateBeanInstanceInterceptor", va(beanTransformer, beanFilterFactory));
InstrumentMethod postProcessor = target.getDeclaredMethod("applyBeanPostProcessorsBeforeInstantiation", "java.lang.Class", "java.lang.String");
postProcessor.addInterceptor("com.navercorp.pinpoint.plugin.spring.beans.interceptor.PostProcessorInterceptor", va(beanTransformer, beanFilterRecipe));
postProcessor.addInterceptor("com.navercorp.pinpoint.plugin.spring.beans.interceptor.PostProcessorInterceptor", va(beanTransformer, beanFilterFactory));
return target.toBytecode();
}
@@ -22,7 +22,6 @@ import java.lang.reflect.Method;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.Collection;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.jar.JarFile;
import javassist.CannotCompileException;
@@ -75,10 +74,13 @@ public class JarProfilerPluginClassInjector implements ClassInjector {
private final Instrumentation instrumentation;
private final InstrumentClassPool classPool;
private final AtomicBoolean injectedToRoot = new AtomicBoolean(false);
private final URL pluginJarURL;
private final String pluginJarURLExternalForm;
private final JarFile pluginJar;
private final Object lock = new Object();
private boolean injectedToRoot = false;
private JarProfilerPluginClassInjector(Instrumentation instrumentation, InstrumentClassPool classPool, URL pluginJarURL, JarFile pluginJar) {
@@ -107,9 +109,12 @@ public class JarProfilerPluginClassInjector implements ClassInjector {
}
private Class<?> injectToBootstrapClassLoader(String className) throws IllegalArgumentException, IllegalAccessException, InvocationTargetException, ClassNotFoundException {
if (injectedToRoot.compareAndSet(false, true)) {
instrumentation.appendToBootstrapClassLoaderSearch(pluginJar);
classPool.appendToBootstrapClassPath(pluginJar.getName());
synchronized (lock) {
if (this.injectedToRoot == false) {
this.injectedToRoot = true;
instrumentation.appendToBootstrapClassLoaderSearch(pluginJar);
classPool.appendToBootstrapClassPath(pluginJar.getName());
}
}
return Class.forName(className, false, null);
@@ -149,38 +154,34 @@ public class JarProfilerPluginClassInjector implements ClassInjector {
private Class<?> injectToPlainClassLoader(ClassPool pool, ClassLoader classLoader, String className) throws NotFoundException, IOException, CannotCompileException, IllegalArgumentException, IllegalAccessException, InvocationTargetException {
Class<?> c = null;
try {
c = classLoader.loadClass(className);
} catch (ClassNotFoundException ignore) {
} catch (ClassNotFoundException ex) {
if (logger.isTraceEnabled()) {
logger.trace("ClassNotFound {}", ex.getMessage(), ex);
}
}
if (c != null) {
return c;
}
CtClass ct = pool.get(className);
final CtClass ct = pool.get(className);
if (ct == null) {
throw new NotFoundException(className);
}
CtClass superClass = ct.getSuperclass();
final CtClass superClass = ct.getSuperclass();
if (superClass != null) {
injectToPlainClassLoader(pool, classLoader, superClass.getName());
}
CtClass[] interfaces = ct.getInterfaces();
for (CtClass i : interfaces) {
injectToPlainClassLoader(pool, classLoader, i.getName());
final CtClass[] interfaces = ct.getInterfaces();
for (CtClass ctInterface : interfaces) {
injectToPlainClassLoader(pool, classLoader, ctInterface.getName());
}
Collection<String> refs = ct.getRefClasses();
final Collection<String> refs = ct.getRefClasses();
for (String ref : refs) {
try {
injectToPlainClassLoader(pool, classLoader, ref);
@@ -189,7 +190,7 @@ public class JarProfilerPluginClassInjector implements ClassInjector {
}
}
byte[] bytes = ct.toBytecode();
final byte[] bytes = ct.toBytecode();
return (Class<?>)DEFINE_CLASS.invoke(classLoader, ct.getName(), bytes, 0, bytes.length);
}
}
@@ -43,7 +43,7 @@ import com.navercorp.pinpoint.bootstrap.interceptor.annotation.TargetMethod;
import com.navercorp.pinpoint.bootstrap.interceptor.annotation.TargetMethods;
import com.navercorp.pinpoint.bootstrap.interceptor.group.ExecutionPolicy;
import com.navercorp.pinpoint.bootstrap.interceptor.group.InterceptorGroup;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory;
import com.navercorp.pinpoint.common.util.Asserts;
import com.navercorp.pinpoint.exception.PinpointException;
import com.navercorp.pinpoint.profiler.instrument.AccessorAnalyzer.AccessorDetails;
@@ -538,7 +538,8 @@ public class JavassistClass implements InstrumentClass {
final TraceContext traceContext = pluginContext.getTraceContext();
final InterceptorArgumentProvider interceptorArgumentProvider = new InterceptorArgumentProvider(traceContext, this);
AutoBindingObjectFactory filterFactory = new AutoBindingObjectFactory(pluginContext, classLoader, interceptorArgumentProvider);
MethodFilter filter = (MethodFilter) filterFactory.createInstance(ObjectRecipe.byConstructor(filterTypeName, (Object[]) annotation.constructorArguments()));
final ObjectFactory objectFactory = ObjectFactory.byConstructor(filterTypeName, (Object[]) annotation.constructorArguments());
MethodFilter filter = (MethodFilter) filterFactory.createInstance(objectFactory);
boolean singleton = annotation.singleton();
int interceptorId = -1;
@@ -41,7 +41,7 @@ import com.navercorp.pinpoint.bootstrap.interceptor.group.GroupedInterceptor4;
import com.navercorp.pinpoint.bootstrap.interceptor.group.GroupedInterceptor5;
import com.navercorp.pinpoint.bootstrap.interceptor.group.GroupedStaticAroundInterceptor;
import com.navercorp.pinpoint.bootstrap.interceptor.group.InterceptorGroup;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory;
import com.navercorp.pinpoint.profiler.objectfactory.AutoBindingObjectFactory;
import com.navercorp.pinpoint.profiler.objectfactory.InterceptorArgumentProvider;
@@ -67,10 +67,10 @@ public class AnnotatedInterceptorFactory implements InterceptorFactory {
}
AutoBindingObjectFactory factory = new AutoBindingObjectFactory(pluginContext, classLoader);
ObjectRecipe recipe = ObjectRecipe.byConstructor(interceptorClassName, providedArguments);
ObjectFactory objectFactory = ObjectFactory.byConstructor(interceptorClassName, providedArguments);
InterceptorArgumentProvider interceptorArgumentProvider = new InterceptorArgumentProvider(pluginContext.getTraceContext(), group, target, targetMethod);
Interceptor interceptor = (Interceptor)factory.createInstance(recipe, interceptorArgumentProvider);
Interceptor interceptor = (Interceptor)factory.createInstance(objectFactory, interceptorArgumentProvider);
if (group != null) {
interceptor = wrapByGroup(interceptor, group, policy == null ? ExecutionPolicy.BOUNDARY : policy);
@@ -24,9 +24,9 @@ import com.navercorp.pinpoint.bootstrap.instrument.InstrumentContext;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe.ByConstructor;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe.ByStaticFactoryMethod;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory.ByConstructor;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory.ByStaticFactoryMethod;
import com.navercorp.pinpoint.exception.PinpointException;
/**
@@ -48,17 +48,17 @@ public class AutoBindingObjectFactory {
this.commonProviders.add(new ProfilerPluginArgumentProvider(pluginContext));
}
public Object createInstance(ObjectRecipe recipe, ArgumentProvider... providers) {
Class<?> type = pluginContext.injectClass(classLoader, recipe.getClassName());
ArgumentsResolver argumentsResolver = getArgumentResolver(recipe, providers);
public Object createInstance(ObjectFactory objectFactory, ArgumentProvider... providers) {
Class<?> type = pluginContext.injectClass(classLoader, objectFactory.getClassName());
ArgumentsResolver argumentsResolver = getArgumentResolver(objectFactory, providers);
if (recipe instanceof ByConstructor) {
return byConstructor(type, (ByConstructor)recipe, argumentsResolver);
} else if (recipe instanceof ByStaticFactoryMethod) {
return byStaticFactoryMethod(type, (ByStaticFactoryMethod)recipe, argumentsResolver);
if (objectFactory instanceof ByConstructor) {
return byConstructor(type, (ByConstructor) objectFactory, argumentsResolver);
} else if (objectFactory instanceof ByStaticFactoryMethod) {
return byStaticFactoryMethod(type, (ByStaticFactoryMethod) objectFactory, argumentsResolver);
}
throw new IllegalArgumentException("Unknown recipe type: " + recipe);
throw new IllegalArgumentException("Unknown objectFactory type: " + objectFactory);
}
private Object byConstructor(Class<?> type, ByConstructor recipe, ArgumentsResolver argumentsResolver) {
@@ -104,7 +104,7 @@ public class AutoBindingObjectFactory {
}
private ArgumentsResolver getArgumentResolver(ObjectRecipe recipe, ArgumentProvider[] providers) {
private ArgumentsResolver getArgumentResolver(ObjectFactory recipe, ArgumentProvider[] providers) {
List<ArgumentProvider> merged = new ArrayList<ArgumentProvider>(commonProviders);
merged.addAll(Arrays.asList(providers));
@@ -16,7 +16,7 @@ package com.navercorp.pinpoint.profiler.objectfactory;
import java.lang.annotation.Annotation;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory;
import com.navercorp.pinpoint.profiler.util.TypeUtils;
/**
@@ -75,8 +75,8 @@ public class OrderedValueProvider implements JudgingParameterResolver {
Object val = values[index];
if (val instanceof ObjectRecipe) {
val = objectFactory.createInstance((ObjectRecipe)val);
if (val instanceof ObjectFactory) {
val = objectFactory.createInstance((ObjectFactory)val);
values[index] = val;
}
}
@@ -28,7 +28,7 @@ import com.navercorp.pinpoint.bootstrap.interceptor.annotation.TargetFilter;
import com.navercorp.pinpoint.bootstrap.interceptor.annotation.TargetMethod;
import com.navercorp.pinpoint.bootstrap.interceptor.annotation.TargetMethods;
import com.navercorp.pinpoint.bootstrap.interceptor.group.ExecutionPolicy;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory;
import com.navercorp.pinpoint.exception.PinpointException;
import com.navercorp.pinpoint.profiler.objectfactory.AutoBindingObjectFactory;
import com.navercorp.pinpoint.profiler.objectfactory.InterceptorArgumentProvider;
@@ -139,7 +139,7 @@ public class TargetAnnotatedInterceptorInjector implements ClassRecipe {
final TraceContext traceContext = pluginContext.getTraceContext();
final InterceptorArgumentProvider interceptorArgumentProvider = new InterceptorArgumentProvider(traceContext, targetClass);
AutoBindingObjectFactory filterFactory = new AutoBindingObjectFactory(pluginContext, classLoader, interceptorArgumentProvider);
MethodFilter filter = (MethodFilter)filterFactory.createInstance(ObjectRecipe.byConstructor(type, (Object[])annotation.constructorArguments()));
MethodFilter filter = (MethodFilter)filterFactory.createInstance(ObjectFactory.byConstructor(type, (Object[]) annotation.constructorArguments()));
MethodRecipe recipe = annotation.singleton() ? new SharedAnnotatedInterceptorInjector(injector) : injector;
return new FilteringMethodTransformer(new MethodFilter[] { filter }, Arrays.<MethodRecipe>asList(recipe), null);
@@ -33,7 +33,7 @@ import com.navercorp.pinpoint.bootstrap.context.TraceContext;
import com.navercorp.pinpoint.bootstrap.instrument.InstrumentClass;
import com.navercorp.pinpoint.bootstrap.instrument.InstrumentMethod;
import com.navercorp.pinpoint.bootstrap.interceptor.Interceptor;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectRecipe;
import com.navercorp.pinpoint.bootstrap.plugin.ObjectFactory;
import com.navercorp.pinpoint.exception.PinpointException;
import com.navercorp.pinpoint.profiler.interceptor.factory.AnnotatedInterceptorFactory;
import com.navercorp.pinpoint.profiler.plugin.TestInterceptors.TestInterceptor0;
@@ -256,7 +256,7 @@ public class AnnotatedInterceptorFactoryTest {
@Test
public void test14() throws Exception {
String arg0 = "arg0";
Object[] args = new Object[] { ObjectRecipe.byConstructor("java.lang.String", arg0) };
Object[] args = new Object[] { ObjectFactory.byConstructor("java.lang.String", arg0) };
AnnotatedInterceptorFactory factory = new AnnotatedInterceptorFactory(pluginContext);
Interceptor interceptor = factory.getInterceptor(getClass().getClassLoader(), TestInterceptor0.class.getName(), args, null, null, aClass, aMethod);
@@ -15,6 +15,7 @@
*/
package com.navercorp.pinpoint.web.controller;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@@ -87,10 +88,12 @@ public class UserGroupController {
@RequestMapping(method = RequestMethod.GET)
@ResponseBody
public List<UserGroup> getUserGroup(@RequestParam(value=USER_ID, required=false) String userId) {
public List<UserGroup> getUserGroup(@RequestParam(value=USER_ID, required=false) String userId, @RequestParam(value=USER_GROUP_ID, required=false) String userGroupId) {
if(userId != null) {
if (!StringUtils.isEmpty(userId)) {
return userGroupService.selectUserGroupByUserId(userId);
} else if (!StringUtils.isEmpty(userGroupId)) {
return userGroupService.selectUserGroupByUserGroupId(userGroupId);
}
return userGroupService.selectUserGroup();
}
@@ -177,7 +180,7 @@ public class UserGroupController {
@ExceptionHandler(Exception.class)
@ResponseBody
public Map<String, String> handleException(Exception e) {
logger.error(" Exception occurred while trying to CRUD userGroup information", e);
logger.error("Exception occurred while trying to CRUD userGroup information", e);
Map<String, String> result = new HashMap<String, String>();
result.put("errorCode", "500");
@@ -30,6 +30,8 @@ public interface UserGroupDao {
List<UserGroup> selectUserGroupByUserId(String userId);
List<UserGroup> selectUserGroupByUserGroupId(String userGroupId);
void updateUserGroup(UserGroup userGroup);
void deleteUserGroup(UserGroup userGroup);
@@ -49,4 +51,5 @@ public interface UserGroupDao {
void deleteMemberByUserGroupId(String userGroupId);
void updateUserGroupIdOfMember(UserGroup userGroup);
}
@@ -81,6 +81,19 @@ public class MemoryUserGroupDao implements UserGroupDao {
return groups;
}
@Override
public List<UserGroup> selectUserGroupByUserGroupId(String userGroupId) {
List<UserGroup> userGroupList = new ArrayList<>();
for(UserGroup userGroup : userGroups.values()) {
if (userGroup.getId().contains(userGroupId)) {
userGroupList.add(userGroup);
}
}
return userGroupList;
}
@Override
public void updateUserGroup(UserGroup userGroup) {
@@ -194,5 +207,4 @@ public class MemoryUserGroupDao implements UserGroupDao {
}
}
}
}
@@ -55,6 +55,11 @@ public class MysqlUserGroupDao implements UserGroupDao {
public List<UserGroup> selectUserGroupByUserId(String userId) {
return sqlSessionTemplate.selectList(NAMESPACE + "selectUserGroupListByUserId", userId);
}
@Override
public List<UserGroup> selectUserGroupByUserGroupId(String userGroupId) {
return sqlSessionTemplate.selectList(NAMESPACE + "selectUserGroupByUserGroupId", userGroupId);
}
@Override
public void updateUserGroup(UserGroup userGroup) {
@@ -104,9 +109,5 @@ public class MysqlUserGroupDao implements UserGroupDao {
@Override
public void updateUserGroupIdOfMember(UserGroup userGroup) {
sqlSessionTemplate.update(NAMESPACE + "updateUserGroupIdOfMember", userGroup);
}
}
@@ -30,6 +30,8 @@ public interface UserGroupService {
List<UserGroup> selectUserGroupByUserId(String userId);
List<UserGroup> selectUserGroupByUserGroupId(String userGroupId);
void updateUserGroup(UserGroup userGroup);
void deleteUserGroup(UserGroup userGroup);
@@ -51,4 +53,5 @@ public interface UserGroupService {
void updateUserGroupIdOfMember(UserGroup userGroup);
}
@@ -48,6 +48,11 @@ public class UserGroupServiceImpl implements UserGroupService {
return userGroupDao.selectUserGroupByUserId(userId);
}
@Override
public List<UserGroup> selectUserGroupByUserGroupId(String userGroupId) {
return userGroupDao.selectUserGroupByUserGroupId(userGroupId);
}
@Override
public void updateUserGroup(UserGroup userGroup) {
userGroupDao.updateUserGroup(userGroup);
@@ -22,6 +22,12 @@
WHERE member_id = #{userId}
)
</select>
<select id="selectUserGroupByUserGroupId" parameterType="String" resultType="UserGroup">
SELECT *
FROM user_group
WHERE id LIKE CONCAT('%', #{userGroupId}, '%')
</select>
<delete id="deleteUserGroup" parameterType="UserGroup">
DELETE
@@ -14,7 +14,7 @@
pinpointApp.directive('loadChartDirective', ['loadChartDirectiveConfig', '$timeout', 'AnalyticsService', function (cfg, $timeout, analyticsService) {
return {
template: '<div></div>',
template: '<div style="text-align:center"></div>',
replace: true,
restrict: 'EA',
scope: {
@@ -27,7 +27,7 @@
// define variables of methods
var setIdAutomatically, setWidthHeight, render, parseTimeSeriesHistogramForAmcharts, updateData,
renderSimple;
renderSimple, renderEmpty;
/**
* set id automatically
@@ -258,6 +258,9 @@
});
});
};
renderEmpty = function() {
element.append("<h4 style='padding-top:25%'>No Data</h4>");
};
/**
* update data
@@ -265,11 +268,17 @@
*/
updateData = function (data) {
// oChart.dataProvider = data;
oChart.clear();
if ( angular.isDefined( oChart ) ) {
oChart.clear();
}
element.empty();
$timeout(function () {
// oChart.validateData();
render(data, true);
if( data.length === 0 ) {
renderEmpty();
} else {
render(data, true);
}
});
};
@@ -279,6 +288,8 @@
* @returns {Array}
*/
parseTimeSeriesHistogramForAmcharts = function (data) {
if ( angular.isUndefined( data ) ) return [];
function getKeyFromNewDataByTime (time) {
for (var key in newData) {
if (moment(time).format("YYYY-MM-DD HH:mm") === newData[key].time) {
@@ -315,7 +326,12 @@
scope.$on('loadChartDirective.initAndRenderWithData.' + scope.namespace, function (event, data, w, h, useChartCursor) {
setIdAutomatically();
setWidthHeight(w, h);
render(parseTimeSeriesHistogramForAmcharts(data), useChartCursor);
var parsedData = parseTimeSeriesHistogramForAmcharts(data);
if ( parsedData.length === 0 ) {
renderEmpty();
} else {
render(parsedData, useChartCursor);
}
});
/**
@@ -331,7 +347,12 @@
scope.$on('loadChartDirective.initAndSimpleRenderWithData.' + scope.namespace, function (event, data, w, h, useChartCursor) {
setIdAutomatically();
setWidthHeight(w, h);
renderSimple(parseTimeSeriesHistogramForAmcharts(data), useChartCursor);
var parsedData = parseTimeSeriesHistogramForAmcharts(data);
if ( parsedData.length === 0 ) {
renderEmpty();
} else {
renderSimple(parsedData, useChartCursor);
}
});
}
};
@@ -20,7 +20,6 @@
replace: true,
templateUrl: 'features/navbar/navbar.html?v=' + G_BUILD_TIME,
link: function (scope, element) {
// define private variables
var $application, $fromPicker, $toPicker, oNavbarVoService;
@@ -28,7 +27,7 @@
var initialize, initializeDateTimePicker, initializeApplication, setDateTime, getQueryEndTimeFromServer,
broadcast, getApplicationList, getQueryStartTime, getQueryEndTime, parseApplicationList, emitAsChanged,
initializeWithStaticApplication, getPeriodType, setPeriodTypeAsCurrent, getDate, startUpdate,
resetTimeLeft, getRangeFromStorage, setRangeToStorage, getMilliSecondByReadablePeriod, movePeriod;
resetTimeLeft, getRangeFromStorage, setRangeToStorage, getMilliSecondByReadablePeriod, movePeriod, selectPeriod;
var applicationResource;
/**
@@ -98,7 +97,7 @@
*/
initialize = function (navbarVoService) {
oNavbarVoService = navbarVoService;
scope.periodType = getPeriodType();
scope.showNavbar = true;
scope.showStaticApplication = false;
@@ -114,7 +113,7 @@
scope.disableApplication = true;
scope.readablePeriod = oNavbarVoService.getReadablePeriod() || preferenceService.getPeriod();
scope.queryEndTime = oNavbarVoService.getQueryEndTime() || '';
initializeApplication();
initializeDateTimePicker();
getApplicationList();
@@ -436,6 +435,19 @@
emitAsChanged();
}
};
selectPeriod = function( readablePeriod ) {
analyticsService.send(analyticsService.CONST.MAIN, analyticsService.CONST.CLK_TIME, readablePeriod);
scope.periodDelay = true;
scope.readablePeriod = readablePeriod;
scope.autoUpdate = false;
broadcast();
$timeout(function () {
scope.periodDelay = false;
if (!scope.$$phase) {
scope.$digest();
}
}, 1000);
}
/**
@@ -450,17 +462,7 @@
* @param readablePeriod
*/
scope.setPeriod = function (readablePeriod) {
analyticsService.send(analyticsService.CONST.MAIN, analyticsService.CONST.CLK_TIME, readablePeriod);
scope.periodDelay = true;
scope.readablePeriod = readablePeriod;
scope.autoUpdate = false;
broadcast();
$timeout(function () {
scope.periodDelay = false;
if (!scope.$$phase) {
scope.$digest();
}
}, 1000);
selectPeriod(readablePeriod);
};
scope.getPreviousClass = function() {
return "";
@@ -584,6 +586,11 @@
scope.$on('navbarDirective.initialize', function (event, navbarVo) {
initialize(navbarVo);
});
scope.$on('navbarDirective.initialize.andReload', function (event, navbarVo) {
initialize(navbarVo);
scope.periodType = 'last';
selectPeriod(preferenceService.getPeriod());
});
/**
* scope event on navbarDirective.initializeWithStaticApplication
@@ -27,7 +27,7 @@
// define variables of methods
var setIdAutomatically, setWidthHeight, render, clickGraphItemListener, updateData,
parseHistogramForAmcharts;
parseHistogramForAmcharts, renderEmpty;
/**
* set id automatically
@@ -128,10 +128,10 @@
* @param data
*/
updateData = function (data) {
oChart.dataProvider = data;
oChart.dataProvider = data;
$timeout(function () {
oChart.validateData();
});
});
};
/**
@@ -140,6 +140,9 @@
* @returns {Array}
*/
parseHistogramForAmcharts = function (data) {
if ( angular.isUndefined( data ) ) {
data = {"1s": 0, "3s": 0, "5s": 0, "Slow": 0, "Error": 0};
}
var newData = [],
alpha = [0.2, 0.3, 0.4, 0.6, 0.6],
i = 0;
@@ -160,7 +163,7 @@
scope.$on('responseTimeChartDirective.initAndRenderWithData.' + scope.namespace, function (event, data, w, h, useFilterTransaction, useChartCursor) {
setIdAutomatically();
setWidthHeight(w, h);
render(parseHistogramForAmcharts(data), useFilterTransaction, useChartCursor);
render(parseHistogramForAmcharts(data), useFilterTransaction, useChartCursor);
});
/**
@@ -222,7 +222,7 @@
* @param mapData
*/
emitDataExisting = function (mapData) {
if (mapData.applicationMapData.nodeDataArray.length === 0 || mapData.applicationMapData.linkDataArray.length === 0) {
if (mapData.applicationMapData.nodeDataArray.length === 0 ) {
scope.$emit('serverMapDirective.hasNoData');
} else {
scope.$emit('serverMapDirective.hasData');
@@ -38,11 +38,15 @@
if ($routeParams.queryEndDateTime) {
oNavbarVoService.setQueryEndDateTime($routeParams.queryEndDateTime);
}
$window.$routeParams = $routeParams;
oNavbarVoService.autoCalculateByQueryEndDateTimeAndReadablePeriod();
$scope.$broadcast('navbarDirective.initialize', oNavbarVoService);
$scope.$broadcast('scatterDirective.initialize', oNavbarVoService);
$scope.$broadcast('serverMapDirective.initialize', oNavbarVoService);
if ( angular.isDefined( $routeParams.application) && angular.isUndefined( $routeParams.readablePeriod ) && angular.isUndefined( $routeParams.readablePeriod ) ) {
$scope.$broadcast('navbarDirective.initialize.andReload', oNavbarVoService);
} else {
$window.$routeParams = $routeParams;
oNavbarVoService.autoCalculateByQueryEndDateTimeAndReadablePeriod();
$scope.$broadcast('navbarDirective.initialize', oNavbarVoService);
$scope.$broadcast('scatterDirective.initialize', oNavbarVoService);
$scope.$broadcast('serverMapDirective.initialize', oNavbarVoService);
}
}, 500);
/**
+3
View File
@@ -11,6 +11,9 @@ pinpointApp.config(['$routeProvider', '$locationProvider', '$modalProvider', fun
$routeProvider.when('/main', {
templateUrl: 'pages/main/ready.html',
controller: 'MainCtrl'
}).when('/main/:application', {
templateUrl: 'pages/main/main.html',
controller: 'MainCtrl'
}).when('/main/:application/:readablePeriod/:queryEndDateTime', {
templateUrl: 'pages/main/main.html',
controller: 'MainCtrl'
@@ -120,8 +120,21 @@ public class UserGroupControllerTest {
String content = result.getResponse().getContentAsString();
ObjectMapper objectMapper = new ObjectMapper();
List<Map> checkerList = objectMapper.readValue(content, List.class);
Assert.assertEquals(checkerList.size(), 2);
List<Map> userGroupList = objectMapper.readValue(content, List.class);
Assert.assertEquals(userGroupList.size(), 2);
}
@Test
public void selectUserGroupByUserGroupId() throws Exception {
MvcResult result = this.mockMvc.perform(get("/userGroup.pinpoint?userGroupId=" + TEST_USER_GROUP_ID).contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isOk())
.andExpect(content().contentType("application/json;charset=UTF-8"))
.andReturn();
String content = result.getResponse().getContentAsString();
ObjectMapper objectMapper = new ObjectMapper();
List<Map> userGroupList = objectMapper.readValue(content, List.class);
Assert.assertEquals(userGroupList.size(), 2);
}
@Test
@@ -19,5 +19,16 @@ public class MemoryUserGroupDaoTest {
assertEquals(userGroupDao.selectUserGroupByUserId("user1").size(), 2);
}
@Test
public void selectUserGroupByUserGroupId() {
MemoryUserGroupDao userGroupDao = new MemoryUserGroupDao();
userGroupDao.createUserGroup(new UserGroup("1", "userGroup1"));
userGroupDao.createUserGroup(new UserGroup("2", "userGroup2"));
userGroupDao.insertMember(new UserGroupMember("userGroup1", "user1"));
userGroupDao.insertMember(new UserGroupMember("userGroup2", "user1"));
assertEquals(userGroupDao.selectUserGroupByUserGroupId("Group").size(), 2);
}
}