Contents
Objective
After reading this Article, You should have an Understanding of –
- Reading the existing package through JcrPackageManager.
- Creating, building, and installing packages through a Java API.
Introduction
In AEM Development, we mostly come across the situation of having to deal with the AEM Package with Java Code. For example, you have to archive the content available in a folder daily and store it in cloud storage. In this case, you can create a package and send it to cloud storage through the Java API. Another case may be to read the package to get the content path. So we will cover all the approaches to creating, reading, installing, building, and uploading features of the package through the Java API.
Hence, without any further delay, let’s get started:
Dependency to use Package Manager API
Dependency in core pom.xml
org.apache.jackrabbit.vault
org.apache.jackrabbit.vault
3.2.8
Reading the package through JcrPackageManager
The JcrPackageManager API helps to get package names, group names, filter sets, and other required details. The below servlet shows the use of the package manager api for getting AEM package details programmatically. These details can be used to create new packages. So lets see the implementation code :
AEMPackageReading.java
package com.adobe.learning.core.servlets;
import com.google.gson.JsonObject;
import org.apache.commons.lang3.StringUtils;
import org.apache.jackrabbit.vault.fs.api.PathFilterSet;
import org.apache.jackrabbit.vault.packaging.JcrPackage;
import org.apache.jackrabbit.vault.packaging.JcrPackageDefinition;
import org.apache.jackrabbit.vault.packaging.JcrPackageManager;
import org.apache.jackrabbit.vault.packaging.PackagingService;
import org.apache.sling.api.SlingHttpServletRequest;
import org.apache.sling.api.SlingHttpServletResponse;
import org.apache.sling.api.resource.ResourceResolver;
import org.apache.sling.api.servlets.HttpConstants;
import org.apache.sling.api.servlets.SlingSafeMethodsServlet;
import org.osgi.framework.Constants;
import org.osgi.service.component.annotations.Component;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.jcr.Node;
import javax.jcr.Session;
import javax.servlet.Servlet;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
/**
* @author Shiv
* http://localhost:4502/bin/packageReading?packagePath=/etc/packages/my_packages/sample.zip
*/
@Component(service = Servlet.class, property = {Constants.SERVICE_DESCRIPTION + "= Package Reading",
"sling.servlet.paths=" + "/bin/packageReading", "sling.servlet.methods=" + HttpConstants.METHOD_GET
})
public class AEMPackageReading extends SlingSafeMethodsServlet {
private static final Logger logger = LoggerFactory.getLogger(AEMPackageReading.class);
ResourceResolver resourceResolver;
String packageName = StringUtils.EMPTY;
List filterPaths;
String groupName = StringUtils.EMPTY;
JsonObject jsonObject;
@Override
protected void doGet(SlingHttpServletRequest request, SlingHttpServletResponse response) {
// Getting package path from query parameter
String packagePath = request.getParameter("packagePath");
//Getting resource resolver and session
resourceResolver = request.getResourceResolver();
Session session = resourceResolver.adaptTo(Session.class);
//Getting JcrPackageManager with the help of session
JcrPackageManager jcrPackageManager = PackagingService.getPackageManager(session);
//Getting the Node from Package
Node packageNode = Objects.requireNonNull(resourceResolver.getResource(packagePath)).adaptTo(Node.class);
assert packageNode != null;
jsonObject = new JsonObject();
//Get JcrPackage with the help of Package Node
try (JcrPackage jcrNodePackage = jcrPackageManager.open(packageNode)) {
assert jcrNodePackage != null;
//Getting Package Definition
JcrPackageDefinition jcrNodeDefinition = jcrNodePackage.getDefinition();
assert jcrNodeDefinition != null;
//Getting Package and Group Name
packageName = jcrNodeDefinition.get("name");
groupName = jcrNodeDefinition.get("group");
jsonObject.addProperty("name", packageName);
jsonObject.addProperty("group", groupName);
//Getting Path Filter Set from Package definition using getMetaImf Method
List pathFilterSetList = Objects.requireNonNull(jcrNodeDefinition.getMetaInf().getFilter()).getFilterSets();
filterPaths = new ArrayList<>();
//Adding all the filter in array list
for (PathFilterSet currentFilter : pathFilterSetList) {
filterPaths.add(currentFilter.getRoot());
}
jsonObject.addProperty("filter", filterPaths.toString());
response.getWriter().write("Package Details : \n");
response.getWriter().write(jsonObject.toString());
} catch (Exception e) {
logger.error("Error in Package Reading {}", e.getMessage());
}
}
}
Creating, building, and installing packages through a Java API
When you work with back-up creation or archiving of assets or pages weekly or monthly, the first thought that comes into your mind is to create a package programmatically and schedule the package creation weekly. Here you will see a servlet showing how we can create a package with a custom name, group name, and filters. You can also build and install it using Java Code. So let’s see the implementation code:
AEMPackageCreation.java
package com.adobe.learning.core.servlets;
import org.apache.commons.lang3.StringUtils;
import org.apache.jackrabbit.vault.fs.api.PathFilterSet;
import org.apache.jackrabbit.vault.fs.api.ProgressTrackerListener;
import org.apache.jackrabbit.vault.fs.config.DefaultWorkspaceFilter;
import org.apache.jackrabbit.vault.fs.io.ImportOptions;
import org.apache.jackrabbit.vault.packaging.JcrPackage;
import org.apache.jackrabbit.vault.packaging.JcrPackageDefinition;
import org.apache.jackrabbit.vault.packaging.JcrPackageManager;
import org.apache.jackrabbit.vault.packaging.PackagingService;
import org.apache.jackrabbit.vault.util.DefaultProgressListener;
import org.apache.sling.api.SlingHttpServletRequest;
import org.apache.sling.api.SlingHttpServletResponse;
import org.apache.sling.api.resource.ResourceResolver;
import org.apache.sling.api.servlets.HttpConstants;
import org.apache.sling.api.servlets.SlingSafeMethodsServlet;
import org.osgi.framework.Constants;
import org.osgi.service.component.annotations.Component;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.jcr.Session;
import javax.servlet.Servlet;
import java.util.ArrayList;
import java.util.List;
/**
* @author Shiv
* http://localhost:4502/bin/packageCreation?packageName=sample&groupName=my_packages
*/
@Component(service = Servlet.class, property = {Constants.SERVICE_DESCRIPTION + "= Package Creation",
"sling.servlet.paths=" + "/bin/packageCreation", "sling.servlet.methods=" + HttpConstants.METHOD_GET
})
public class AEMPackageCreation extends SlingSafeMethodsServlet {
private static final Logger logger = LoggerFactory.getLogger(AEMPackageCreation.class);
ResourceResolver resourceResolver;
String packageName = StringUtils.EMPTY;
private List filterPaths;
String groupName = StringUtils.EMPTY;
@Override
protected void doGet(SlingHttpServletRequest request, SlingHttpServletResponse response) {
// Getting package name & group name from query parameter
packageName = request.getParameter("packageName");
groupName = request.getParameter("groupName");
//Setting up the filter pages for package
filterPaths = new ArrayList<>();
filterPaths.add("/content/learning/us/en/samplePage");
filterPaths.add("/content/learning/us/en/learningPage");
//Getting resource resolver and session
resourceResolver = request.getResourceResolver();
Session session = resourceResolver.adaptTo(Session.class);
//Getting JcrPackageManager with the help of session
JcrPackageManager jcrPackageManager = PackagingService.getPackageManager(session);
//Creating JcrPackage with the help of name and group
try (JcrPackage jcrPackage = jcrPackageManager.create(groupName, packageName)) {
//Getting JcrPackageDefinition
JcrPackageDefinition definition = jcrPackage.getDefinition();
//Getting DefaultWorkspaceFilter and setting up filter
DefaultWorkspaceFilter filter = new DefaultWorkspaceFilter();
/*filterPaths is the package filters*/
for (String filterPath : filterPaths) {
PathFilterSet pathFilterSet = new PathFilterSet();
pathFilterSet.setRoot(filterPath);
filter.add(pathFilterSet);
}
//if autoSave is false then we have to explicitly save the session.
assert definition != null;
definition.setFilter(filter, true);
//This method will build the package.
ProgressTrackerListener listener = new DefaultProgressListener();
jcrPackageManager.assemble(jcrPackage, listener);
//Method to install the Package and Specify the import configurations
ImportOptions importOption = new ImportOptions();
jcrPackage.install(importOption);
response.getWriter().write("Package created successfully !!!");
} catch (Exception e) {
logger.error("Error in Package Creation {}", e.getMessage());
}
}
}
Conclusion
- So in this post, we tried to cover most of the operations in the AEM Package through the Java API. I hope you enjoyed this post. If you find it useful, leave us a comment. I would love to hear your thoughts and suggestions to make it better. Also, you can connect with me on LinkedIn.
This is a great tip, particularly for those new to the blogosphere.
Short but very accurate info… Thanks for sharing this one.
A must-read ρost!
Hi ,
Is it possible to translate the path when we create this package? Meaning /content/dam/abc should be written as “/content/dam/bcd” when the package gets created?
I would like to thank you an eye to the efforts youve got produced in article this post. I am hoping the exact unaltered most https://googles7.com