Мы создаем несколько дочерних загрузчиков классов для загрузки в несколько субприложений в Java-приложение "контейнер", прототипирование горячего развертывания. Когда переменная classpath для определенного загрузчика классов была изменена (т.е. Баночки были добавлены, удалены, обновлены), старый загрузчик классов отбрасывается (не привязывается) и создается новый загрузчик классов для нового класса маршрутов jars.
После обновления пути к классам, запускающего горячее развертывание, мы взяли кучу кучи. Дамп кучи (с использованием Memory Analyzer) указывает, что старые загрузчики классов не собирались мусором. Некоторые классы в родительском загрузчике классов кэшировали старые загрузчики классов. Для очистки этих кешей были использованы следующие действия:
java.lang.ResourceBundle.clearCache(classLoader);
org.apache.commons.logging.LogFactory.release(classLoader);
java.beans.Introspector.flushCaches();
Даже после очистки указанных кешей старый загрузчик классов по-прежнему не собирался сбор мусора. Остальные ссылки на загрузчик классов включали следующее:
- классы, загруженные загрузчиком классов
- java.lang.Package, созданный самим загрузчиком классов
- java.lang.ProtectionDomain, созданный самим загрузчиком классов
Все вышеперечисленное относится к циклическим ссылкам в загрузчике классов, что должно приводить к сбору мусора. Я не уверен, почему это не так. Кто-нибудь знает, почему старые загрузчики классов по-прежнему не собираются мусором даже с круговыми ссылками?