May 3, 2020
Estimated Post Reading Time ~

Converting AEM/Sling Resources to JSON

You can easily convert an AEM Page, Sling Resource, or JCR Node to JSON using the org.apache.sling.commons.json.jcr.JsonItemWriter class. This simple but useful utility allows you to dump a Node into a JSONObject. It also allows you to dump the Node into a JSON string into a PrintWriter for use in servlets for example.

The constructor accepts a Set of Strings representing JCR properties to exclude from the JSON output. You may want to ignore the standard cq:*, sling:*, and jcr:* properties while allowing only your custom properties to populate the JSON.

The overloaded dump methods allow you to pass in the recursion level similar to how you would use a selector when making AJAX calls to the Default Get Servlet. Just as you can cURL /content/geometrixx/en.json, /content/geometrixx/en.1.json and /content/geometrixx/en.-1.json, you can pass in a positive integer for the recursion level as well as -1 for infinite recursion.

Likewise, just as you can cURL /content/geometrixx/en.tidy.json, you can specify whether you want the JSON output nicely formatted or not.

The following examples demonstrate the JsonItemWriter utilizing a PrintWriter in a servlet and a JSONObject in a standard Java class.
ConvertResourceToJSON.java
package com.nateyolles.aem;

import org.apache.sling.api.resource.Resource;
import org.apache.sling.api.resource.ResourceResolver;
import org.apache.sling.commons.json.JSONException;
import org.apache.sling.commons.json.JSONObject;
import org.apache.sling.commons.json.jcr.JsonItemWriter;

import javax.jcr.Node;
import javax.jcr.RepositoryException;

import java.io.StringWriter;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
* Example of how to easily turn a Node into a JSONObject.
*/
public class ConvertResourceToJSON {

/** The logger */
private static final Logger LOGGER = LoggerFactory.getLogger(ConvertResourceToJSON.class);

/**
* Get the JSON representation of a Resource
*
* @param resolver Resolver to get resource
* @param resource Resource to turn into JSON
* @return JSON representation of the resource
*/
public JSONObject resourceToJSON(final ResourceResolver resolver, final Resource resource) {
final Node node = resource.adaptTo(Node.class);
final StringWriter stringWriter = new StringWriter();
final JsonItemWriter jsonWriter = new JsonItemWriter(null);

JSONObject jsonObject = null;

try {
/* Get JSON with no limit to recursion depth. */
jsonWriter.dump(node, stringWriter, -1);
jsonObject = new JSONObject(stringWriter.toString());
} catch (RepositoryException | JSONException e) {
LOGGER.error("Could not create JSON", e);
}

return jsonObject;
}
}

ResourceToJSONServlet.java
package com.nateyolles.aem;

import org.apache.felix.scr.annotations.sling.SlingServlet;
import org.apache.sling.api.SlingHttpServletRequest;
import org.apache.sling.api.SlingHttpServletResponse;
import org.apache.sling.api.resource.Resource;
import org.apache.sling.api.resource.ResourceResolver;
import org.apache.sling.api.servlets.SlingSafeMethodsServlet;
import org.apache.sling.commons.json.JSONException;
import org.apache.sling.commons.json.jcr.JsonItemWriter;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.jcr.Node;
import javax.jcr.RepositoryException;
import javax.servlet.ServletException;

import java.io.IOException;
import java.io.PrintWriter;
import java.util.HashSet;
import java.util.Set;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
* Sample servlet which easily converts a Node as JSON to the PrintWriter.
*/
@SlingServlet(paths={"/bin/foo"})
public class ResourceToJSONServlet extends SlingSafeMethodsServlet {

/** The logger */
private static final Logger logger = LoggerFactory.getLogger(ResourceToJSONServlet.class);

@Override
protected void doGet(SlingHttpServletRequest request, SlingHttpServletResponse response)
throws ServletException, IOException {

response.setCharacterEncoding("UTF-8");
response.setContentType("application/json");

final PrintWriter out = response.getWriter();
final ResourceResolver resolver = request.getResourceResolver();
final Resource resource = resolver.getResource("/content/my-app/us/en/my-page/jcr:content");
final Node node = resource.adaptTo(Node.class);

/* Node properties to exclude from the JSON object. */
final Set<String> propertiesToIgnore = new HashSet<String>() {{
add("jcr:created");
add("jcr:createdBy");
add("jcr:versionHistory");
add("jcr:predecessors");
add("jcr:baseVersion");
add("jcr:uuid");
}};

JsonItemWriter jsonWriter = new JsonItemWriter(propertiesToIgnore);

try {
/* Write the JSON to the PrintWriter with max recursion of 1 level and tidy formatting. */
jsonWriter.dump(node, out, 1, true);
response.setStatus(SlingHttpServletResponse.SC_OK);
} catch (RepositoryException | JSONException e) {
logger.error("Could not get JSON", e);
response.setStatus(SlingHttpServletResponse.SC_INTERNAL_SERVER_ERROR);
}
}
}


By aem4beginner

No comments:

Post a Comment

If you have any doubts or questions, please let us know.