When debugging code I frequently need to determine what the underlying AEM product code is doing. This helps me better understand why I’m seeing a particular bug.
There are also times where I know what I want to do, but there isn’t much documentation around the functionality I’m trying to use. Can I give it my own code to execute when it’s done? Can I configure an existing bundle to do what I want? Does it have an option to execute a workflow when it’s done?
Also, are there log statements in the AEM product code that may help me debug an issue in Production? If I can’t reproduce the issue on a local environment (or don’t have the time), I can’t connect a debugger to a production system.
Today I’m going to share my secret behind finding the AEM product code jar file and decompiling. In the past I’ve done it in different ways, but this is the quickest way I’ve found to get the code decompiled on my laptop. (If you have a better way please share in the comments.)
1. Determine the OSGi bundle name
This is always the most difficult part. Sometimes, I can just guess the name well enough that I can search for it (see step 2). Other times it is some obscure name. As an example, in the code I was analyzing, I knew an InDesign Server job was started with the topic “dam/proxy/ids/job“.
I knew that there must be a job consumer for this job topic. I had already setup logging for sling jobs as I mention in Debug AEM Commit Issues. From this, I knew that com.day.cq.dam.ids.impl.IDSJobProcessor was the job consumer class.
Since a common InDesign Server abbreviation is IDS, I tried searching the Felix console for “ids“. I did get one result, but it seemed related to print and not jobs.
My second guess was to search for “indesign” and Huzzah! I found it! The bundle I’m looking for is com.day.cq.dam.cq-dam-indesign.
2. Search your crx-quickstart directory
Step 1 really is optional and you could just skip right to step 2, but it does give you some context for what we are doing in step 2. So to actually find the jar and decompile it you need to first go to the /crx-quickstart/launchpad/felix directory.
This directory contains all of the product related bundles right on your hard drive. If you did follow step 1, then you may have noticed that hovering over the bundle gives you a link such as http://localhost:4502/system/console/bundles/170. Well, in /crx-quickstart/launchpad/felix, all you need to do is scroll to the bundle312 folder and find the jar below that folder. You can then just skip to step 5.
I don’t normally perform step 1 and skip straight to just guessing what the bundle name is directly in /crx-quickstart/launchpad/felix. So again, I first searched for “ids” and then for “indesign” to find what I was looking for. The bundle.info file contains the actual name for the OSGi bundle.
Search the /crx-quickstart/launchpad/felix directory for the bundle name
3. Open bundle.info
If you see multiple bundle.info results or you aren’t sure which bundle you are looking for, you will need to open each one to find the right one. In this case I opened bundle.info and see this is the bundle.info associated with cq-dam-indesign-5.11.30.jar.
4. Open the containing folder
Once you have the correct bundle.info file, right click the file and choose Show in Enclosing Folder.
You should then see a folder which is a sibling to the bundle.info file.
In my example I’m opening the version0.1 folder. Inside I find a bundle.jar. It turns out all the bundle jars are named bundle.jar and the bundle.info is the only way to easily determine what’s in it. You could decompile each bundle.jar, but that would take a lot of time and effort.
5. Decompile Jar
Now that you have found the jar, it’s time to decompile. Use a Java decompiler such as JD-GUI to view the code. In my example I’ve opened the jar and can see the com.day.cq.dam.ids.impl.IDSJobProcessor job consumer and it subscribes to the “dam/proxy/ids/job” job topic.
Looking through the code deeper, I see that you can provide a workflow model as a parameter to the job. An instance of the workflow model will then be started once the InDesign Server job has completed. This is exactly what I was looking for in my example!
Bonus
Once you have the jar file and you have connected your IDE’s debugger (such as Intellij) to your local instance, you can now add the jars to your classpath and set breakpoints in decompiled AEM code. I was able to step through the code above and see exactly what was available at runtime.
Let me know if you are interested in a detailed tutorial for doing this in a specific IDE and I can write up the details.
Summary
If I’m stuck on a problem or need to dig one level deeper, decompiling the AEM bundles will help get me unstuck. There is an easy way to find the jar files already located on your hard drive. All you need to know is the bundle name and then you can easily search for the jar. Once you have the jar you can understand what the code is doing and even use the jar at runtime to debug issues.