On Mar 20, 2012, at 3:37 PM, Jörg Schaible wrote:

> Hi Bjorn
> 
> Bjorn Roche wrote:
> 
>> Hey all,
>> 
>> First off, I heart XStream. I just wanted to share a problem I had
>> recently and how I solved it. It seems to me the solution is unintuitive
>> and hard to find. This maybe isn't a bug, but at the very least I think it
>> should be easier to do what I needed to do, or maybe his needs to be a FAQ
>> or something.
>> 
>> So here's my story:
>> 
>> I noticed my dates were not being converted the way I wanted. After much
>> searching I found this: http://jira.codehaus.org/browse/XSTR-116 Ah hah!
>> that's all I need to do!
>> 
>> - first comment: that should be a FAQ or something. ISO8601 dates are
>> pretty widely accepted as standard for XML, right? If they don't work
>> automatically, it should be easy for people to figure out how to make them
>> work, and I think the FAQ is the right place for that.
> 
> 
> The ISO8601 converters are listed:
> http://xstream.codehaus.org/converters.html

Fair enough. So much of xstream is automagic that when a widely accepted format 
(standard?) is not default, it seems strange.

> 
> 
>> So I installed Jodatime, registered my converter and thought I was done
>> with it. But I wasn't. Unbeknownst to me, my persistence engine was
>> converting my java.util.date objects to java.sql.timestamp objects....
>> sometimes. One solution, of course, was to manually change that, since I
>> was using different objects for persistence and XML conversion, but that
>> seemed error-prone. Not a good solution. SO I thought the right was would
>> be to make XStream handle this.
>> 
>> The problem was here:
>> 
>> public class ISO8601DateConverter extends
>> ISO8601GregorianCalendarConverter {
>> 
>>    public boolean canConvert(Class type) {
>>        return type.equals(Date.class);
>>    }
>> ...
>> }
>> 
>> The date converter was only handling java.util.Date classes and not
>> subclasses. Was that intentional? I don't know, but my solution was to do
>> this:
>> 
>> public static ISO8601DateConverter DATE_CONVERTER = new
>> ISO8601DateConverter() { @Override
>> public boolean canConvert(Class type) {
>> return Date.class.isAssignableFrom(type);
>> }
>> };
>> 
>> That worked! horray! Now java.util.Date AND ALL SUBCLASSES are converted
>> to ISO8601 dates, like I wanted.
>> 
>> - Second Comment/question: Is this a bug, or was that intentional?
> 
> Intentional. How can XStream know what additional fields/data a derived 
> class might have? The ISO8601DateConverter will never produce a different 
> string representation.

Okay. Makes sense.

> 
>> If it
>> was intentional, is my subclassed cade safe?
> 
> No.
> 
>> Now here's the problem I don't really understand: the timestamp objects
>> still converted like this:
>> 
>> <cTime class="sql-timestamp​">2012-03-17T20:44:00.490Z</cTime>
>> 
>> So the date/time format is right, but the class annotation confuses
>> XStream when trying to deserialize this.
> 
> No, it is simply ignored, because the ISO8601DateConverter only creates Date 
> instances. And XStream will throw an exception afterwards, since it expected 
> the converter to produce a Timestamp.

You say "No", but I think we are in agreement: this is a problem.

> 
>> The solution, which was
>> counterintuitive to me, was this:
>> 
>> XStream xstream = super.createXstream(mediaType);
>> 
> xstream.addDefaultImplementation(java.sql.Date.class,java.util.Date.class);
>> 
> xstream.addDefaultImplementation(java.sql.Timestamp.class,java.util.Date.class);
>> 
> xstream.addDefaultImplementation(java.sql.Time.class,java.util.Date.class);
>> xstream.registerConverter(DATE_CONVERTER);
>> 
>> That gets rid of the pesky annotation, although I suppose some other
>> subclass could come along and mess things up.
> 
> You simply suppressed the check of XStream. You still create only Date 
> instances. XStream will no longer care if your data structures (and your 
> application afterwards) expect something else. ClassCastExceptions are to be 
> expected.
> 
>> - Third comment/question: Is this the best way? Am I missing something? If
>> this is the best way, I think there should be a better way as this is
>> unintuitive and potentially error prone if another date subclass comes
>> along.
> 
> Registering the ISO8601SqlTimestampConverter?
> 

Okay. I'll try it.

thanks,

        bjorn

> Cheers,
> Jörg
> 
> 
> ---------------------------------------------------------------------
> To unsubscribe from this list, please visit:
> 
>    http://xircles.codehaus.org/manage_email
> 
> 

-----------------------------
Bjorn Roche
http://www.xonami.com
Audio Collaboration
http://blog.bjornroche.com




Reply via email to