How to configure XStream to map to different classes depending on XML attributes?

killerkill34

New Member
I have the following Java object hierarchy:\[code\]public interface Function { public void calculate(long t);}public class ConstantFunction implements Function { private double constant; @Override public void calculate(long t) { // ... }}public class LinearFunction implements Function { private double slope; private double yIntercept; @Override public void calculate(long t) { // ... }}\[/code\]Users can create \[code\]ConstantFunction\[/code\] and \[code\]LinearFunction\[/code\] instances by defining them inside XML like so:\[code\]<myapp> <function type="ConstantFunction> <!-- ... --> </function> <function type="LinearFunction> <!-- ... --> </function></myapp>\[/code\]I am using XStream to OX-map the user-defined XML into Java POJOs. I'm currently trying to configure the \[code\]XStream\[/code\] mapper with aliases so that it knows what Java class to bind to the \[code\]function\[/code\] element:\[code\]XStream oxmapper = new XStream();oxmapper.alias("myapp", MyApp.class);oxmapper.alias("function", ???);\[/code\]The problem is, I need to configure XStream with logic that says: *if \[code\]function/type\[/code\] is \[code\]ConstantFunction\[/code\], then use \[code\]oxmapper.alias("function", ConstantFunction.class)\[/code\]; but if its value is \[code\]LinearFunction\[/code\], then use \[code\]oxmapper.alias("function", LinearFunction.class)\[/code\].The problem is, I don't think XStream API gives provides a way to inspect the XML the way I need it to in order to implement this logic. If I am incorrect, please point me in the right direction!If I am correct, then the only solution I can think of would be to have a really nasty "hodgepodge" class that forms a union of all the \[code\]Function\[/code\] concretions like so:\[code\]public class FunctionFactory implements Function { private double constant; private double slope; private double yIntercept; private Class<? extends Function> concreteClass; @Override public void calculate(long t) { // Do nothing. This class is a workaround to limitations with XStream. return; }}\[/code\]In the OX-mapper config:\[code\]oxampper.alias("function", FunctionFactory.class);oxmapper.aliasField("function", "type", "concreteClass");\[/code\]Now, every time I read an XML instance into a \[code\]MyApp\[/code\] instance, I need to correct the conversion:\[code\]XStream oxmapper = getConfiguredMapper();MyApp app = oxmapper.fromXml("<myapp>...</myapp>");FunctionFactory factory = app.getFunction();Function concretion = factory.getConcreteClass();app.setFunction(concretion);\[/code\]This is the only workaround I can cook up, but it feels really nasty, and I have to believe there's a better way to do this. Thanks in advance!
 
Back
Top