MPTStore 0.9.1

  1. What is MPTStore?
  2. How does it differ from existing approaches?
  3. Downloading and Installing
  4. API Documentation
  5. Known Issues / Bugs
  6. Coding Standards
  7. License Information

1. What is MPTStore?

MPTStore is a Java library for projects that need persistent, transaction-capable storage and querying of very large quantities of RDF data.

The primary areas of focus are scalability and transaction safety with simple query support. Complex query support (a subset of SPARQL features) is in development and looks very promising. Out of scope features include reasoning (inference) and quads.

MPTStore is implemented as a lightweight layer on top of JDBC. It was originally developed using Postgres as the underlying database, but be easily made to work with other databases by writing a DDLGenerator.

2. How does it differ from existing approaches?

The traditional way of storing RDF in a relational database is to use a "big table of triples". Variations on this basic approach are employed by popular RDF storage engines including Jena, Sesame, and 3store.

Our approach, MPT ("Mapped Predicate Tables"), is different. Recognizing that the number of relationship types in real RDF data is much lower than the number of nodes, MPT distributes triples across several tables, each holding all the relationships of a certain type. This design offers efficient query plans for complex queries as well as an opportunity to scale across storage devices.

3. Downloading and Installing

4. API Documentation

The main interface you work with is the DatabaseAdaptor. This interface allows you to add and delete triples and execute RDF queries.

The only current implementation of this interface is GenericDatabaseAdaptor. In order to construct one, you'll need a JDBC DataSource (which your application must provide on it's own), and a DDLGenerator.

A DDLGenerator tells MPTStore how to create and drop tables for a particular database type. Existing implementations include:

Once you have a DataSource and a DDLGenerator, you can construct a BasicTableManager, which can then be used to construct a GenericDatabaseAdaptor. Here is an example of putting the above pieces together and exercising the functionality of the DatabaseAdaptor interface.

  // initialize the adaptor
  TableManager tableMan = new BasicTableManager(dataSource,
                                                new PostgresDDLGenerator(),
                                                "tMap",
                                                "t");
  DatabaseAdaptor adaptor = new GenericDatabaseAdaptor(tableMan, true);

  // instantiate a couple triples
  Set<Triple> triples = new HashSet<Triple>();
  triples.add(new Triple(new URIReference("urn:resource:1"),
                         new URIReference("urn:title"),
                         new Literal("Resource One")));
  triples.add(new Triple(new URIReference("urn:resource:2"),
                         new URIReference("urn:title"),
                         new Literal("Resource Two")));

  // add the triples in a transaction
  Connection conn = dataSource.getConnection();
  conn.setAutoCommit(false);
  adaptor.addTriples(conn, triples.iterator());
  conn.commit();
  conn.setAutoCommit(true);
  conn.close();

  // query for all titles
  QueryResults results = adaptor.query(dataSource.getConnection(),
                                       QueryLanguage.SPO,
                                       0, true, "* <urn:title> *");
  while (results.hasNext()) {
      List<Node> row = results.next();
      System.out.println("The title of " + row.get(0).toString()
              + " is " + row.get(2).toString());
  }
  results.close();

  // delete the triples in a transaction
  conn = dataSource.getConnection();
  conn.setAutoCommit(false);
  adaptor.deleteTriples(conn, triples.iterator());
  conn.commit();
  conn.setAutoCommit(true);
  conn.close();

Once you have a populated triplestore, more advanced queries are possible. However, we don't yet have a SPARQL parser, so you must work at a lower level to perform these kinds of queries. The basic steps are:

  1. Instantiate a GraphQuery object.
  2. Add optional and required QueryElements to it.
  3. Instantiate a GraphQuerySQLProvider using your GraphQuery and a TableManager instance.
  4. Set the names of the values that are being selected by using setTargets(List<String>)
  5. Instantiate a SQLUnionQueryResults object by passing your GraphQuerySQLProvider and a Connection in the constructor.
  6. Iterate the results as in the example above. The values in the result rows will be Node objects (or null).

See the Full API Javadocs for more details.

5. Known Issues / Bugs

6. Coding Standards

Coding standards for the project are documented in coding-standards.xml.

These can be automatically checked using the "ant checkstyle" task. Committed code in subversion should pass the tests but may generate warnings. Most tests generate errors. Warnings are generated for the following:

7. License Information

MPTStore is distributed under the Educational Community License (ECL), v1.0.

The distribution also includes several third-party, open-source libraries, each with it's own license terms.

See the License Information Page for specific terms of all relevant licenses.