You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@wicket.apache.org by sv...@apache.org on 2021/08/20 17:45:39 UTC
[wicket] 01/01: WICKET-6913 replace proxies with StandardMBean
This is an automated email from the ASF dual-hosted git repository.
svenmeier pushed a commit to branch jmx-standardmbean-instead-proxy
in repository https://gitbox.apache.org/repos/asf/wicket.git
commit c776f4d922b6ecd704f846748d488942d5b87ec2
Author: Sven Meier <sv...@apache.org>
AuthorDate: Fri Aug 20 19:34:33 2021 +0200
WICKET-6913 replace proxies with StandardMBean
---
.../java/org/apache/wicket/jmx/Initializer.java | 160 +++++++--------------
1 file changed, 54 insertions(+), 106 deletions(-)
diff --git a/wicket-jmx/src/main/java/org/apache/wicket/jmx/Initializer.java b/wicket-jmx/src/main/java/org/apache/wicket/jmx/Initializer.java
index 181f293..bb89f78 100644
--- a/wicket-jmx/src/main/java/org/apache/wicket/jmx/Initializer.java
+++ b/wicket-jmx/src/main/java/org/apache/wicket/jmx/Initializer.java
@@ -17,11 +17,11 @@
package org.apache.wicket.jmx;
import java.lang.management.ManagementFactory;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.List;
+import javax.management.Attribute;
+import javax.management.AttributeList;
import javax.management.InstanceAlreadyExistsException;
import javax.management.InstanceNotFoundException;
import javax.management.MBeanRegistrationException;
@@ -30,17 +30,7 @@ import javax.management.MBeanServerFactory;
import javax.management.MalformedObjectNameException;
import javax.management.NotCompliantMBeanException;
import javax.management.ObjectName;
-
-import net.bytebuddy.ByteBuddy;
-import net.bytebuddy.NamingStrategy;
-import net.bytebuddy.TypeCache;
-import net.bytebuddy.description.type.TypeDescription;
-import net.bytebuddy.dynamic.loading.ClassLoadingStrategy;
-import net.bytebuddy.implementation.MethodDelegation;
-import net.bytebuddy.implementation.bind.annotation.AllArguments;
-import net.bytebuddy.implementation.bind.annotation.Origin;
-import net.bytebuddy.implementation.bind.annotation.RuntimeType;
-import net.bytebuddy.matcher.ElementMatchers;
+import javax.management.StandardMBean;
import org.apache.wicket.IInitializer;
import org.apache.wicket.ThreadContext;
@@ -78,15 +68,6 @@ public class Initializer implements IInitializer
{
private static final Logger LOG = LoggerFactory.getLogger(Initializer.class);
- /**
- * A cache used to store the dynamically generated classes by ByteBuddy.
- * Without this cache a new class will be generated for each proxy creation
- * and this will fill up the metaspace
- */
- private static final TypeCache<TypeCache.SimpleKey> DYNAMIC_CLASS_CACHE = new TypeCache.WithInlineExpunction<>(TypeCache.Sort.SOFT);
-
- private static final ByteBuddy BYTE_BUDDY = new ByteBuddy();
-
// It's best to store a reference to the MBeanServer rather than getting it
// over and over
private MBeanServer mbeanServer = null;
@@ -246,102 +227,69 @@ public class Initializer implements IInitializer
* @throws MBeanRegistrationException
* @throws InstanceAlreadyExistsException
*/
- private void register(final org.apache.wicket.Application application, final Object o,
+ private <T> void register(final org.apache.wicket.Application application, final T o,
final ObjectName objectName) throws InstanceAlreadyExistsException,
MBeanRegistrationException, NotCompliantMBeanException
{
- Object proxy = createProxy(application, o);
- mbeanServer.registerMBean(proxy, objectName);
- registered.add(objectName);
- }
-
- // must be public to prevent JMX Server throwing:
- // failed to access class org.apache.wicket.jmx.Initializer$Interceptor from class org.apache.wicket.jmx.Application
- public static class Interceptor
- {
- private final org.apache.wicket.Application application;
- private final Object object;
-
- private Interceptor(org.apache.wicket.Application application, Object object) {
- this.application = application;
- this.object = object;
- }
-
- @RuntimeType
- public Object intercept(final @Origin Method method,
- final @AllArguments Object[] args)
- throws Throwable
- {
- boolean existed = ThreadContext.exists();
-
- if (existed == false)
+ StandardMBean bean = new StandardMBean(o, (Class<T>)o.getClass().getInterfaces()[0]) {
+ @Override
+ public Object getAttribute(String attribute)
{
- ThreadContext.setApplication(application);
+ return withApplication(() -> super.getAttribute(attribute));
}
-
- try
+
+ @Override
+ public void setAttribute(Attribute attribute)
+ {
+ withApplication(() -> {
+ super.setAttribute(attribute);
+ return null;
+ });
+ }
+
+ @Override
+ public AttributeList setAttributes(AttributeList attributes)
{
- return method.invoke(object, args);
+ return withApplication(() -> super.setAttributes(attributes));
}
- finally
+
+ @Override
+ public Object invoke(String actionName, Object[] params, String[] signature)
{
+ return withApplication(() -> super.invoke(actionName, params, signature));
+ }
+
+ private <R> R withApplication(Invocation<R> invocation)
+ {
+ boolean existed = ThreadContext.exists();
+
if (existed == false)
{
- ThreadContext.detach();
+ ThreadContext.setApplication(application);
}
- }
- }
- }
-
- private Object createProxy(final org.apache.wicket.Application application, final Object o)
- {
- final Class<?> type = o.getClass();
- final ClassLoader classLoader = resolveClassLoader();
-
- Class<?> proxyClass = DYNAMIC_CLASS_CACHE.findOrInsert(classLoader,
- new TypeCache.SimpleKey(type),
- () -> BYTE_BUDDY
- .with(new NamingStrategy.AbstractBase()
- {
- @Override
- protected String name(TypeDescription superClass)
- {
- return type.getName().replace(".wrapper", "");
- }
- })
- .subclass(Object.class)
- .implement(type.getInterfaces())
- .method(ElementMatchers.any())
- .intercept(MethodDelegation.to(new Interceptor(application, o)))
- .make()
- .load(classLoader, ClassLoadingStrategy.Default.INJECTION)
- .getLoaded());
-
- try
- {
- return proxyClass.getDeclaredConstructor().newInstance();
- }
- catch (InstantiationException | IllegalAccessException | InvocationTargetException | NoSuchMethodException e)
- {
- throw new WicketRuntimeException(e);
- }
+ try
+ {
+ return invocation.invoke();
+ }
+ catch (Exception ex)
+ {
+ throw new WicketRuntimeException(ex);
+ }
+ finally
+ {
+ if (existed == false)
+ {
+ ThreadContext.detach();
+ }
+ }
+ }
+ };
+ mbeanServer.registerMBean(bean, objectName);
+ registered.add(objectName);
}
- private static ClassLoader resolveClassLoader()
- {
- ClassLoader classLoader = null;
- if (org.apache.wicket.Application.exists())
- {
- classLoader = org.apache.wicket.Application.get().getApplicationSettings()
- .getClassResolver().getClassLoader();
- }
-
- if (classLoader == null) {
- classLoader = Thread.currentThread().getContextClassLoader();
- }
-
- return classLoader;
+ private static interface Invocation<R> {
+ R invoke() throws Exception;
}
-
-}
+}
\ No newline at end of file