Switching to a string wouldn't be a problem. However, I don't think we can get away from region based classloading since we must handle serializable types. The following require this:
- Custom serializable types
Can these be stored internally in a MarshalledValue variant (i.e. lazy-demarshalling by the interceptor on the field read)?
Assume the MarshalledValue variant is efficient; i.e. doesn't create a byte version of the object until it itself is serialized; discards the byte as soon as get() is called.
Yes, that would work. Although I think this functionality belongs in JBoss Cache directly. There could be some kind of deserializeOnLoad option.
Ah, so I am not alone here :)
Ok so, off the top of my head, I can see 3 possible core cache solutions to this problem.
1) Have an option that enables lazy wrapper style serialization (like you are suggesting) using the TCL. The reason this should be optional is that any wrapper serialization usage has greater cost than a region CL (double buffering + additional synchronization).
2) Add a serialization manager which allows app registered callbacks when deserializing/serializing an Object. This is essentially the reverse of a region CL. The callback would be passed various node information that could be used to locate the correct deployment CL.
3) Both 1 + 2. A registered serialization callback could decide to use a wrapper type, which would be deserialized and automatically unwrapped by the cache layer.
Chat history related to above:
[14:43:27] Jason T. Greene: did you ever review my reply to the marshalvalue thread?
[14:48:01] Brian Stansberry: i was a little unclear on #2; i.e. when the deserialization occurs and what gets passed to the callback
[14:50:15] ? i.e. how it would be different from the current region-based marshalling
[14:51:07] Jason T. Greene: it would just keep you from having to configure the region up front
[14:51:27] ? and allow for you to make decisions at the node level
[14:52:03] Brian Stansberry: ok, ic.
[14:52:17] ? here's a sucky thing about region-based....
[14:52:45] ? for a tx prepare, we need to figure out the region
[14:53:10] ? we do that by checking the first method call in the set of method calls that make up the prepare
[14:53:25] ? if a tx spans classloader regions, that breaks
[14:54:24] ? i suppose a serialization manager could be more intelligent
[14:54:44] Jason T. Greene: hmm shouldnt prepare deseralize each call separately according to the fqn
[14:54:45] ? ?
[14:55:41] Brian Stansberry: yeah, that would be better. DOH!
[14:56:22] ? just serialize the elements individually and then wrap them up in the prepare method call
[14:57:11] Jason T. Greene: yeah you could even do this intelligently with markers that prevent double buffering
[14:59:40] Jason T. Greene: so the serialization manager suggestion was really because i was interpreting the problem being allocating the structure to fit the region model
[15:01:01] Brian Stansberry: well, its more than that
[15:01:18] ? assume the goal is to fit all session repl in a shared cache
[15:02:03] ? for most usages, the session is represented by a single key/value pair in one node.
[15:02:53] ? and most txs involve changing a single session
[15:03:13] ? for that case, a wrapper obj is more efficient than passing a region-fqn as external metadata for every call
[15:04:36] Jason T. Greene: ok so the issue is multiple classloaders in the same session right?
[15:05:03] Brian Stansberry: no, multiple classloaders in the same cache; only one per session
[15:05:27] ? I can either use something like region-based marshalling or wrap the cached objects
[15:05:38] Jason T. Greene: oh i see
[15:05:50] ? now i get what you are talking about
[15:06:27] ? technically the region-fqn is duplicate information
[15:06:38] ? you already know the region from the fqn
[15:06:38] Brian Stansberry: yes
[15:07:27] ? yes, although the Fqn is encapsulated as an arg in the MethodCall, and which arg depends on the method
[15:08:12] ? also, an element of the fqn can itself be a custom type, as long as its below the region root
[15:08:40] ? BTW that's an issue with Hibernate caching (which is a quite different use case)
[15:10:43] Jason T. Greene: the first problem is an issue with the serialization format
[15:10:54] ? the second is bigger problem
[15:11:21] Brian Stansberry: +1
[15:16:17] Jason T. Greene: I want to get rid of that usage in pojo cache
[15:16:41] Brian Stansberry: which?
[15:16:49] Jason T. Greene: custom types in an fqn
[15:16:59] ? its used for maps right now
[15:17:39] Brian Stansberry: the key for a map entry is the last Fqn element?
[15:18:09] Jason T. Greene: yeah, it was done that way to make locking more efficient
[15:18:29] ? and index retrieval is effecient as well
[15:19:34] ? what i probably want to do is keep it like that for simple types
[15:19:55] ? but when a custom type is used generate a hash based UUID
[15:21:39] ? anyway its a problem i have to think about
[15:21:48] ? because their are other issues with custom fqns
[15:21:53] ? like cache loaders