XStream
  1. XStream
  2. XSTR-188

Problem with the implementation of WriteReplace

    Details

    • Type: Bug Bug
    • Status: Closed Closed
    • Resolution: Fixed
    • Affects Version/s: None
    • Fix Version/s: 1.1.1
    • Component/s: None
    • Labels:
      None
    • JDK version and platform:
      Sun 1.4.2_06 for Windows

      Description

      I have the following issue.

      I am serializing an object that implements the writeReplace method. The write replace method returns an object of a different type to the original.

      The replacement type implements the readResolve method which returns an object of the original type.

      The xml generated by xstream specifies an object of the original type but contains the fields of the replacement type.

      This causes a problem when unmashalling the xml as it creates an object of the orriginal type and tries to assign the values of the replacement type to it.

      Here is an example:

      import com.thoughtworks.xstream.XStream;
      import java.io.Serializable;

      public class Streamtest
      {
      public static void main( String argv[])

      { XStream xstr = new XStream(); TestClass testClass = new TestClass(); String xml = xstr.toXML( testClass ); System.out.println( xml ); TestClass unmartialedTestClass = ( TestClass )xstr.fromXML( xml ); }

      public static class TestClass implements Serializable{
      int testClassValue = 23;

      private Object writeReplace()

      { return new TestClassReplacement(); }

      }

      public static class TestClassReplacement implements Serializable {
      String replacementTestClassValue = "Replaced Value";

      private Object readResolve()

      { return new TestClass(); }

      }
      }

      executing this generates the following output:

      <Streamtest-TestClass>
      <replacementTestClassValue>Replaced Value</replacementTestClassValue>
      </Streamtest-TestClass>
      com.thoughtworks.xstream.converters.ConversionException: replacementTestClassValue : replacementTestClassValue
      ---- Debugging information ----
      required-type : Streamtest$TestClass
      cause-message : replacementTestClassValue : replacementTestClassValue
      class : Streamtest$TestClass
      message : replacementTestClassValue : replacementTestClassValue
      line number : 2
      path : /Streamtest-TestClass/replacementTestClassValue
      cause-exception : com.thoughtworks.xstream.alias.CannotResolveClassException
      -------------------------------
      at com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother(TreeUnmarshaller.java:46)
      at com.thoughtworks.xstream.core.ReferenceByXPathUnmarshaller.convertAnother(ReferenceByXPathUnmarshaller.java:37)
      at com.thoughtworks.xstream.core.TreeUnmarshaller.start(TreeUnmarshaller.java:96)
      at com.thoughtworks.xstream.core.ReferenceByXPathMarshallingStrategy.unmarshal(ReferenceByXPathMarshallingStrategy.java:12)
      at com.thoughtworks.xstream.XStream.unmarshal(XStream.java:286)
      at com.thoughtworks.xstream.XStream.unmarshal(XStream.java:274)
      at com.thoughtworks.xstream.XStream.fromXML(XStream.java:242)
      at com.thoughtworks.xstream.XStream.fromXML(XStream.java:233)
      at Streamtest.main(Streamtest.java:13)
      at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
      at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
      at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
      at java.lang.reflect.Method.invoke(Method.java:324)
      at com.intellij.rt.execution.application.AppMain.main(AppMain.java:78)
      Caused by: com.thoughtworks.xstream.alias.CannotResolveClassException: replacementTestClassValue : replacementTestClassValue
      at com.thoughtworks.xstream.core.DefaultClassMapper.lookupType(DefaultClassMapper.java:223)
      at com.thoughtworks.xstream.converters.reflection.ReflectionConverter.determineType(ReflectionConverter.java:178)
      at com.thoughtworks.xstream.converters.reflection.ReflectionConverter.unmarshal(ReflectionConverter.java:104)
      at com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother(TreeUnmarshaller.java:39)
      ... 13 more
      Exception in thread "main"

      As I understand it should be the replacement object that is actually serialized and hence the xml generated should be:

      <Streamtest-TestClassReplacement>
      <replacementTestClassValue>Replaced Value</replacementTestClassValue>
      </Streamtest-TestClassReplacement>

      Which is unmartialled correctly to a Streamtest.TestClass.

      Thanks and keep up the good work,

      Regards Francis

        People

        • Assignee:
          Unassigned
          Reporter:
          Francis Rhys-Jones
        • Votes:
          0 Vote for this issue
          Watchers:
          0 Start watching this issue

          Dates

          • Created:
            Updated:
            Resolved: