How to always use the same PersistenceManager within the same RPC request on Google App Engine

笑着哭i 提交于 2020-01-02 12:09:57

问题


Is there a way to ensure the same PersistenceManager instance is used throughout the different code parts executed in the context of the same RPC request?

Having to manually handle out the persistence manager instance from function to function is quite a pain:

for example:

private void updateItem(ItemModel listItem)
        throws UserNotLoggedInException {
   PersistenceManager pm = PMF.get().getPersistenceManager();
   if (isItemIsNew(pm, listItem)) { 
        workOnItem(pm, listItem);
   }
   workSomeMoreOnItem(pm, listItem);

}

回答1:


Google Cookbook offers the following answer:

Using a filter, you can make the PersistenceManager available and guarantee that it is closed at the end of the request. If you are using an MVC framework that handles the rendering for you such as Spring, then this is also useful to keep the manager open long enough for the View to still be able to fetch persistent objects that haven't already been accessed.

public final class PersistenceFilter implements Filter {
    private static final PersistenceManagerFactory persistenceManagerFactory
        = JDOHelper.getPersistenceManagerFactory("transactions-optional");

    private static PersistenceManagerFactory factory() {
        return persistenceManagerFactory;
    }

    private static ThreadLocal currentManager = new ThreadLocal();

    public static PersistenceManager getManager() {
        if (currentManager.get() == null) {
            currentManager.set(factory().getPersistenceManager());
        }
        return currentManager.get();
    }
    @Override
    public void doFilter(ServletRequest req, ServletResponse res,
            FilterChain chain) throws IOException, ServletException {
        PersistenceManager manager  = null;
        try {
            manager = getManager();
            //Optional: allow all persistent objects implementing a custom interface
            //to be notified of when they are saved and loaded.
            manager.addInstanceLifecycleListener(new PersistHookListener(), PersistHooks.class);
            chain.doFilter(req, res);
        } finally {
            if (manager != null) {
                manager.flush();
                manager.close();
            }
        }
    }
    @Override
    public void init(FilterConfig arg0) throws ServletException {}
    @Override
    public void destroy() {}
}

http://appengine-cookbook.appspot.com/recipe/persistencefilter/?id=ahJhcHBlbmdpbmUtY29va2Jvb2tyigELEgtSZWNpcGVJbmRleCI2YWhKaGNIQmxibWRwYm1VdFkyOXZhMkp2YjJ0eUVnc1NDRU5oZEdWbmIzSjVJZ1JLWVhaaERBDAsSBlJlY2lwZSI3YWhKaGNIQmxibWRwYm1VdFkyOXZhMkp2YjJ0eUVnc1NDRU5oZEdWbmIzSjVJZ1JLWVhaaERBMAw



来源:https://stackoverflow.com/questions/2021287/how-to-always-use-the-same-persistencemanager-within-the-same-rpc-request-on-goo

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!