Uploaded image for project: 'PUBLIC - Liferay Portal Community Edition'
  1. PUBLIC - Liferay Portal Community Edition
  2. LPS-67195

Hook Hot Deploy Listener fails to load DummyAntivirusScanner or ClamAntivirusScanner from hook plugin during deployment

    Details

    • Fix Priority:
      3

      Description

      Issue

      Hook Hot Deploy Listener fails to load DummyAntivirusScanner or ClamAntivirusScanner from hook plugin during deployment

      This issue was noted while investigating and resolving ticket LPANTIVIRUS-9.

      Review

      Class "com.liferay.portal.deploy.hot.HookHotDeployListener" loads portal property "dl.store.antivirus.impl" during hook plugin deployment.

      If portal property refers to Dummy Antivirus Scanner or Clam Antivirus Scanner, hook plugin deployment fails as those scanners are only available on portal class loader, not the portlet (hook) class loader.

      e.g.

      FILE: HOOK_PLUGIN/WEB-INF/classes/portal.properties

          # Use Dummy antivirus scanner
          dl.store.antivirus.impl=com.liferay.portlet.documentlibrary.antivirus.DummyAntivirusScannerImpl
      
          # --- OR ---
      
          # Use Clam antivirus scanner
          dl.store.antivirus.impl=com.liferay.portlet.documentlibrary.antivirus.ClamAntivirusScannerImpl
      

      The HookHotDeployListener uses the portletClassLoader to load a new instance of the AntivirusScanner.

      i.e.

                              // lines 1932 to 1934
      			AntivirusScanner antivirusScanner = (AntivirusScanner)newInstance(
      				portletClassLoader, AntivirusScanner.class,
      				antivirusScannerClassName);
      

      Review Class com.liferay.portal.deploy.hot.HookHotDeployListener

      CLASS: com.liferay.portal.deploy.hot.HookHotDeployListener

      package com.liferay.portal.deploy.hot;
      
      public class HookHotDeployListener
      	extends BaseHotDeployListener implements PropsKeys {
      
      
      	public static final String[] SUPPORTED_PROPERTIES = {
      . . .
      		"dl.store.antivirus.impl"
      
      
      	protected void initPortalProperties(
      			String servletContextName, ClassLoader portletClassLoader,
      			Properties portalProperties, Properties unfilteredPortalProperties)
      		throws Exception {
      
                      // . . .
      
                      //
                      // lines 1928 - 1941
                      //
      
      		if (portalProperties.containsKey(PropsKeys.DL_STORE_ANTIVIRUS_IMPL)) {
      			String antivirusScannerClassName = portalProperties.getProperty(
      				PropsKeys.DL_STORE_ANTIVIRUS_IMPL);
      
      			AntivirusScanner antivirusScanner = (AntivirusScanner)newInstance(
      				portletClassLoader, AntivirusScanner.class,
      				antivirusScannerClassName);
      
      			AntivirusScannerWrapper antivirusScannerWrapper =
      				(AntivirusScannerWrapper)
      					AntivirusScannerUtil.getAntivirusScanner();
      
      			antivirusScannerWrapper.setAntivirusScanner(antivirusScanner);
      		}
      
                      // . . .
      
            }
      }
      

      Proposed Solution

      Revise class "com.liferay.portal.deploy.hot.HookHotDeployListener" to load antivirus scanner from portlet (hook) class loader then fall back to using portal class loader.

      We could reuse the class loading logic from method "_get" in class "com.liferay.portal.kernel.util.InstancePool".

      e.g.

      			Class<?> clazz = portalClassLoader.loadClass(className);
      

      Reuse class loading logic from method "_get" in method "com.liferay.portal.kernel.util.InstancePool"

      CLASS: com.liferay.portal.kernel.util.InstancePool

      package com.liferay.portal.kernel.util;
      
      public class InstancePool {
      
              // lines 62 to 112
      	private Object _get(String className, boolean logErrors) {
      		className = className.trim();
      
      		Object instance = _instances.get(className);
      
      		if (instance != null) {
      			return instance;
      		}
      
      		ClassLoader portalClassLoader = PortalClassLoaderUtil.getClassLoader();
      
      		try {
      			Class<?> clazz = portalClassLoader.loadClass(className);
      
      			instance = clazz.newInstance();
      
      			_instances.put(className, instance);
      		}
      		catch (Exception e1) {
      			if (logErrors && _log.isWarnEnabled()) {
      				_log.warn(
      					"Unable to load " + className +
      						" with the portal class loader",
      					e1);
      			}
      
      			Thread currentThread = Thread.currentThread();
      
      			ClassLoader contextClassLoader =
      				currentThread.getContextClassLoader();
      
      			try {
      				Class<?> clazz = contextClassLoader.loadClass(className);
      
      				instance = clazz.newInstance();
      
      				_instances.put(className, instance);
      			}
      			catch (Exception e2) {
      				if (logErrors) {
      					_log.error(
      						"Unable to load " + className +
      							" with the portal class loader or the " +
      								"current context class loader",
      						e2);
      				}
      			}
      		}
      
      		return instance;
      	}
      }
      

        Attachments

          Activity

            People

            • Votes:
              0 Vote for this issue
              Watchers:
              1 Start watching this issue

              Dates

              • Created:
                Updated:
                Resolved:
                Days since last comment:
                3 years, 3 weeks, 5 days ago

                Packages

                Version Package