use of org.hotswap.agent.plugin.owb.command.BeanClassRefreshCommand in project HotswapAgent by HotswapProjects.
the class OwbPlugin method classReload.
/**
* Called on class redefinition. Class may be bean class
*
* @param classLoader the class loader in which class is redefined (Archive class loader)
* @param ctClass the ct class
* @param original the original
*/
@OnClassLoadEvent(classNameRegexp = ".*", events = LoadEvent.REDEFINE)
public void classReload(ClassLoader classLoader, CtClass ctClass, Class<?> original) {
if (classLoader != appClassLoader) {
LOGGER.debug("Attempt to redefine class '{}' in unsupported classLoader{}.", original.getName(), classLoader);
return;
}
if (original == null || isSyntheticCdiClass(ctClass.getName()) || isInnerNonPublicStaticClass(ctClass)) {
if (original != null) {
LOGGER.trace("Skipping synthetic or inner class {}.", original.getName());
}
return;
}
try {
String classUrl = ctClass.getURL().toExternalForm();
Iterator<Entry<URL, URL>> iterator = registeredArchives.entrySet().iterator();
while (iterator.hasNext()) {
Entry<URL, URL> entry = iterator.next();
if (classUrl.startsWith(entry.getKey().toExternalForm())) {
LOGGER.debug("Class '{}' redefined in classLoader {}.", original.getName(), classLoader);
String oldSignForProxyCheck = OwbClassSignatureHelper.getSignatureForProxyClass(original);
String oldSignByStrategy = OwbClassSignatureHelper.getSignatureByStrategy(beanReloadStrategy, original);
scheduler.scheduleCommand(new BeanClassRefreshCommand(appClassLoader, original.getName(), oldSignForProxyCheck, oldSignByStrategy, entry.getValue(), beanReloadStrategy), WAIT_ON_REDEFINE);
break;
}
}
} catch (Exception e) {
LOGGER.error("classReload() exception {}.", e, e.getMessage());
}
}
use of org.hotswap.agent.plugin.owb.command.BeanClassRefreshCommand in project HotswapAgent by HotswapProjects.
the class OwbPlugin method registerBeansXmls.
/**
* Register BeanArchive's paths to watcher. In case of new class the class file is not known
* to JVM hence no hotswap is called and therefore it must be handled by watcher.
*
* @param bdaLocations the Set of URLs of archive locations
*/
public void registerBeansXmls(Set bdaLocations) {
// for all application resources watch for changes
for (final URL beanArchiveUrl : (Set<URL>) bdaLocations) {
String beansXmlPath = beanArchiveUrl.getPath();
if (!beansXmlPath.endsWith("beans.xml")) {
LOGGER.debug("Skipping bda location: '{}' ", beanArchiveUrl);
continue;
}
final String archivePath;
if (beansXmlPath.endsWith("META-INF/beans.xml")) {
archivePath = beansXmlPath.substring(0, beansXmlPath.length() - "META-INF/beans.xml".length());
} else if (beansXmlPath.endsWith("WEB-INF/beans.xml")) {
archivePath = beansXmlPath.substring(0, beansXmlPath.length() - "beans.xml".length()) + "classes";
} else {
LOGGER.warning("Unexpected beans.xml location '{}'", beansXmlPath);
continue;
}
if (archivePath.endsWith(".jar!/")) {
LOGGER.debug("Skipping unsupported jar beans.xml location '{}'", beansXmlPath);
continue;
}
// store path for unit tests (single archive expected)
OwbPlugin.archivePath = archivePath;
try {
URL archivePathUrl = resourceNameToURL(archivePath);
if (registeredArchives.containsKey(archivePathUrl)) {
continue;
}
registeredArchives.put(archivePathUrl, beanArchiveUrl);
URI uri = archivePathUrl.toURI();
watcher.addEventListener(appClassLoader, uri, new WatchEventListener() {
@Override
public void onEvent(WatchFileEvent event) {
if (event.isFile() && event.getURI().toString().endsWith(".class")) {
// check that the class is not loaded by the classloader yet (avoid duplicate reload)
String className;
try {
className = IOUtils.urlToClassName(event.getURI());
} catch (IOException e) {
LOGGER.trace("Watch event on resource '{}' skipped, probably Ok because of delete/create event sequence (compilation not finished yet).", e, event.getURI());
return;
}
if (!ClassLoaderHelper.isClassLoaded(appClassLoader, className) || isTestEnvironment) {
// refresh weld only for new classes
LOGGER.trace("register reload command: {} ", className);
scheduler.scheduleCommand(new BeanClassRefreshCommand(appClassLoader, archivePath, beanArchiveUrl, event), WAIT_ON_CREATE);
}
}
}
});
LOGGER.info("Registered watch for path '{}' for changes.", archivePathUrl);
} catch (URISyntaxException e) {
LOGGER.error("Unable to watch path '{}' for changes.", e, archivePath);
} catch (Exception e) {
LOGGER.warning("registerBeanDeplArchivePath() exception : {}", e.getMessage());
}
}
}
Aggregations