Cyberborean Chronicles

Simple RDF data binding

A large part of SW development is representing the information as RDF for persistence and interoperability. It’s usually done with lots of the glue code to map the programming object model to RDF triples and vice versa.

Update: RDFBeans is an open-source object-RDF databinding and persistence library for the Semantic Web development with Java language. It provides a framework for mapping an object-oriented domain model to RDF resource descriptions.

Information on this page is likely outdated. Please refer to:

All posts about RDFBeans framework are here.

Working on my current project, I had to deal with a rich object model which is persisted into a RDF triple-store, so quickly I stuck in writing the object-triples translation code. I thought it would be a good idea to automate this by providing a simple data binding framework for transparent mapping of the Java objects to RDF (like Hibernate and other tools does so for SQL or XML) with the following requirements in mind:

  • It should be easy to make existing classes compatible with the framework with minimum modifications. This should not affect the business object model (no special interfaces and superclasses) and should not interfere with common JavaBeans-oriented frameworks (like Spring, etc.). Any JavaBean-like POJO class can be RDF-serializable just with few Java annotations added.
  • No predefined ontologies and RDF-schemas are required.
  • Class information is stored in the RDF model for transparent instantiation of the objects.
  • Cascade binding for related objects should be supported.
  • Basic Java Collection types should be supported.

This framework is implemented using Java annotations and Reflection APIs and works with major RDF triple-stores (via RDF2GO abstraction layer).

RDF Beans

In order to be mapped to an RDF resource, a Java class must obey certain conventions:

  • The class must have a public default (no-argument) constructor.
  • The class declaration must have a @RDFBean annotation to associate it with appropriate RDFS class:
    @RDFBean("http://xmlns.com/foaf/0.1/Person")
    public class Person { ...

See also: A RDFBean class example.

Properties

The class properties must be accessible using standard getter and setter methods. The properties are mapped to their RDF counterparts with @RDF annotations:

@RDF("http://xmlns.com/foaf/0.1/name")
String name;
 
@RDF("http://xmlns.com/foaf/0.1/mbox")
String email;
 
public String getName() { return name; }
public void setName(String name) { this.name = name; }
public String getEmail() { return email; }
public void setEmail(String email) { this.email = email; }

The argument of @RDF is a valid URI of a RDF property (predicate) in a domain of the specified RDFS class. The following types of properties are permitted:

  • A Literal (String, Boolean, Date, Integer, Float, Double, Long, Short, Byte, java.net.URI)
  • Another RDFBean class
  • A Java Collection (List or Set) of Literals or RDFBeans

Literal values are represented in RDF with corresponding XML-Schema datatypes and Collections with RDF Containers (rdf:Bag or rdf:Seq depending on a Collection type). References to other RDFBean objects will be kept as RDF object properties and the values will be represented as separate RDF resources.

RDF subject

There must be a special String property to hold an unique URI value to identify the RDF resource (the subject URI). It must be accessible with getter and setter methods and be marked with @RDFSubject annotation:

@RDFSubject
String id;

The property value must be a valid absolute URI, otherwise you can use the prefix argument for a common prefix to construct URIs from arbitrary String identifiers:

@RDFSubject(prefix="http://example.com/persons#")
String id;

Data Binding

RDFBeans data binding framework is based on RDF2Go API which creates an abstraction layer above physical RDF storages. It makes an RDF model independent from specific RDF frameworks (such as Sesame and Jena), thus it can work with any, if a RDF2Go adapter is implemented. The data binding is performed using single RDFBinding class, which is initialized with existing RDF2Go model:

import org.cyberborean.rdfbeans.RDFBinding;
import org.ontoware.rdf2go.RDF2Go;
import org.ontoware.rdf2go.model.Model;
...
Model model = RDF2Go.getModelFactory().createModel();
model.open();
RDFBinding binding = new RDFBinding(model);

The marshal method converts a Java object into a RDF resource in the model:

Person person = new Person();
person.setId("http://example.com/staff#johndoe");
person.setName("John Doe");
person.setEmail("johndoe@example.com");
...
binding.marshal(person);

This code will create a set of RDF statements representing the properties of the given object in the model:

<http://example.com/staff#johndoe> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <http://xmlns.com/foaf/0.1/Person> .
<http://example.com/staff#johndoe> <http://xmlns.com/foaf/0.1/name> "John Doe"^^<http://www.w3.org/2001/XMLSchema#string> .
<http://example.com/staff#johndoe> <http://xmlns.com/foaf/0.1/mbox> "johndoe@example.com"^^<http://www.w3.org/2001/XMLSchema#string> .

Additionally, it adds a special statement to associate the RDFS class with Java:

<http://xmlns.com/foaf/0.1/Person> <http://cyberborean.org/rdfbeans/1.0/bindingClass> "com.example.Person" .

The marshal method inspects the properties which link the object with other RDFBeans and initiates their cascade binding to the RDF model, thus simplifying the development and ensuring referential integrity of the RDFBeans.

To reconstruct a Java object from RDF model, there is unmarshal method:

import org.ontoware.rdf2go.model.node.URI;
...
URI subject = model.createURI("http://example.com/staff#johndoe");
Person person = (Person) binding.unmarshal(subject);

The method creates new instance of the Java class (defined by http://cyberborean.org/rdfbeans/1.0/bindingClass property) and fill the properties with data from the RDF model. If a property holds a reference to another RDFBean, it results into cascade unmarshalling of related objects, thus restoring the original object model.

Code

[Update: 2009-08-04]

RDFBeans framework is released on SourceForge: http://rdfbeans.sourceforge.net. The API has been changed, please check the documentation and Javadocs for details.

One Response to “Simple RDF data binding”

  1. Timo Westkämper · October 1, 2010 at 1:27 pm · Reply

    Nice blog post. We have develope a similar framework for Object/RDF usage : http://source.mysema.com/display/rdfbean/RDFBean

    Currently we supported only Sesame, Lucene and our own persistence backends. But we plan to support BigData as well.

Leave a Reply