Oprócz zrozumienia dostępów między modułami i ich odpowiednich pakietów. Uważam, że sedno tego leży w systemie modułowym # Relaxed-strong-encapsulation i wybrałbym tylko odpowiednie części, aby spróbować odpowiedzieć na pytanie.
Co definiuje nielegalny dostęp odblaskowy i jakie okoliczności powodują ostrzeżenie?
Aby ułatwić migrację do Java-9, można złagodzić silną enkapsulację modułów.
Implementacja może zapewniać dostęp statyczny , tj. Poprzez skompilowany kod bajtowy.
Może zapewnić sposób wywołania swojego systemu wykonawczego z jednym lub większą liczbą pakietów jednego lub więcej jego modułów otwartych na kod we wszystkich nienazwanych modułach , tj. Na kod w ścieżce klas. Jeśli system czasu wykonywania jest wywoływany w ten sposób i jeśli to zrobi, niektóre wywołania interfejsów API odbicia zakończą się powodzeniem tam, gdzie w przeciwnym razie zakończyłyby się niepowodzeniem.
W takich przypadkach faktycznie kończyło się na utworzeniu dostępu refleksyjnego, który jest „nielegalny”, ponieważ w czysto modularnym świecie nie miałeś takiego dostępu.
Jak to wszystko się układa i co powoduje ostrzeżenie w jakim scenariuszu?
To złagodzenie enkapsulacji jest kontrolowane w czasie wykonywania przez nową opcję programu uruchamiającego, --illegal-access
która domyślnie w Java9 jest równa permit
. Te permit
, zapewnia tryb
Pierwsza operacja dostępu odblaskowego do takiego opakowania powoduje wydanie ostrzeżenia, ale po tym czasie żadne ostrzeżenia nie są emitowane. To pojedyncze ostrzeżenie opisuje, jak włączyć dalsze ostrzeżenia. Tego ostrzeżenia nie można pominąć.
Tryby można konfigurować za pomocą wartości debug
(komunikat, jak również śledzenie stosu dla każdego takiego dostępu), warn
(komunikat dla każdego takiego dostępu) i deny
(wyłącza takie operacje).
Niewiele rzeczy do debugowania i naprawiania w aplikacjach to: -
- Uruchom go z,
--illegal-access=deny
aby poznać i uniknąć otwierania pakietów z jednego modułu do drugiego bez deklaracji modułu zawierającej taką dyrektywę ( opens
) lub jawnego użycia --add-opens
argumentu VM.
- Statyczne odniesienia ze skompilowanego kodu do wewnętrznych interfejsów API JDK można zidentyfikować za pomocą
jdeps
narzędzia z --jdk-internals
opcją
Komunikat ostrzegawczy generowany w przypadku wykrycia nielegalnej operacji dostępu odblaskowego ma następującą postać:
WARNING: Illegal reflective access by $PERPETRATOR to $VICTIM
gdzie:
$PERPETRATOR
jest w pełni kwalifikowaną nazwą typu zawierającą kod, który wywołał daną operację refleksyjną oraz źródło kodu (tj. ścieżkę do pliku JAR), jeśli jest dostępne, oraz
$VICTIM
jest ciągiem opisującym element członkowski, do którego uzyskiwany jest dostęp, w tym w pełni kwalifikowaną nazwą otaczającego typu
Pytania do takiego przykładowego ostrzeżenia: = JDK9: Wystąpiła nielegalna operacja dostępu odblaskowego. org.python.core.PySystemState
Ostatnia i ważna uwaga, próbując upewnić się, że nie napotkasz takich ostrzeżeń i będziesz bezpieczny w przyszłości, wszystko, co musisz zrobić, to upewnić się, że twoje moduły nie wykonują tych nielegalnych odblaskowych wejść. :)