Consider this example :
import java.lang.reflect.Field;
public class Test {
public static void main(String[] args) {
C c = new C();
try {
Field f = C.class.getDeclaredField("a");
f.setAccessible(true);
Integer i = (Integer)f.get(c);
System.out.println(i);
} catch (Exception e) {}
}
}
class C {
private Integer a =6;
}
It seems illogical that you are allowed to access private fields of classes with reflection. Why is such a functionality available? Isn't it "dangerous" to allow such access?
Both
getDeclaredField()
andsetAccessible()
are actually checked by the security manager and will throw an exception when your code is not allowed to do this. More often than not you won't notice it, because Java code is often run without a security manager.One important exception are Applets, which always run with a security manager.
From the description of the
java.lang.reflect
package:Reflection provides a mechanism for accessing information about classes through means which are usually not available by regular interaction between classes and objects. One of such is allowing access to private fields from outside classes and objects.
Yes, reflection in general can indeed be dangerous, as it can expose the internals of classes and objects.
However, it also is a very powerful tool that can be used to inspect the internals of classes and objects, which can't be accessed by other standard means.
Reflection is dangerous. Period.
What's the point in limiting the utility of a really dangerous system for the sake of ever so slightly increased safety?
Also, automated serialization requires the ability to "suck the brains" out of any class; ignoring access modifiers is a necessity in this case.
Yes it's not nice but it does allow frameworks such as Java Serialization to work.
I beleive that the functionality can be disabled through the
SecurityManager
http://javabeans.asia/2008/10/12/how_to_set_securitymanager_and_java_security_policy_programmatically.html
Private is intended to prevent accidental misuse, not as a security mechanism. If you choose to bypass it then you can do so at your own risk and the assumption you know what you are doing.
Reflection is a complete API for getting inside classes. Private members and all.
In cases where you don't trust the code you're running (applets and the like) you can prevent the code from using reflection at all. See this Stack Overflow question for details.