1

Using JDO JDOPersistenceManager, I keep getting memory leak detection reports from Plumbr, what is the correct way to create and destroy a JDOPersistenceManager

Plumbr report:

The objects are created at

org.datanucleus.api.jdo.JDOPersistenceManagerFactory.newPM(org.datanucleus.api.jdo.JDOPersistenceManagerFactory, java.lang.String, java.lang.String):838

and are being held

in key of java.util.HashMap$Entry
in table of java.util.HashMap
in map of java.util.HashSet
in pmCache of org.datanucleus.api.jdo.JDOPersistenceManagerFactory
in pmf of com.example.MyServlet

the last line, pmf is a singleton which initiates the object and used through the lifetime of the request. MyServlet is an httpservlet and a doPost is being called.

PMF.java:

public class PMF {

    private static PersistenceManagerFactory instance;

    public static PersistenceManagerFactory get() {

        if (instance == null) {
            Properties props = new Properties();
            props.setProperty("javax.jdo.PersistenceManagerFactoryClass",
                    "org.datanucleus.api.jdo.JDOPersistenceManagerFactory");
            props.put("datanucleus.PersistenceUnitName", "pmf");
            instance = JDOHelper.getPersistenceManagerFactory(props);
        }
        return instance;
    }
}

typically i use the pmf instance in a try / finally block and use pmf:

PersistenceManager pm = pmf.getPersistenceManager();

    try {
    //do stuff
    }
    finally {
    pm.close();
    }

what is the correct way to dispose of the pmf singlton so as not to cause a memory leak as reported by plumbr?

bsautner
  • 4,479
  • 1
  • 36
  • 50

2 Answers2

1

Judging by the source code of org.datanucleus.api.jdo.JDOPersistenceManagerFactory , you should call instance.releasePersistenceManager(pm) at the end of the request in order to properly destroy PersistanceManager and remove it from Factory's cache.

And thanks for using our tool :) Plumbr developer

Nikem
  • 5,716
  • 3
  • 32
  • 59
0

I don't know Nikem's answer works and don't think you should explicitly call public void releasePersistenceManager(JDOPersistenceManager pm) because

  1. It is internally called by JDOPersistenceManager's public void close().

  2. The comments for this method says:

Only the PersistenceManager is allowed to call this method