Uploaded image for project: 'PUBLIC - Liferay Faces'
  1. PUBLIC - Liferay Faces
  2. FACES-2177

ViewScope beans memory leak for Mojarra 2.1.28 and newer

    Details

      Description

      Hello, All

      Below is reason of the memory leaks that we have faced after upgrading from Liferay 6.1.1 to Liferay 6.1.2.

      Memory dump analysis revealed that ViewScope beans are not being destroyed properly in LR6.1.2, meanwhile in LR6.1.1 no leaks were found.

      The root reason of the issue is that Liferay Faces in LR6.1.2 have wrong expectations how beans are stored in the JSF. The way of storing has changed in the version of JSF 2.1.28. Even in the master branch of the Liferay's bridge.
      Here's the diff between 2.1.28 and 2.1.27 versions of the code where ViewScope beans are being stored in the sessionMap:
      http://grepcode.com/file/repo1.maven.org/maven2/com.sun.faces/jsf-impl/2.1.28/com/sun/faces/application/view/ViewScopeManager.java/
      > if (sessionMap.get(ACTIVE_VIEW_MAPS) == null)

      { > sessionMap.put(ACTIVE_VIEW_MAPS, (Map<String, Object>) Collections.synchronizedMap(new LRUMap<String, Object>(size))); > }

      http://grepcode.com/file/repo1.maven.org/maven2/com.sun.faces/jsf-impl/2.1.27/com/sun/faces/application/view/ViewScopeManager.java/
      > if (sessionMap.get(ACTIVE_VIEW_MAPS) == null)

      { > sessionMap.put(ACTIVE_VIEW_MAPS, (Map<String, Object>) new LRUMap<String, Object>(size)); > }

      But Liferay expects that beans have been put into the map like 2.1.27 version do and gets them in the following way(lines 210-213):
      https://github.com/liferay/liferay-faces/blob/3.0.x/bridge-impl/src/main/java/com/liferay/faces/bridge/servlet/BridgeSessionListener.java
      > // If the current session attribute is Mojarra-vendor-specific, then
      > String fqcn = attributeValue.getClass().getName();
      >
      > if ((fqcn != null) && (fqcn.contains(MOJARRA_PACKAGE_PREFIX))) {
      where
      > private static final String MOJARRA_PACKAGE_PREFIX = "com.sun.faces";
      But Collections.synchronizedMap is a "java.util" package so if-condition is false and beans' cleanup code is not being invoked.

      After downgrade to the jsf-impl 2.1.27 leaks were gone. I believe that this is good but not a temporary solution.

      Could you please confirm that Liferay faces are working as described above or please denote the wrong place in the description.

        Attachments

          Activity

            People

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

              Dates

              • Created:
                Updated:
                Resolved:

                Packages

                Version Package
                liferay-faces-3.0.5-legacy-ga6
                liferay-faces-3.0.5-ga6
                liferay-faces-3.1.5-ga6
                liferay-faces-3.2.5-ga6
                liferay-faces-4.2.5-ga6