/** * This file is part of d:swarm graph extension. * * d:swarm graph extension is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * d:swarm graph extension is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with d:swarm graph extension. If not, see <http://www.gnu.org/licenses/>. */ package org.dswarm.graph.rdf.export; import java.util.Map; import java.util.Map.Entry; import com.google.common.base.Optional; import org.apache.jena.query.Dataset; import org.apache.jena.query.DatasetFactory; import org.neo4j.graphdb.GraphDatabaseService; import org.neo4j.graphdb.Relationship; import org.neo4j.graphdb.Result; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.dswarm.graph.DMPGraphException; import org.dswarm.graph.index.NamespaceIndex; import org.dswarm.graph.model.GraphStatics; import org.dswarm.graph.tx.TransactionHandler; public class DataModelRDFExporter extends BaseRDFExporter { private static final Logger LOG = LoggerFactory.getLogger(DataModelRDFExporter.class); public static final int CYPHER_LIMIT = 1000; private final String dataModelURI; private final String prefixedDataModelURI; private final TransactionHandler tx; public DataModelRDFExporter(final GraphDatabaseService databaseArg, final String dataModelURIArg, final TransactionHandler txArg, final NamespaceIndex namespaceIndex) throws DMPGraphException { super(databaseArg, namespaceIndex); dataModelURI = dataModelURIArg; tx = txArg; prefixedDataModelURI = namespaceIndex.createPrefixedURI(dataModelURIArg); } /** * export a data model identified by dataModelURI * * @return a data model identified by dataModelURI */ @Override public Optional<Dataset> export() throws DMPGraphException { DataModelRDFExporter.LOG.debug("start exporting data for dataModelURI \"{}\" ('{}')", dataModelURI, prefixedDataModelURI); tx.ensureRunningTx(); try { dataset = DatasetFactory.createMem(); boolean requestResults = true; long start = 0; while (requestResults) { final Result result = database.execute("MATCH (n)-[r]->(m) WHERE r." + GraphStatics.DATA_MODEL_PROPERTY + " = \"" + prefixedDataModelURI + "\" RETURN DISTINCT r ORDER BY id(r) SKIP " + start + " LIMIT " + DataModelRDFExporter.CYPHER_LIMIT); if (result == null) { DataModelRDFExporter.LOG.debug("no results for '{}' ('')", dataModelURI, prefixedDataModelURI); break; } start += DataModelRDFExporter.CYPHER_LIMIT; requestResults = false; // please note that the Jena model implementation has its size limits (~1 mio statements (?) -> so one graph (of // one data resource) need to keep this size in mind) if (BaseRDFExporter.JENA_MODEL_WARNING_SIZE == start) { DataModelRDFExporter.LOG.warn("reached {} statements. This is approximately the jena model implementation size limit.", BaseRDFExporter.JENA_MODEL_WARNING_SIZE); } // activate for debug // StringBuilder rows = new StringBuilder("\n\n"); while (result.hasNext()) { final Map<String, Object> row = result.next(); for (final Entry<String, Object> column : row.entrySet()) { final Relationship relationship = (Relationship) column.getValue(); // rows.append(column.getKey()).append(": "); // rows.append(relationship).append(": "); // rows.append("has dataModelURI \"").append(relationship.getProperty("__DATA_MODEL__")).append("\", "); // SR TODO to check: do we need to do all the stuff the RelationshipHandler does? relationshipHandler.handleRelationship(relationship); requestResults = true; // for (Node node : relationship.getNodes()) { // rows.append("NodeID ").append(node.getId()).append(" (is in relationships ["); // for (Relationship relation : node.getRelationships()) { // rows.append(relation.getId()).append(", "); // } // rows.append("]), "); // } // rows.append(";\n"); } // rows.append("\n"); } // rows.append("\n"); // LOG.debug(rows.toString()); result.close(); } tx.succeedTx(); } catch (final Exception e) { final String mesage = "couldn't finish read RDF TX successfully"; tx.failTx(); DataModelRDFExporter.LOG.error(mesage, e); throw new DMPGraphException(mesage); } return Optional.fromNullable(dataset); } }