2010-04-16 7 views
6

Supongamos que tengo una clase singleton en una lib externa a mi aplicación. Pero aún puedo crear instancias de esa clase en particular usando reflexión. Me gusta estoFramework de reflexión de Java y seguridad

Class clas = Class.forName(Private.class.getName()); 

    for(Constructor c : clas.getDeclaredConstructors()){ 
     c.setAccessible(true); 
     Private p = (Private) c.newInstance(); 
     System.out.println(p); 
    } 

¿Cómo puedo restringir esto? .

Gracias J

+0

Ah los dolores de embarazos únicos .. –

+2

Consulte también: http://stackoverflow.com/questions/2481862/how-to-limit-setaccessible-to-only-legitimate-uses – polygenelubricants

Respuesta

6

Mediante el uso de un SecurityManager y controlar controlando ReflectPermission("suppressAccessChecks") (example).

Las actuaciones afecta a la seguridad del gestor embargo, y rara vez se utiliza en el lado del servidor.

+0

[¿Qué tan grande es el ¿impacto en el rendimiento?] (http://stackoverflow.com/questions/14903423/security-manager-rarely-used-on-server) –

0

Larga historia corta: no se puede.

Cualquier constructor, públicos como privados, se puede acceder por la reflexión y se puede utilizar para crear instancias de un objeto nuevo.

Tendrá que recurrir a otros métodos, como SecurityManager.

0

No creo que pueda restringir esto.

Evidentemente, es una práctica peligrosa/cuestionable usar el reflejo para acceder a las partes privadas de los demás (snicker), pero a veces es necesario por varios tipos de herramientas y aplicaciones.

1

Si estamos hablando de embarazos únicos, en particular: que es una razón por la mejor manera de ponerlas en práctica es a través de una enumeración:

public enum YourSingleton { 
    INSTANCE; 
    // methods go here 
} 

si estamos hablando acerca del uso de setAccessible() en general: Si el código está escrito por alguien en quien no confías para no hacer trucos de esa manera, no debes ejecutarlo de todos modos (o ejecutarlo en una caja de arena). Entre los desarrolladores, público/privado debe considerarse una metainformación sobre cómo se pretende usar el código, no como una característica de seguridad.

0

Aparentemente, este es una especie de metaprogramming y por lo tanto requiere verificación en diferentes capas de abstracción. Desde Javadoc, supongo que debe usar SecurityManager para aplicar el comportamiento que desee: setAccessible(). Generalmente, en mi humilde opinión, realmente debería saber lo que está haciendo cuando está metaprogramando y cambiar el acceso en realidad debería tener buenas razones para hacerlo.

0

Puede hacer de esta manera.

private static final Private INSTANCE = new Private(); 
    private Private() { 
     if(INSTANCE !=null) 
      throw new IllegalStateException("Already instantiated"); 
    } 
    public static Private getInstance() { 
      return INSTANCE; 
     } 
+0

El singleton está fuera de su alcance en un contenedor de terceros. Entonces esto no ayudará en absoluto. Por cierto, esta técnica no es segura, ya que puede cambiarla a través de la reflexión (como se menciona en la pregunta). – whiskeysierra

Cuestiones relacionadas