Hello Chris, On Tue, May 28, 2024 at 6:38 PM Christopher Schultz < ch...@christopherschultz.net> wrote:
> Jakub, > > On 5/24/24 09:31, Jakub Królikowski wrote: > > On Fri, May 24, 2024 at 11:23 AM Mark Thomas <ma...@apache.org> wrote: > > > >> Can you provide the simplest web application (with source) that > >> replications the problem? > >> > >> Mark > >> > >> > >> On 23/05/2024 23:45, Jakub Królikowski wrote: > >>> Hi, > >>> > >>> I'm working with Tomcat 10.1. > >>> > >>> When a user starts using the store in my web application, I save the > >>> ShopCart object on the "cart" session attribute. > >>> I want the "cart" attributes to return to the session after restarting > >> the > >>> app. > >>> > >>> > >>> To enable session persistence I added > >>> > >>> <Manager pathname="SESSIONS.ser" /> > >>> > >>> to the Context. It loads the StandardManager. > >>> > >>> And this works fine - after reload / restart the object "ShopCart" is > >> back > >>> in the session. > >>> > >>> > >>> > >>> I want to experiment with PersistentManager. Tomcat docs says: " > >>> The persistence across restarts provided by the *StandardManager* is a > >>> simpler implementation than that provided by the *PersistentManager*. > If > >>> robust, production quality persistence across restarts is required then > >> the > >>> *PersistentManager* should be used with an appropriate configuration. > >>> > >>> " > >>> > >>> I hope for a Listener of deserialization of the session attributes. > >>> > >>> The new Manager configuration looks like this: > >>> > >>> <Manager className="org.apache.catalina.session.PersistentManager" > >>> maxActiveSessions="2" saveOnRestart="true"> > >>> > >>> <Store className="org.apache.catalina.session.FileStore" directory= > >>> "c:\tomcat10\sessionperm"/> > >>> > >>> </Manager> > >>> > >>> But it doesn't work. After restart I get this exception: > >>> > >>> > >>> java.lang.ClassNotFoundException: ....ShopCart > >>> > >>> at > >>> > >> > org.apache.catalina.loader.WebappClassLoaderBase.loadClass(WebappClassLoaderBase.java:1332) > >>> > >>> at > >>> > >> > org.apache.catalina.loader.WebappClassLoaderBase.loadClass(WebappClassLoaderBase.java:1144) > >>> > >>> at java.base/java.lang.Class.forName0(Native Method) > >>> > >>> at java.base/java.lang.Class.forName(Class.java:534) > >>> > >>> at java.base/java.lang.Class.forName(Class.java:513) > >>> > >>> at > >>> > >> > org.apache.catalina.util.CustomObjectInputStream.resolveClass(CustomObjectInputStream.java:158) > >>> > >>> at > >>> java.base/java.io > >> .ObjectInputStream.readNonProxyDesc(ObjectInputStream.java:2061) > >>> > >>> at > >>> java.base/java.io > >> .ObjectInputStream.readClassDesc(ObjectInputStream.java:1927) > >>> > >>> at > >>> java.base/java.io > >> .ObjectInputStream.readOrdinaryObject(ObjectInputStream.java:2252) > >>> > >>> at > >>> java.base/java.io > >> .ObjectInputStream.readObject0(ObjectInputStream.java:1762) > >>> > >>> at > >>> java.base/java.io > >> .ObjectInputStream.readObject(ObjectInputStream.java:540) > >>> > >>> at > >>> java.base/java.io > >> .ObjectInputStream.readObject(ObjectInputStream.java:498) > >>> > >>> at > >>> > >> > org.apache.catalina.session.StandardSession.doReadObject(StandardSession.java:1198) > >>> > >>> at > >>> > >> > org.apache.catalina.session.StandardSession.readObjectData(StandardSession.java:831) > >>> > >>> at org.apache.catalina.session.FileStore.load(FileStore.java:203) > >>> > >>> at > >> org.apache.catalina.session.StoreBase.processExpires(StoreBase.java:138) > >>> > >>> at > >>> > >> > org.apache.catalina.session.PersistentManagerBase.processExpires(PersistentManagerBase.java:409) > >>> > >>> at > >>> > >> > org.apache.catalina.session.ManagerBase.backgroundProcess(ManagerBase.java:587) > >>> > >>> at > >>> > >> > org.apache.catalina.core.StandardContext.backgroundProcess(StandardContext.java:4787) > >>> > >>> at > >>> > >> > org.apache.catalina.core.ContainerBase$ContainerBackgroundProcessor.processChildren(ContainerBase.java:1172) > >>> > >>> at > >>> > >> > org.apache.catalina.core.ContainerBase$ContainerBackgroundProcessor.processChildren(ContainerBase.java:1176) > >>> > >>> at > >>> > >> > org.apache.catalina.core.ContainerBase$ContainerBackgroundProcessor.processChildren(ContainerBase.java:1176) > >>> > >>> at > >>> > >> > org.apache.catalina.core.ContainerBase$ContainerBackgroundProcessor.run(ContainerBase.java:1154) > >>> > >>> at > >>> > >> > java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:572) > >> > > > > > >>> > >>> at > >>> > >> > java.base/java.util.concurrent.FutureTask.runAndReset(FutureTask.java:358) > >>> > >>> at > >>> > >> > java.base/java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:305) > >>> > >>> at > >>> > >> > java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144) > >>> > >>> at > >>> > >> > java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642) > >>> > >>> at > >>> > >> > org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:63) > >>> > >>> at java.base/java.lang.Thread.run(Thread.java:1583) > >>> > >>> > >>> I guess this means that the two managers use ClassLoader differently. > >>> How to get the PersistentManager to work in this case? > >>> > >>> Best regards, > >>> -- > >>> Jakub Królikowski > >>> > >> > >> --------------------------------------------------------------------- > >> To unsubscribe, e-mail: users-unsubscr...@tomcat.apache.org > >> For additional commands, e-mail: users-h...@tomcat.apache.org > >> > >> > > > > Hi Mark, > > It seems to me that this can be tested on any application. > > In Tomcat 10.1, if any session attribute is an instance of a new public > > class (unknown to Tomcat and to Tomcat class loader), implementing > > java.io.Serializable, > > then on reloading the application PersistanceManager (configured as in > the > > first message) crashes with ClassNotFoundException. StandardManager > works. > > I don't know if this problem occurred in earlier versions of Tomcat. > > > > If you fail to reproduce this bug, let me know, I will prepare a simple > web > > app. > > Where is your <Manager> configuration located? It *should* be inside > your <Context> located in META-INF/context.xml in your web application. > If it's in there, then everything it does should be in the context (and > ClassLoader) of your web application -- where your classes should be > locatable. > > If you have it anywhere else, it probably won't work the way you expect > it to work. > > -chris > > --------------------------------------------------------------------- > To unsubscribe, e-mail: users-unsubscr...@tomcat.apache.org > For additional commands, e-mail: users-h...@tomcat.apache.org > > Yes, you are right! Thank you for this hint! I have configured <Manager> in <tomcat-dir>/conf/server.xml. And indeed - interestingly, StandardManager, works correctly even there! PersistentManager, however, does not. After moving the configuration to <app-dir>/META-INF/context.xml, both managers work fine. It may be worth mentioning this in the documentation: https://tomcat.apache.org/tomcat-10.1-doc/config/manager.html#Persistence_Across_Restarts Jakub