DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Over 2 million developers have joined DZone.
Log In / Join
Refcards Trend Reports
Events Video Library
Refcards
Trend Reports

Events

View Events Video Library

Zones

Culture and Methodologies Agile Career Development Methodologies Team Management
Data Engineering AI/ML Big Data Data Databases IoT
Software Design and Architecture Cloud Architecture Containers Integration Microservices Performance Security
Coding Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks
Culture and Methodologies
Agile Career Development Methodologies Team Management
Data Engineering
AI/ML Big Data Data Databases IoT
Software Design and Architecture
Cloud Architecture Containers Integration Microservices Performance Security
Coding
Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance
Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks

Last call! Secure your stack and shape the future! Help dev teams across the globe navigate their software supply chain security challenges.

Modernize your data layer. Learn how to design cloud-native database architectures to meet the evolving demands of AI and GenAI workloads.

Releasing software shouldn't be stressful or risky. Learn how to leverage progressive delivery techniques to ensure safer deployments.

Avoid machine learning mistakes and boost model performance! Discover key ML patterns, anti-patterns, data strategies, and more.

Related

  • Mastering Git
  • 5 Subtle Indicators Your Development Environment Is Under Siege
  • Loading XML into MongoDB
  • Understanding the Differences Between Repository and Data Access Object (DAO)

Trending

  • Measuring the Impact of AI on Software Engineering Productivity
  • Immutable Secrets Management: A Zero-Trust Approach to Sensitive Data in Containers
  • Understanding IEEE 802.11(Wi-Fi) Encryption and Authentication: Write Your Own Custom Packet Sniffer
  • Agentic AI for Automated Application Security and Vulnerability Management
  1. DZone
  2. Data Engineering
  3. Databases
  4. Creating a Content Repository Using Jackrabbit Oak and MongoDB

Creating a Content Repository Using Jackrabbit Oak and MongoDB

Let's start with some real code to see how we can create a repository with MongoDB. I will be using Maven to build the project and will use Java 8 for this example.

By 
Bishnu Mishra user avatar
Bishnu Mishra
·
Apr. 07, 18 · Tutorial
Likes (6)
Comment
Save
Tweet
Share
19.9K Views

Join the DZone community and get the full member experience.

Join For Free

Content repositories/content stores are essential in the digital world. A content repository/content store is a data store of digital content with an associated set of data management features.

Typically, content repositories act as the storage engine for larger applications such as a content management system or a document management system.

Java provides a content repository specification (JCR) that defines how to access content bi-directionally on a granular level within a content repository.

Apache Jackrabbit is the reference implementation of the Java Content Repository. Jackrabbit Oak is a part/flavor of Apache Jackrabbit that aims to provide a scalable and performant implementation of the Java Content Repository specification.

Oak supports multiple underlying storages for contents, like NoSQL, RDBMS, FS, etc. It also provides features like full-text search.

Oak Storage Flavors

Oak comes with two node storage flavors: segment and document.

Segment storage is optimized for max performance in standalone environments, whereas document storage is designed for scalability in clustered environments.

In this article, I will focus on the document storage flavor, which stores data in document-oriented format. The document store supports a number of backends, like MongoDocumentStore for MongoDB, RDBDocumentStore, and MemoryDocumentStore.

This article will cover MongoDocumentStore and explain how to manage content using Jackrabbit APIs and MongoDB as backend storage.

Now, let's start with some real code to see how we can create a repository with MongoDB. I will be using Maven to build the project and will use Java 8 for this example.

Maven Dependency

<dependency>
<groupId>org.apache.jackrabbit</groupId>
<artifactId>oak-jcr</artifactId>
<version>1.7.6</version>
</dependency>
<dependency>
<groupId>javax.jcr</groupId>
<artifactId>jcr</artifactId>
<version>2.0</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.mongodb/mongo-java-driver -->
<dependency>
<groupId>org.mongodb</groupId>
<artifactId>mongo-java-driver</artifactId>
<version>3.4.3</version>
</dependency>

We need oak-jcr, jcr, and mongo-java-driver dependencies for using Jackrabbit libraries and connecting to MongoDB server.

Build/Initialize the Repository

The javax.jcr.Repository represents a content repository stored in MongoDB. The below code can be used to create a repository.

String uri = "mongodb://" + host + ":" + port;
DocumentNodeStore ns = new DocumentMK.Builder().setMongoDB(uri, "oak_demo", 16).getNodeStore();
Repository repo = new Jcr(new Oak(ns)).createRepository();

Here, oak_demo is the Mongo database to be connected.

Creating Nodes

Items or contents in node store are managed in nodes. Once we create the repository, we can use javax.jcr.Repository to log into the repository and get a javax.jcr.Session. The session is used to interact with the repository.

Session session = repository.login(new SimpleCredentials("admin", "admin".toCharArray()));
Node parentNode = session.getRootNode();
Node childNode = parentNode.addNode("childNodeName");
childNode..setProperty("propertyName", "propertyValue");

Creating File Nodes

A File node is a different type of node than the normal node that we created in the above step. The type for the node we created earlier is "nt:unstructured:. The node type for file node is "nt:file". A File node is added to an existing node (at path /node1/node2).

Node fileNodeParent = session.getNode("pathToParentNode"); // /node1/node2/
Node fileNode = fileNodeParent.addNode("theFile", "nt:file");
Node content = fileNode.addNode("jcr:content", "nt:resource");
InputStream is = getFileInputStream();//Get the file data as stream.
Binary binary = session.getValueFactory().createBinary(is);
content.setProperty("jcr:data", binary);
session.save();
// To enable versioning use VersionManager
VersionManager vm = session.getWorkspace().getVersionManager();
vm.checkin(fileNode.getPath());

The File node needs to have a node of type nt:resource, which will store the file data as binary.

Retrieving File From Repository

Node fileNodeParent = session.getNode("pathToParentNode"); // /node1/node2/
Node fileContent = fileNodeParent.getNode("theFile").getNode("jcr:content");
Binary bin = fileContent.getProperty("jcr:data").getBinary();
InputStream stream = bin.getStream();
byte[] bytes = IOUtils.toByteArray(stream);
bin.dispose();
stream.close();

Retrieving Version of a Content

VersionManager vm = session.getWorkspace().getVersionManager();
javax.jcr.version.VersionHistory versionHistory = vm.getVersionHistory("filePath");
Version currentVersion = vm.getBaseVersion(filePath);// This is the current version of the file
VersionIterator itr = versionHistory.getAllVersions();// gets all the versions of that content

We can iterate over the VersionIterator to get specific versions and its properties.

Similarly, we can restore a specific version of a content.

//Restoring a specific version
VersionManager vm = session.getWorkspace().getVersionManager();
Version version = (Version) session.getNodeByIdentifier("versionId");
vm.restore(version, false);// boolean flag governs what happens in case of an identifier collision.

Likewise, other operations like deleting and editing files can be performed on content stored in the repository.

Conclusion

This is article covers basic steps to use the Jackrabbit Oak library with MongoDB. There are other features that Oak provides that are not covered in this article like indexing, searching documents, access control mechanisms, etc.

The complete example can be found in this GitHub repository.

Thanks for reading this article and please provide your opinions in the comment section.

Repository (version control) Content repository MongoDB

Opinions expressed by DZone contributors are their own.

Related

  • Mastering Git
  • 5 Subtle Indicators Your Development Environment Is Under Siege
  • Loading XML into MongoDB
  • Understanding the Differences Between Repository and Data Access Object (DAO)

Partner Resources

×

Comments

The likes didn't load as expected. Please refresh the page and try again.

ABOUT US

  • About DZone
  • Support and feedback
  • Community research
  • Sitemap

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Core Program
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 3343 Perimeter Hill Drive
  • Suite 100
  • Nashville, TN 37211
  • support@dzone.com

Let's be friends: