Re: [kryo] Class is not registered error for field of class with registered serializer

746 views
Skip to first unread message

Nate

unread,
Aug 28, 2012, 6:18:50 PM8/28/12
to kryo-...@googlegroups.com
On Tue, Aug 28, 2012 at 4:26 AM, DDS <bra...@gmail.com> wrote:
Hi All,

I'm relatively new to Kryo, but have already found it very helpful in my project so thanks to all those involved.

Let's say I have a class named Person, and this class has a private field of type org.joda.time.DateTime. If I create a Kryo object, register Person.class, register DateTime.class, and also add a default serializer for DateTime

Setup:
class Person with private field of type org.joda.time.DateTime

Execution:
create Kryo object
set reqistration required
register Person.class
register DateTime.class
add default serializer for DateTime.class (from https://github.com/magro/kryo-serializers/)

When I attempt to write an object of type person, the default field serializer is used, as I would expect. But when the field serializer gets to the DateTime field, instead of using the registered DateTime serializer, it looks through the DateTime class and throws an IllegalArgumentException "Class not registered" when if finds field types that have not been registered (e.g. org.joda.time.chrono.ISOChronology).

Kryo itself won't look through a class, find field types that aren't registered, and throw an error. FieldSerializer would though. It sounds like FieldSerializer is being used for your DateTime class.

When you register, it will use the default serializer for the type if a serializer is not specified. If registration is required, there is no usefulness to adding default serializers. Instead, specify them when you register each class.

-Nate

 

I would have expected the serializer I added to be passed the DateTime field for serialization and didn't think the inner types would need to be registered.

So I guess my question is, is this is proscribed behaviour? If I assign a default serializer for a class, do I still need to register it's field types? Or have I likely made an error somewhere (in which case I'll try to cut the code down and paste here).

Thanks in advance for any help

--
You received this message because you are subscribed to the "kryo-users" group.
http://groups.google.com/group/kryo-users

DDS

unread,
Aug 29, 2012, 2:03:00 AM8/29/12
to kryo-...@googlegroups.com
Thanks for the pointer Nate.

I fixed the problem by adding the DateTime serializer prior to registering DateTime class, but I take your point that I could simply assign the serializer in the register call.

I do find the behavior a little non-intuitive though. I'm assuming (maybe incorrectly) that kryo has an internal Map of class types to serializers. When I call

kryo.register(DateTime.clas, #)

I presume it puts an entry of DateTime class=FieldSerializer (the default). When I subsequently call:

kryo.addDefaultSerializer(DateTime.class, DateTimeSerializer.class)

I would expect any existing assignment of DateTime.class=FieldSerializer  to be replaced, but this does not appear to be the case and it still uses FieldSerializer on any subsequent attempts to write a DateTime object.

 

Nate

unread,
Aug 29, 2012, 2:09:53 AM8/29/12
to kryo-...@googlegroups.com
On Tue, Aug 28, 2012 at 11:03 PM, DDS <bra...@gmail.com> wrote:
Thanks for the pointer Nate.

I fixed the problem by adding the DateTime serializer prior to registering DateTime class, but I take your point that I could simply assign the serializer in the register call.

I do find the behavior a little non-intuitive though.

I think it seems odd because the default serializers aren't intended to be used at all for your use case (registration required). First, default serializers are used to choose a serializer if you don't specify one, allowing Kryo to ship with many serializers for JDK classes. Second, default serializers are useful when classes are encountered at runtime and a serializer must be chosen. In this case, the classes are likely not known up front, so they can't be registered. The default serializer class might be an interface or super class.
 
I'm assuming (maybe incorrectly) that kryo has an internal Map of class types to serializers. When I call

kryo.register(DateTime.clas, #)

I presume it puts an entry of DateTime class=FieldSerializer (the default). When I subsequently call:

kryo.addDefaultSerializer(DateTime.class, DateTimeSerializer.class)

I would expect any existing assignment of DateTime.class=FieldSerializer  to be replaced, but this does not appear to be the case and it still uses FieldSerializer on any subsequent attempts to write a DateTime object.

Adding default serializers after registering classes is a bit odd, don't do that. ;) I think it might be less intuitive for add default serializer to have a side effect that changes registered classes.

-Nate

DDS

unread,
Aug 29, 2012, 9:20:24 AM8/29/12
to kryo-...@googlegroups.com
Understood. It's all working well now anyway. Thanks again for a great library
 
Reply all
Reply to author
Forward
0 new messages