Java 反射 API 提供 Method.setAccessible(true) 繞過訪問檢查,使得 private、default、protected 方法均可被外部調用。這正是 Hibernate、Spring 等框架實現「無侵入」注入的基石。
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
public class PrivateMethodInvoker {
public static void main(String[] args) throws Exception {
// 1. 獲取目標類 Class 對象
Class> clazz = PackageClazz.class;
// 2. 獲取私有方法(需精確匹配參數類型)
Method method = clazz.getDeclaredMethod("privilegedMethod", String.class, String.class);
// 3. 關鍵步驟:暴力反射,繞過訪問檢查
method.setAccessible(true);
// 4. 調用:第一個參數傳實例對象(非靜態方法)
method.invoke(new PackageClazz(), "452345234", "q31234132");
}
}
class PackageClazz {
private void privilegedMethod(String invokerName, String adb) {
System.out.println("---" + invokerName + "----" + adb);
}
}
| 方法 | 獲取範圍 | 繼承鏈 |
|---|---|---|
getMethod | 僅 public | 包含繼承 |
getDeclaredMethod | 所有(含 private) | 僅當前類聲明 |
有,且非常重要。
private 向開發者傳達「內部實現細節,不保證穩定,請勿依賴」。setAccessible,生產環境可禁用暴力反射。反射破解封裝屬於「核選項」,僅在框架開發、測試 Mock、舊系統整合等受控場景使用。業務代碼中若頻繁用到,請重新審視設計——或許缺少恰當的公共介面或策略模式。