Invocar método privado con java.lang.invoke.MethodHandle

¿Cómo puedo invocar un método privado usando manejadores de métodos?

Hasta donde puedo ver, solo hay dos tipos de Lookupinstancias de acceso público :

  • MethodHandles.lookup()
  • MethodHandles.publicLookup()

y ninguno permite el acceso privado sin restricciones.

Hay lo no público Lookup.IMPL_LOOKUP que hace lo que quiero. ¿Hay alguna forma pública de obtenerlo (suponiendo que SecurityManager lo permita)?

Respuesta 1

Resulta que es posible con Lookup # irreflect (Method) y temporalmente haciendo que el método sea accesible (potencialmente introduciendo un pequeño problema de seguridad a menos que se haga durante la inicialización del programa).

Aquí está el método principal modificado de la respuesta de Thorben:

public static void main(String[] args) {

    Lookup lookup = MethodHandles.lookup();
    NestedTestClass ntc = new Program().new NestedTestClass();

    try {
        // Grab method using normal reflection and make it accessible
        Method pm = NestedTestClass.class.getDeclaredMethod("gimmeTheAnswer");
        pm.setAccessible(true);

        // Now convert reflected method into method handle
        MethodHandle pmh = lookup.unreflect(pm);
        System.out.println("reflection:" + pm.invoke(ntc));

        // We can now revoke access to original method
        pm.setAccessible(false);

        // And yet the method handle still works!
        System.out.println("handle:" + pmh.invoke(ntc));

        // While reflection is now denied again (throws exception)
        System.out.println("reflection:" + pm.invoke(ntc));

    } catch (Throwable e) {
        e.printStackTrace();
    }

}
Respuesta: 2

Acabo de encontrarme con este tipo de situación mientras desarrollaba una aplicación de Android hoy en la que se me exigía que representara gráficos basados ​​en las respuestas de 2 API diferentes. Estoy usando Volley y lo que yo ...

Necesito abrir un símbolo del sistema desde el código de Java y ejecutar algunos comandos en el mismo y después de eso necesito leer esa salida del símbolo del sistema en código Java en tiempo real. He intentado con el siguiente código pero yo ...

Estoy tratando de ejecutar varias herramientas en un servidor Windows Tomcat. El servidor comienza bien, y también puedo ver la página del administrador de Tomcat. Pero cuando abro una herramienta, aparece un "OutOfMemoryError: espacio PermGen". ...

¿Puedo llamar a un método estático desde un inicializador estático en Java? ¿Es válido y está garantizado que lo siguiente funcione según la especificación Java? public class Foo {private int static int bar; ...