4

I'm looking for best tool/way to create and load JAVA objects from XML definitions. I had checked out JAXB, seems pretty nice, but didn't find is there a way to work with Entities which properties are dynamic, or changed from time to time, so want to have something like automatic way of working with entities, without converting Object into predefine Entity object. Does something like that exists?

Workflow would be like this read from XML create class for each Entity with dynamic set of attributes and/or create ORM mapping part for those entities and then all manipulation retrieve/store into db or probably will going to use some NoSQL solution like MongoDB.

vaske
  • 9,332
  • 11
  • 50
  • 69
  • If I get you right you might be interested in these two posts: http://stackoverflow.com/questions/4248099/jaxb-dynamically-generate-java-sources-without-xjc and http://stackoverflow.com/questions/4556179/how-to-force-schema-compiled-classes-to-extend-specific-class-outside-schema This is how i generate java classes from xml on the fly. – andbi Sep 01 '11 at 17:51

2 Answers2

3

Note: I'm the EclipseLink JAXB (MOXy) lead, and a member of the JAXB 2 (JSR-222) expert group.


Check out the following EclipseLink example. It demonstrates how to use dynamic properties with both the JPA and JAXB implementations:


Option #1 - Static Objects with Dynamic Properties

MOXy has an @XmlVirtualAccessMethods extension which allows you to map entries in a map to XML. This allows you to add properties to a static class. In the example below the Customer class has a "real" name property and may have many "virtual" properties.

package blog.metadatasource.refresh;

import java.util.*;
import javax.xml.bind.annotation.*;
import org.eclipse.persistence.oxm.annotations.XmlVirtualAccessMethods;

@XmlRootElement
@XmlType(propOrder={"firstName", "lastName", "address"})
@XmlVirtualAccessMethods
public class Customer {

    private String name;
    private Map<String, Object> extensions = new HashMap<String, Object>();

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Object get(String key) {
        return extensions.get(key);
    }

    public void set(String key, Object value) {
        extensions.put(key, value);
    }

}

The virtual properties are defined via MOXy's XML metadata. In the example below we will add two properties: middleName and shippingAddress.

<?xml version="1.0"?>
<xml-bindings
    xmlns="http://www.eclipse.org/eclipselink/xsds/persistence/oxm"
    package-name="blog.metadatasource.refresh">
    <java-types>
        <java-type name="Customer">
            <java-attributes>
                <xml-element
                    java-attribute="middleName"
                    name="middle-name"
                    type="java.lang.String"/>
                <xml-element
                    java-attribute="shippingAddress"
                    name="shipping-address"
                    type="blog.metadatasource.multiple.Address"/>
            </java-attributes>
        </java-type>
    </java-types>
</xml-bindings>

For More Information


Option #2 - Dynamic Objects

MOXy also offers full dynamic object models:

DynamicJAXBContext jaxbContext = DynamicJAXBContextFactory.createContextFromXSD(xsdInputStream, null, null, null);

Unmarshaller unmarshaller = jaxbContext.createUnmarshaller();
DynamicEntity customer = (DynamicEntity) unmarshaller.unmarshal(inputStream);

DynamicEntity address = jaxbContext.newDynamicEntity("org.example.Address");
address.set(street, "123 A Street");
address.set(city, "Any Town");
customer.set("address", address);

Marshaller marshaller = jaxbContext.createMarshaller();
marshaller.marshal(customer, System.out);

For More Information

bdoughan
  • 147,609
  • 23
  • 300
  • 400
  • Looks nice, but is there a way to manage things if we don't know exact structure of future POJO object, in your example you use "firstName", "lastName", "address" which is fixed, what about if I want to have it dynamic? – vaske Sep 01 '11 at 18:18
  • @vaske - With option #1 (static models with dynamic properties), the name property is static (accessed with `getName()`/`setName("Jane")`, and the middle name property is dynamic (accessed with `get("middleName")`/`set("middleName", "Anne")`. – bdoughan Sep 01 '11 at 18:25
  • thanks yes that's it, also about class names, I'm going to pull them from XML file, basically all my entities would be in one file, defined then I'll read it and create POJO objects and use it like a mapping source for usage in application. – vaske Sep 01 '11 at 18:27
  • MOXy supplies an XML mapping file (http://blog.bdoughan.com/2010/12/extending-jaxb-representing-annotations.html), that can be used to map static clases, add dynamic properties to static classes (http://blog.bdoughan.com/2011/06/extensible-models-with-eclipselink-jaxb.html), or boostrap entirely dynamic models (http://wiki.eclipse.org/EclipseLink/UserGuide/MOXy/Runtime/Bootstrapping/From_OXM). Is this what you are looking for? – bdoughan Sep 01 '11 at 18:32
  • last one seems like something I had been looking for. main problem is in fact that read structure from XML file then use that structure to manipulate with data which grab from third part, basically I'm not sure does anything of those will help me as I thought that would...but investigating :) – vaske Sep 01 '11 at 19:03
2

So, you're basically trying to make POJO's (plain old Java objects) using XML files? They are just like data classes, right?

I'm a big fan of XStream, which is really easy to use and works great if you don't need validation. I've used Castor when validation against a schema was required. I just used XStream to save an object to an xml file and then I can read it back in from anywhere, even if I change the data values associated with the object (which I think is what you mean by "dynamic set of attributes", right?).

Dave
  • 4,050
  • 6
  • 30
  • 35
  • Yes I'm trying to make POJO objects and to use them, that XML file contains definition of each entity, schema look like, and schema should be changed from time to time. I need to establish a dynamic way for management of POJO objects. All data will be stored in MongoDB and this POJO object will load them from there, so this XML just contains definition of POJO object. Validation is not necessary. – vaske Sep 01 '11 at 17:23