Это обзорная страница. Для получения дополнительной информации посетите hotswapagent.org.
Java неограниченный класс времени выполнения и переопределение ресурсов.
Основная цель этого проекта заключалась в устранении необходимости традиционного цикла разработки «изменить код -> перезапустить и подождать... -> проверить». Со временем эта концепция превратилась в новую парадигму в экосистеме Java, позволяющую разрабатывать программное обеспечение в режиме реального времени в рамках работающего приложения. Этот подход возможен даже в ограниченных средах, таких как контейнеры Docker.
Если вы являетесь пользователем IntelliJ, вы можете упростить настройку HA и DCEVM, используя плагин IntelliJ HotSwapHelper.
Загрузите и установите:
Для Java 17/21: загрузите последнюю версию JBR17 или JBR21. Поскольку эти версии не включают встроенный агент Hotswap, вам придется вручную скопировать hotswap-agent.jar
в папку lib/hotswap
. Вы можете найти последнюю версию агента Hotswap здесь. Убедитесь, что файл в папке lib/hotswap
называется hotswap-agent.jar
без номеров версий в имени файла.
Для Java 11: используйте TravaJDK со встроенным агентом HotswapAgent и установите его в качестве альтернативы JDK. Альтернативно, TravaJDK включает встроенный HotswapAgent.
Для Java 8: используйте jdk8-dcevm вместе с HotswapAgent.
Режимы агента горячей замены:
Начиная с dcevm-11.0.9
HotswapAgent по умолчанию отключен. Вы можете включить поддержку HotswapAgent с помощью параметров JVM в одном из трех режимов:
Режим HotswapAgent=core
работает без дополнительных плагинов, за исключением основных плагинов JVM, что приводит к повышению производительности за счет сокращения задач сканирования и копирования классов. Чтобы использовать дополнительные плагины, вам необходимо настроить их как зависимости Maven в файле pom.xml
. С другой стороны, режим HotswapAgent=fatjar
по умолчанию включает все плагины, что может немного замедлить запуск приложения.
-XX:HotswapAgent=fatjar
активирует внутренний Fatjar HotswapAgent.
-XX:HotswapAgent=core
активирует внутренний основной HotswapAgent.
-XX:HotswapAgent=external
настраивает поддержку JVM для HotswapAgent и позволяет пользователю предоставить внешний hotswap-agent.jar
с помощью параметра -javaagent:
.
3. Запуск:
Java17/21: запустите приложение с параметрами -XX:+AllowEnhancedClassRedefinition -XX:HotswapAgent=fatjar
чтобы включить расширенную горячую замену (dcevm) и использовать версию Fatjar агента Hotswap Agent. В качестве альтернативы можно использовать core
или external
моды вместо fatjar
.
Java11: запустите приложение с параметрами -XX:HotswapAgent=fatjar
чтобы использовать версию Fatjar агента Hotswap.
Java8: запустите приложение с параметрами -XXaltjvm=dcevm -javaagent:hotswap-agent.jar
чтобы выполнить базовую настройку. При желании вы можете добавить hotswap-agent.properties
в свое приложение, чтобы настроить плагины и поведение агента.
3. Запустите приложение:
Запустите приложение в режиме отладки, проверьте правильность инициализации агента и плагинов:
HOTSWAP AGENT: 9:49:29.548 INFO (org.hotswap.agent.HotswapAgent) - Loading Hotswap agent - unlimited runtime class redefinition. HOTSWAP AGENT: 9:49:29.725 INFO (org.hotswap.agent.config.PluginRegistry) - Discovered plugins: [org.hotswap.agent.plugin.hotswapper.HotswapperPlugin, org.hotswap.agent.plugin.jvm.AnonymousClassPatchPlugin, org.hotswap.agent.plugin.hibernate.HibernatePlugin, org.hotswap.agent.plugin.spring.SpringPlugin, org.hotswap.agent.plugin.jetty.JettyPlugin, org.hotswap.agent.plugin.tomcat.TomcatPlugin, org.hotswap.agent.plugin.zk.ZkPlugin, org.hotswap.agent.plugin.logback.LogbackPlugin] ... HOTSWAP AGENT: 9:49:38.700 INFO (org.hotswap.agent.plugin.spring.SpringPlugin) - Spring plugin initialized - Spring core version '3.2.3.RELEASE'
4.Проверьте переопределение
Сохраните измененный ресурс и/или используйте функцию HotSwap вашей IDE для перезагрузки изменений.
Каждой платформе приложения (Spring, Hibernate, Logback,...) необходим специальный механизм перезагрузки, чтобы поддерживать актуальность после переопределения класса (например, перезагрузка конфигурации Hibernate после введения нового класса сущности). Агент Hotswap работает как система плагинов и поставляется предварительно настроенным со всеми основными плагинами платформы. Написать собственный плагин легко, даже как часть вашего приложения.
Этот проект очень сложен из-за множества поддерживаемых фреймворков и различных версий. Вклад сообщества является обязательным для поддержания его существования. Вы можете начать с создания плагина внутри вашего приложения или написания примера/интеграционного теста. Всегда есть необходимость в улучшении документации :-). Спасибо за любую помощь!
Расширенная горячая замена Java — изменение тела метода, добавление/переименование метода, поля и т. д. Единственная неподдерживаемая операция — изменение суперкласса.
Вы можете использовать стандартную Java Hotswap из IDE в режиме отладки, чтобы перезагрузить измененный класс.
или установите свойство autoHotswap -XXaltjvm=dcevm -javaagent:PATH_TO_AGENThotswap-agent.jar=autoHotswap=true
чтобы перезагрузить измененные классы после компиляции. Эта настройка позволяет даже перезагрузить производственную систему без перезагрузки.
Автоматическая конфигурация — все локальные классы и ресурсы, известные работающему Java-приложению, автоматически обнаруживаются и отслеживаются на предмет перезагрузки (все файлы в локальной файловой системе, а не внутри какого-либо файла JAR).
Дополнительный путь к классам. Нужно изменить класс времени выполнения внутри зависимого JAR? Используйте свойство extraClasspath, чтобы добавить любой каталог в качестве пути к классам для отслеживания файлов классов.
Перезагрузить ресурс после изменения — ресурсы из каталога веб-приложения обычно перезагружаются сервером приложений. А как насчет других ресурсов, таких как src/main/resources? Используйте свойство watchResources, чтобы добавить любой каталог для отслеживания изменений ресурса.
Поддержка фреймворков — через систему плагинов поддерживаются многие фреймворки. Новые плагины могут быть легко добавлены.
Быстро — до тех пор, пока плагин не будет инициализирован, он не потребляет никаких ресурсов и не замедляет работу приложения (дополнительную информацию см. в разделе «Накладные расходы во время выполнения»).
Если у вас возникнут какие-либо проблемы или вопросы, задайте их на форуме HotswapAgent.
Этот проект похож на JRebel. Основные различия:
HotswapAgent (DCEVM) поддерживает Java8, Java11 и Java17!
HotswapAgent не требует дополнительной настройки для базовой настройки проекта.
JRebel в настоящее время более зрелый и содержит больше плагинов.
JRebel не является ни открытым исходным кодом, ни бесплатным.
JRebel изменяет байт-код всех классов при перезагрузке. Для исправления отладки вам понадобится специальный плагин IDE.
HotswapAgent extraClasspath аналогичен конфигурации JRebel.
HotswapAgent добавляет конфигурацию watchResources
См. проект HotswapAgentExamples на GitHub. Цель примера приложения:
сложные автоматизированные интеграционные тесты (проверка различных конфигураций перед выпуском, см. скрипт run-tests.sh
)
для проверки использования плагина «реального мира» во время разработки плагина (т. е. внутри контейнера)
предоставить работающее решение для типичных настроек приложений
песочница для моделирования проблем существующих или новых настроек
Не стесняйтесь разветвлять/разветвлять и создавать приложение для вашей установки (функциональное, но максимально простое). Общие настройки будут объединены в основные.
Ничего не нужно :) Действительно! Все изменения прозрачны, и все, что вам нужно сделать, это загрузить патч + агент и настроить свое приложение/сервер приложений. Поскольку мы используем стандартное поведение горячей замены Java, ваша IDE будет работать должным образом. Однако мы работаем над плагинами IDE, которые помогут с загрузкой и настройкой.
Некоторые плагины уже доступны:
Добавьте два действия рядом с кнопкой «Отладка» в intellij: «Запуск с горячей заменой», «Отладка с горячей заменой».
При нажатии на действие параметры виртуальной машины будут установлены для вас, нет необходимости устанавливать параметры виртуальной машины вручную.
Исходный код и документация: https://github.com/gejun123456/HotSwapHelper.
Базовая конфигурация настроена на перезагрузку классов и ресурсов из пути к классам, известного работающему приложению (загрузчику классов). Если вам нужна другая конфигурация, добавьте файл hotswap-agent.properties в корень пути к классам (например, src/main/resources/hotswap-agent.properties
).
Подробную документацию о доступных свойствах и значениях по умолчанию можно найти в файле свойств агента.
Полный синтаксис параметров командной строки:
-javaagent:[yourpath/]hotswap-agent.jar=[option1]=[value1],[option2]=[value2]
Агент горячей замены принимает следующие параметры:
autoHotswap=true — отслеживать все файлы .class на наличие изменений и автоматически выполнять горячую замену класса в работающем приложении (вместо запуска Hotswap из сеанса отладки IDE).
DisablePlugin=[pluginName] — отключить плагин. Обратите внимание, что это полностью запретит загрузку плагина (в отличие от параметра DisablePlugin в hotswap-agent.properties, который отключит плагин только для загрузчика классов. Вы можете повторить эту опцию для каждого отключаемого плагина.
Добавьте опцию vm -Dhotswapagent.disablePlugin=Spring,SpringBoot для отключения плагинов, работает так же, как опция агента DisablePlugin в предыдущем разделе.
Агент горячей замены выполняет работу по перезагрузке ресурсов и конфигурации платформы (Spring, Hibernate,...), но перезагрузка классов зависит от стандартного механизма горячей замены Java. Стандартная горячая замена Java допускает только изменение тела метода, что делает ее практически непригодной для использования. DCEVM — это патч JVM (Hotspot), который позволяет практически любое изменение структурного класса при горячей замене (за исключением изменения иерархии). Хотя агент горячей замены работает даже со стандартной Java, мы рекомендуем использовать DCEVM (и во всех руководствах DCEVM используется в качестве целевой JVM).
Агент Hotswap — это контейнер плагинов с менеджером плагинов, реестром плагинов и несколькими службами агента (например, для отслеживания изменений класса/ресурса). Это помогает решать общие задачи и проблемы с загрузкой классов. Он сканирует путь к классам в поисках класса, помеченного аннотацией @Plugin, внедряет службы агента и регистрирует перехватчики перезагрузки. Модификация байт-кода во время выполнения обеспечивается библиотекой javaasist.
Плагины, администрируемые агентом Hotswap, обычно ориентированы на конкретную платформу. Например, плагин Spring использует службы высокой доступности для:
Измените корневые классы Spring, чтобы получить контексты Spring и зарегистрированный путь сканирования.
Следите за любыми изменениями ресурсов на пути сканирования.
Следите за горячей заменой файла класса в пакете пути сканирования.
Перезагрузить определение компонента после изменения
... и многие другие
CXF-JAXRS (3.x) — переопределить ресурс JAXRS после переопределения класса ресурса, повторно внедрить экземпляр, если он интегрирован со Spring и CDI (Weld/OWB).
Deltaspike (1.x,2.x) — сообщения, ViewConfig, репозиторий, перезагрузка прокси. Deltaspike провел повторное внедрение компонентов CDI.
ELResolver (2.x-5.x) (JuelEL, Appache Commons EL, Oracle EL 3.0) — очищать кеш ELResolver при смене класса. Поддержка горячей замены для выражений #{...}.
FreeMarker — очистка кэша интроспекции классов компонентов Apache Freemarker при изменении определения класса.
Hibernate (3.x-6.x) — перезагрузите конфигурацию Hibernate после создания/изменения объекта.
iBatis - перезагрузка конфигурации iBatis.
IDEA — поддержка разработки IntelliJ IDEA в IDEA.
Джексон — очищает внутренние кэши Джексона при переопределении класса.
Jersey1 — перезагрузить контейнер Jersey1 после определения или переопределения корневого ресурса или класса поставщика.
Jersey2 — перезагрузить контейнер Jersey2 после определения или переопределения корневого ресурса или класса поставщика.
Logback — перезагрузка конфигурации журнала.
Log4j2 — перезагрузка конфигурации Log4j2.
Mojarra (2.x) — поддержка изменений пакета ресурсов приложения (файл свойств). Поддержка повторного внедрения/перезагрузки bean-компонентов ViewScoped.
MyBatis (5.3) — перезагрузить конфигурацию после изменения файла картографа
MyFaces (2.x-4.x) — поддержка изменений пакетов ресурсов приложения (файлов свойств). Поддержка повторного внедрения/перезагрузки bean-компонентов ViewScoped.
OmniFaces — поддержка повторного внедрения/перезагрузки bean-компонентов ViewScoped.
OpenWebBeans - (CDI) (1.x-4.x) - перезагрузить определение класса компонента после определения/изменения класса. Компоненты могут быть перезагружены в соответствии со стратегией, определенной в файле свойств.
OsgiEquinox — поддержка горячей замены для плагинов Eclipse или разработки платформы Eclipse.
RestEasy (2.x, 3.x) — очищает и регистрирует переопределения классов.
Spring (3.2.x+, 4.x, 5.x) — перезагрузить конфигурацию Spring после определения/изменения класса.
Spring Boot (1.5.x+, 2.0.x) — динамическая перезагрузка файлов конфигурации Spring Boot в режиме реального времени.
Vaadin (23.x, 24.x) — обновление маршрутов, моделей шаблонов и всего остального на лету.
WebObjects — очищайте кэши кодирования значений ключей, компонентов, действий и проверок после изменения класса.
Weld (CDI) (2.x-5.x) — перезагрузка определения класса компонента после определения/изменения класса. Компоненты могут быть перезагружены в соответствии со стратегией, определенной в файле свойств.
Калитка — очищать кэши калиток, если файлы свойств изменяются.
WildFlyELResolver — очищает BeanELResolver после любого переопределения класса.
ZK (5x-7x) — ZK Framework (http://www.zkoss.org/). Измените значения свойств библиотеки по умолчанию, чтобы отключить кеши, сохранить кеш меток и кеш преобразователя компонентов.
JBossModules — добавьте дополнительный путь к классу загрузчика классов модулей JBoss. (Дикая муха)
Jetty — добавьте дополнительный путь к классам в загрузчик классов приложения. Должны поддерживаться все версии, поддерживающие WebAppContext.getExtraClasspath.
Tomcat (7.x,8.x,9.x,10.x) настройте Apache Tomcat с помощью extraClasspath и свойства webApp. Поддерживает также GlassFish, Payara и Tomee7.
Undertow — добавьте дополнительный путь к классам, watchResources и webappDir в менеджер ресурсов Undertow.
Weblogic — добавьте дополнительный путь к классам в загрузчик классов приложения.
AnonymousClassPatch — поменяйте местами имена анонимных внутренних классов, чтобы избежать несовместимых изменений.
ClassInit — инициализирует новые статические члены/значения перечисления после переопределения класса/перечисления и сохраняет оставшиеся статические значения. (Исправлено известное ограничение DCEVM)
Горячая замена — отслеживайте любые изменения файлов классов и перезагружайте (горячую замену) их на лету с помощью архитектуры отладчика платформы Java (JPDA).
Прокси (поддерживается com.sun.proxy, CGlib) — переопределяет прокси-классы, которые реализуют или расширяют измененные интерфейсы или классы.
Подробную документацию по каждому плагину можно найти в основном файле README.md проекта плагина.
Это зависит от того, сколько фреймворков вы используете и какие кеши отключены. Пример измерений для большого реального корпоративного приложения на основе Spring + Hibernate, запущенного на Jetty.
Setup | Startup time -----------------------------|------------- Run (plain Java) | 23s Debug (plain Java) | 24s Debug (plain DCEVM) | 28s Agent - disabled all plugins | 31s Agent - all plugins | 35s
Вы можете написать плагин непосредственно как часть вашего приложения. Установите pluginPackages=your.plugin.package
в конфигурации hotswap-agent.properties
, чтобы обнаружить классы с аннотациями @Plugin
. Для компиляции вам также понадобится зависимость JAR агента, но будьте осторожны и НЕ добавляйте JAR в свое приложение; он должен быть загружен только как javaagent. Зависимость Maven:
org.hotswapagent HotswapAgent ${project.version} provided
См. раздел «ExamplePlugin» (часть TestApplication), чтобы просмотреть простой плагин с комментариями. Прочтите файл readme для агента, чтобы понять концепции агента. Проверьте исходный код существующих плагинов, чтобы увидеть больше примеров.
Запустите скрипт run-tests.sh
в основном каталоге. В настоящее время вам необходимо вручную настроить каталог расположения JAVA_HOME. Перед выпуском следует проверить как минимум Java 11 с DCEVM. Все автоматические тесты настроены на провал всего сценария в случае сбоя любого отдельного теста.
Перейдите в каталог, представляющий корень репозитория. Если DCEVM называется dcevm
mvn release:prepare mvn release:perform
Агент горячей замены:
Иржи Бубник – координатор проекта, начальная реализация
Александрос Пападакис — Управление версиями Maven, Weld, JSF, Hibernate3, RestEasy, плагины WildFly
Erki Ehtla — плагин Spring, плагин прокси
Владимир Дворжак — ELResolver, OsgiEquinox, Weld, Owb, Deltaspike, Jvm, Jdk, JBossModules, ClassInit, JSF, Mybatis
Сергей Лысенко - Плагин Weld
Сэмюэль Пеллетье — плагин WebObjects
Ян Текл - веб-дизайн
@liuzhengyang — плагин Джексона
Лукаш Варжеха — плагин Log4j2
@muwaiwai — плагин iBatis
Томас Хейгл — плагин Wicket
AJ Banck — плагин FreeMarker
Синан Юмак — Модхарра, плагины MyFaces
smallfour — плагин Mybatis
@cvictory — плагин Spring, плагин Spring Boot
@homejim — плагин MyBatis, плагин MyBatisPlus
ДЦЕВМ:
Томас Вюртингер - первоначальная реализация.
Иван Дубров - бывший координатор проекта, обновление до Java7+Java8, патчи, система сборки (Gradle)
Керстин Брейтендер - автор.
Кристоф Вимбергер - участник.
Владимир Дворжак - миграция java9,java11,jbr17,jbr21, участник
Иржи Бубник - миграция java9,java11