AEM Convert Excel to JSON Simple Servlet Example

In this article, I present a straightforward yet powerful solution that demonstrates how to seamlessly convert Excel data into JSON format using Adobe Experience Manager (AEM). By implementing a custom servlet, I will illustrate the process of converting an Excel sheet named ‘example.xlsx’ into structured JSON data; it can be downloaded below for you following this tutorial. This tutorial is validated on both AEM 6.5 with the latest Service Pack and AEM as a Cloud Service (AEMaaCS), ensuring its compatibility with diverse AEM environments.

Resource File:
example.xlsx


Request URI:
The request URI for accessing the JSON output through the ExampleServlet that we’ve been discussing would typically look like this:

1
http://localhost:4502/bin/exportexcelfortext.json

JSON Output:

1
2
3
4
5
6
7
8
{
  "people": [
    { "name": "Brian", "age": "100" },
    { "name": "Doris", "age": "20" },
    { "name": "Stuart", "age": "103" },
    { "name": "David", "age": "5" }
  ]
}

Servlet Implementation ExcelExampleServlet.java:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
package com.sourcedcode.core.servlets;

import com.fasterxml.jackson.databind.ObjectMapper;
import org.apache.poi.ss.usermodel.*;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
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.osgi.service.component.annotations.Component;
import javax.servlet.Servlet;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import com.day.cq.dam.api.Asset;

@Component(
        service = { Servlet.class },
        property = {
                "sling.servlet.paths=/bin/exportexcelfortext",
                "sling.servlet.extensions=json",
                "sling.servlet.methods=GET"
        }
)
public class ExcelExampleServlet extends SlingSafeMethodsServlet {
    @Override
    protected void doGet(SlingHttpServletRequest request, SlingHttpServletResponse response) throws IOException {
        try {
            // Get the Excel file path in DAM
            String excelFilePath = "/content/dam/example/example.xlsx";

            // Get the resource resolver
            ResourceResolver resourceResolver = request.getResourceResolver();

            // Check if the Excel file exists
            Resource excelResource = resourceResolver.getResource(excelFilePath);
            if (excelResource == null) {
                response.setStatus(HttpServletResponse.SC_NOT_FOUND);
                return;
            }

            // Adapt the resource to an Asset
            Asset asset = Objects.requireNonNull(excelResource).adaptTo(Asset.class);
            if (asset == null) {
                response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
                return;
            }

            // Get an InputStream from the Asset's original
            InputStream excelInputStream = Objects.requireNonNull(asset).getOriginal().getStream();

            // Process the Excel content and convert it to JSON
            Workbook workbook = new XSSFWorkbook(excelInputStream);
            List<Map<String, String>> jsonData = new ArrayList<>();

            // Iterate through the Excel rows and columns
            Sheet sheet = workbook.getSheetAt(0); // Assuming it's the first sheet
            Row headerRow = sheet.getRow(0); // Assuming the first row is the header row
            int totalColumns = headerRow.getLastCellNum();

            for (int i = 1; i < sheet.getPhysicalNumberOfRows(); i++) {
                Row dataRow = sheet.getRow(i);
                Map<String, String> rowMap = new LinkedHashMap<>();

                for (int j = 0; j < totalColumns; j++) {
                    Cell headerCell = headerRow.getCell(j);
                    Cell dataCell = dataRow.getCell(j);

                    if (headerCell != null && dataCell != null) {
                        // Check the cell type to handle numeric and string values
                        if (dataCell.getCellType() == CellType.STRING) {
                            rowMap.put(headerCell.getStringCellValue(), dataCell.getStringCellValue());
                        } else if (dataCell.getCellType() == CellType.NUMERIC) {
                            // Handle numeric values as integers (remove decimals)
                            int age = (int) dataCell.getNumericCellValue();
                            rowMap.put(headerCell.getStringCellValue(), String.valueOf(age));
                        }
                    }
                }

                jsonData.add(rowMap);
            }

            // Prepare the JSON response
            List<Map<String, String>> peopleList = new ArrayList<>();
            for (Map<String, String> personData : jsonData) {
                Map<String, String> person = new LinkedHashMap<>();
                person.put("name", personData.get("Name"));
                person.put("age", personData.get("Age"));
                peopleList.add(person);
            }

            Map<String, List<Map<String, String>>> jsonResponse = new LinkedHashMap<>();
            jsonResponse.put("people", peopleList);

            // Set response content type and write JSON content to the response
            response.setContentType("application/json");
            response.getWriter().write(new ObjectMapper().writeValueAsString(jsonResponse));
        } catch (Exception e) {
            response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
        }
    }
}

Servlet Depdendencies:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
<dependencies>
    <!-- Apache POI for Excel processing -->
    <dependency>
        <groupId>org.apache.poi</groupId>
        <artifactId>poi</artifactId>
        <version>5.2.3</version>
    </dependency>
    <dependency>
        <groupId>org.apache.poi</groupId>
        <artifactId>poi-ooxml</artifactId>
        <version>5.2.3</version>
    </dependency>
    <!-- Jackson for JSON processing -->
    <dependency>
        <groupId>com.fasterxml.jackson.core</groupId>
        <artifactId>jackson-core</artifactId>
        <version>2.13.0</version>
    </dependency>
    <dependency>
        <groupId>com.fasterxml.jackson.core</groupId>
        <artifactId>jackson-databind</artifactId>
        <version>2.13.0</version>
    </dependency>
</dependencies>

Hello, I am an enthusiastic Adobe Community Advisor and a seasoned Lead AEM Developer. I am currently serving as an AEM Technical Lead at MNPDigital.ca, bringing over a decade of extensive web engineering experience and more than eight years of practical AEM experience to the table. My goal is to give back to the AEM Full Stack Development community by sharing my wealth of knowledge with others. You can connect with me on LinkedIn.

One thought on “AEM Convert Excel to JSON Simple Servlet Example

Leave a Reply

Your email address will not be published. Required fields are marked *


Back To Top