Article summary

Note:

This article is OUTDATED. To learn how to write an AEM component that uses web services, see this community articleCreating an AEM HTML Template Language Component that displays data from a SOAP Web Service.

Summary

Discusses how to create an AEM 6 Touch UI component that invokes an OSGi bundle that contains Java proxy classes that consume a third-party web service. The Java proxy classes are used to create an OSGi bundle that is deployed to AEM. In addition, discusses how to invoke an OSGi bundle operation from a Touch UI component.

If you are interested in using a previous version of AEM (5.x) and web services, see Creating Adobe Experience Manager bundles using Apache CXF that consume web services.

Digital Marketing Solution(s) Adobe Experience Manager (Adobe CQ)
Audience
Developer (intermediate)
Required Skills
Java, web services, XML
Tested On Adobe Experience Manager 6

Note:

This workflow works on Adobe CQ; however, you may encounter the following exception:

Caused by: java.lang.ClassNotFoundException: com.sun.xml.internal.ws.spi.ProviderImpl
at org.apache.sling.commons.classloader.impl.ClassLoaderFacade.loadClass(ClassLoaderFacade.java:127)
at java.lang.ClassLoader.loadClass(Unknown Source)
at javax.xml.ws.spi.FactoryFinder.safeLoadClass(Unknown Source)
... 107 more
Solution:
To fix this issue and ensure that you can create a bundle that consumes web services as described in this article, modify the sling.properties file located in the crx-quickstart\conf folder. Add the following line of code to this file: sling.bootdelegation.com.sun=com.sun.*. Then restart the server. Once you perform this task, you can follow along with this article.

Introduction

You can create an Adobe Experience Manager (AEM) 6 Touch component that displays data obtained from a third-party web service. For example, assume that you use AEM to create a web site for a government department that tracks weather information. In this situation, you can create an AEM Touch UI component that retrieves data from a third-party web service and displays the data in an AEM web page.

The following illustration shows AEM retrieving data from a third-party web service.

WebService

You can develop an AEM Touch UI component that can be dragged from the AEM 6 side rail and dropped onto an AEM web page. 

TouchUIWebService

The component displays weather information obtained from a third-party WSDL. The Touch UI component invokes an OSGi bundle that contains Java proxy classes that are created by using Apache CFX. The following illustration shows the AEM Touch UI component displaying information obtained from a third-party web service. Notice that the USA ZIP code is entered into the AEM Touch UI dialog. 

 

webserviceZipDialog

You can use a tool such as Apache CXF WSDL to Java to generate the Java proxy classes that are based on the WSDL of an external web service. For information, see Apache CXF.

Then you can use these Java proxy classes within your OSGi bundle. The OSGi bundle that is created in this development article contains Java proxy classes that consume operations exposed by the following third-party WSDL:

An OSGi bundle lets you dynamically load, unload, configure, and control the Java module without restarting the server. The tool that is used in this development article to create the OSGi bundle is Eclipse. All of the instructions needed to build an OSGi bundle that contains Java web service proxy classes are covered in this development article.

Note:

Before following along with this development article, make sure that you install AEM 6 and have it running. In addition, ensure that you have Eclipse 3.6.1 or higher. Eclipse is used to create the OSGi bundle that contains the Java proxy classes.

To create an AEM Touch UI component that diaplays data from a third-party SOAP stack, perform the following tasks:

  1. Create an AEM application folder structure. 
  2. Create a template on which the page component is based. 
  3. Create a render component that uses the template. This page lets an author drag the web service Touch UI component from the AEM side rail to the web page.
  4. Create Java proxy classes using Apache CXF that consume the soap stack of the external web service. 
  5. Create the OSGi bundle that contains the Java proxy classes. 
  6. Create an AEM Touch UI component that invokes operations exposed by the OSGi bundle.  The Touch UI component displays returned data. 
  7. Create a new web page that displays data returned by the OSGi bundle.

Create an AEM application folder structure

You can create an application folder structure that contains templates, components, and pages. Before you create application assets such as templates, components, or pages, you create an application, which is essentially a specific folder. You can create this folder structure by using CRXDE Lite.

CQAppSetup

The following describes each application folder:

  • application name: contains all of the resources that an application uses. The resources can be templates, pages, components, and so on
  • components: contains components that your application uses
  • page: contains page components. A page component is a script such as a JSP file
  • global: contains global components that your application uses
  • template: contains templates that you can base page components on
  • src: contains source code that comprises an OSGi component (this development does not create an OSGi bundle using this folder or CRXDE. Rather Eclipse is used)
  • install: contains a compiled OSGi bundles container

To create an application folder structure, perform these steps:

  1. To view the CQ welcome page, enter the URL http://[host name]:[port] into a web browser. For example, http://localhost:4502.
  2. Select CRXDE Lite.
  3. Right-click the apps folder (or the parent folder), select Create, Create Folder.
  4. Enter the folder name into the Create Folder dialog box. Enter weatherapp
  5. Repeat steps 1-4 for each folder specified in the previous illustration. 
  6. Click the Save All button. 

Note:

You have to click the Save All button when working in CRXDE Lite for the changes to be made.

Create an AEM Template

You can create a template by using CRXDE Lite. A CQ template enables you to define a consistent style for the pages in your application. A template comprises of nodes that specify the page structure. For more information, see Templates.

To create a CQ template, perform these steps:

1. To view the CQ welcome page, enter the URL http://[host name]:[port] into a web browser. For example, http://localhost:4502.

2. Select CRXDE Lite.

3. Right-click the template folder (within your application), select Create, Create
Template.

4. Enter the following information into the Create Template dialog box:

  •  Label: The name of the template to create. Enter weathertemplate.
  • Title: The title that is assigned to the template
  • Description: The description that is assigned to the template
  • Resource Type: The component's path that is assigned to the template and copied to implementing pages. Enter weatherapp/components/page/weathertemplate.
  • Ranking: The order (ascending) in which this template will appear in relation to other templates. Setting this value to 1 ensures that the template appears first in the list.

5. Add a path to Allowed Paths. Click on the plus sign and enter the following value: /content(/.*)?.

6. Click Next for Allowed Parents.

7. Select OK on Allowed Children.

Create a render component that uses the template

Components are re-usable modules that implement specific application logic to render the content of your web site. You can think of a component as a collection of scripts (for example, JSPs, Java servlets, and so on) that completely realize a specific function. In order to realize this functionality, it is your responsibility as a CQ developer to create scripts that perform specific functionality. For more information, see Components.

By default, a component has at least one default script, identical to the name of the component.
To create a render component:

1. To view the CQ welcome page, enter the URL http://[host name]:[port] into a web browser. For example, http://localhost:4502.

2. Select CRXDE Lite.

3. Right-click /apps/weatherapp/components/page, then select
Create, Create Component.

4. Enter the following information into the Create Component dialog box:

  • Label: The name of the component to create. Enter weathertemplate.
  • Title: The title that is assigned to the component
  • Description: The description that is assigned to the template
  • Super Type:foundation/components/page (in AEM 6, you specify this value for page components. In previous versions of AEM, this was not required.)

5. Select Next for Advanced Component Settings and Allowed Parents.

6. Select OK on Allowed Children.

7. Open the weatertemplate.jps located at: /apps/weatherapp /components/page/weathertemplate /weathertemplate.jsp.

8. Enter the following HTML code:

<html>
<%@include file="/libs/foundation/global.jsp" %>
<cq:include script="/libs/wcm/core/components/init/init.jsp"/>
<body>
<h1>Here is where your Touch UI Web Service component will go</h1>
<cq:include path="par" resourceType="foundation/components/parsys" />
</body>
</html>

Create Java proxy classes using Apache CXF that consume the soap stack of the external web service

You can use Apache CXF to convert a third-party WSDL to Java proxy classes. These Java classes enable you to invoke operations exposed by the soap stack. In this development article, the operations are exposed by the following WSDL:

http://wsf.cdyne.com/WeatherWS/Weather.asmx?WSDL

To create Java proxy classes using Apache CXF, perform these steps:

1. Download Apache CFX on the client computer. (See http://cxf.apache.org/download.html.)

2. Install JDK 1.6 or later.

  • Add the JDK bin directory to your class path.
  • Add the JRE bin directory to your class path. This bin is located in the [JDK_INSTALL_LOCATION]/jre directory.
  • Set the JAVA_HOME environment variable to the directory where you installed the JDK. The JDK 1.6 includes the wsimport program used in the build.xml file. JDK 1.5 does not include that program.

3. Open the command line and change the directory to the apache-cxf-2.6.0\bin. This directory contains the wsdl2java BAT file that you use.

4. Enter the following command:

wsdl2java -p com.aem.ws -d c:\proxy http://wsf.cdyne.com/WeatherWS/Weather.asmx?WSDL

The -p argument specifies the package in which the Java proxy classes are placed into. The -d argument specifies the directory in which the Java proxy classes are placed into. Finally the URL of the WSDL is specified.   

5. Package the JAVA files into a JAR file by using Eclipse. Perform the following tasks:

  • Create a new Java project that is used to package the proxy JAVA files into a JAR file.
  • Create a source folder in the project.
  • Create a com.aem.ws package in the source folder. This is the package to which the Java proxy classes belong.
  • Add the JAR files to the Java project that are located in apache-cxf-2.6.0\lib.
  • Select the com.aem.ws package and then import the JAVA files  (see the illustration after this list).
  • Set the Java compiler's compliance level to 5.0 or greater.
  • Build the project.
  • Export the project as a JAR file named WeatherService.jar.

The following illustration shows the Java proxy files that Apache CXF creates.

CXFFiles

Note:

If there are errors in the Java proxy files, simply comment out the Java code. These commented out lines of code do not affect the application logic in this development article.

Create the OSGi bundle that contains the Java proxy classes

Create an OSGi bundle that contains WeatherService.jar file. Once you upload the OSGi bundle to Adobe Experience Manager, you can call the methods located in Java files that are part of the com.aem.ws package. That is, the OSGi bundle is able to invoke operations exposed by the WSDL. To create the OSGi bundle, you can use another Eclipse project. An OSGi bundle is essentially a collection of Java files and a MANIFEST.MF file.

To create an OSGi bundle that contains Java proxy classes using Eclipse, perform these steps:

1. Start Eclipse (Indigo). The steps below have been tested on Eclipse Java EE IDE for Web Developers version Indigo Service Release 1.

2. Select File, New, Other.

3. Under the Plug-in Development folder, choose Plug-in from Existing JAR Archives.

4. In the JAR selection dialog, click the Add external button, and browse to the WeatherService.jar file that you just created.

5. Click Next.

6. In the Plug-in Project properties dialog, ensure that you check the checkbox for Analyze library contents and add dependencies (see the following illustration).

7. Make sure that the Target Platform is the standard OSGi framework (see the following illustration).

8. Ensure the checkboxes for Unzip the JAR archives into the project and Update references to the JAR files are both checked (see the following illustration).

WSBunlde

9. Click Next, and then Finish.

10. Click on the Runtime tab.

11. Make sure that the Exported Packages list is populated.

12. Make sure these have been added under the Export-Package header in MANIFEST.MF. Remove the version information in the MANIFEST.MF file. Version numbers can cause conflicts when you upload the OSGi bundle.

13. Ensure that the Import-Package header in MANIFEST.MF is also populated. The following code represents the MANIFEST.MF file.

Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: ApacheCXFWSOSGI
Bundle-SymbolicName: ApacheCXFWSOSGI
Bundle-Version: 1.0.0
Export-Package: com.aem.ws,
Import-Package: javax.xml.bind,
 javax.xml.ws,
 javax.xml.datatype,
 javax.xml.namespace
Bundle-RequiredExecutionEnvironment: JavaSE-1.6

14. Save the project.

15. Build the OSGi bundle by right clicking the project in the left pane, choose Export, Plug-in Development, Deployable plug-ins and fragments and click Next.

16. Select a location for the export (C:\TEMP) and click Finish. (Ignore any error messages).

17. In C:\TEMP\plugins, you should now find the OSGi bundle with a name similar to cdynewebservice_1.0.0.jar.

18. Login to Apache Felix Web Console at http://server:port/system/console/bundles (default admin user = admin with password= admin).

19. Sort the bundle list by Id and note the Id of the last bundle.

20. Click the Install/Update button.

21. Check the Start Bundle checkbox.

22. Browse to the bundle JAR file you just built. (C:\TEMP\plugins).

23. Click Install.

24. Click the Refresh Packages button.

25. Check the bundle with the highest Id.

26. Your new bundle should now be listed with the status Active.

27. If the status is not Active, check the CQ error.log for exceptions. If you get “org.osgi.framework.BundleException: Unresolved constraint” errors, check the MANIFEST.MF for strict version requirements which might look as follows: javax.xml.namespace; version=”3.1.0”

28. If the version requirement causes problems, remove it so that the entry looks like this: javax.xml.namespace,.

29. If the entry is not required, remove it entirely.

30. Rebuild the bundle.

31. Delete the previous bundle and deploy the new one.

32. If all goes well, the CQ error.log should have log entries such as follows:
*INFO* [FelixDispatchQueue] com.oracle.jdbc BundleEvent STARTED
*INFO* [FelixDispatchQueue] org.apache.felix.framework FrameworkEvent PACKAGES REFRESHED

Note:

Now the Java proxy classes that know how to invoke operations exposed by the WSDL are part of the OSGI service container. You can create Java proxy objects and call their methods from a JSP.

Create an AEM Touch UI component that invokes operations exposed by the OSGi bundle 

Create the AEM Touch UI component by using CRXDE Lite:

1. Right click on /apps/weatherapp/components and then select New, Component.

2. Enter the following information into the Create Component dialog box:

  • Label: The name of the component to create. Enter heroweather.
  • Title: The title that is assigned to the component. Enter heroweather.
  • Description: The description that is assigned to the template. Enter heroweather.
  • Super Resource Type: Enter foundation/components/parbase.
  • Group: The group in the side kick where the component appears. Enter General. (The heroweather component is located under the General heading in the Touch UI side rail.)
  • Allowed parents: Enter */*parsys.

3. Click Ok.

Add a dialog to the Touch UI component

A dialog lets an author click on the component in the Touch UI (or Classic UI) view during design time and enter values that are used by the component. The component created in this development article lets the AEM author enter a USA ZIP code used in the web service operation.

A dialog that is built for the Touch UI is defined by using nodes of type un:structured. You define the type of control on the Touch UI dialog by setting the node's sling:resourceType property. For example, to define a text field on a Touch UI dialog, set the  sling:resourceType property to granite/ui/components/foundation/form/textfield.

For more information about creating a dialog for Touch UI components, see Creating your first Adobe Experience Manager Touch UI component.

Note:

When building a dialog for the Touch UI view, you define the type of control (for example, a text field) by setting the sling:resourceType property. In contrast, when building a dialog for the classic view, you define the type of control by setting its xtype property. You set both properties in the following sections. 

The following illustration shows the Touch UI dialog for the web service component. 

dialogwebservice

Perform these tasks:

1. Select /apps/weatherapp/components.

2. Right click and select Create, Create Node.

3. Enter the following values:

  • Name: cq:dialog
  • Type: nt:unstructured

4. Add the following properties to the cq:dialog node.

 

Name Type Value Description
helppath String en/cq/current/wcm/
default_components.html#Carousel
Specifies the location of the help content. (see the help button on the top of the Touch UI dialog shown at the start of this article)
jcr:title
String
Hero Weather
Specifies the title displayed in the dialog. (see the illustration at the start of this article)
sling:resourceType
String
cq/gui/components/authoring/dialog
Specifies the type of node. In this example, the type is a dialog.

5. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog.

6. Right click and select Create, Create Node. Enter the following values:

  • Name: content
  • Type: nt:unstructured

7. Add the following property to the content node.

Name Type Value Description
sling:resourceType String granite/ui/components/foundation/container Defines the type

8. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog/content.

9. Right click and select Create, Create Node. Enter the following values:

  • Name: layout
  • Type: nt:unstructured

10. Add the following properties to the layout node.

Name Type Value Description
sling:resourceType String granite/ui/components/foundation/
layouts/tabs
Defines the type
type String nav defines tab functionality

11. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog/content.

12. Right click and select Create, Create Node. Enter the following values:

  • Name: items
  • Type: nt:unstructured

13. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog/content/items.

14. Right click and select Create, Create Node. Enter the following values:

  • Name: herotext
  • Type: nt:unstructured
15. Add the following properties to the herotext node (this node represents the tab).
Name Type Value Description
jcr:title String Hero Text Properties The value displayed on the tab of the Touch UI dialog (see the illustration at the start of this article)
sling:resourceType String granite/ui/components/
foundation/section
Defines the tab functionality

16. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog/content/items/herotext.

17. Right click and select Create, Create Node. Enter the following values:

  • Name: layout
  • Type: nt:unstructured

18. Add the following property to the layout node.

Name Type Value Description
sling:resourceType String granite/ui/components/foundation/
layouts/fixedcolumns
defines the type of sling resource

19. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog/content/items/herotext.

20. Right click and select Create, Create Node. Enter the following values:

  • Name: items
  • Type: nt:unstructured

21. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog/content/items/herotext/items.

22. Right click and select Create, Create Node. Enter the following values:

  • Name: column
  • Type: nt:unstructured

23. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog/content/items/herotext/items/column.

24. Add the following property to the column node. 

Name Type Value Description
sling:resourceType String granite/ui/components/foundation/container defines the type of sling resource

25. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog/content/items/herotext/items/column.

26. Right click and select Create, Create Node. Enter the following values:

  • Name: items
  • Type: nt:unstructured

27. Click on the following node: /apps/weatherapp/components/heroweather/cq:dialog/content/items/herotext
/items/column/items
.

28. Right click and select Create, Create Node. Enter the following values:

  • Name:headingText
  • Type: nt:unstructured

29. Click on the following node:

/apps/weatherapp/components/heroweather/cq:dialog/content/items/herotext/items/column
/items/headingText
.

30. Add the following properties to the headingText node (this node represents the Heading Text input control on the dialog. See the illustration at the start of this article.)

Name Type Value Description
fieldLabel Value Heading Text Defines the label associated with the input control
name String ./jcr:Heading Defines the name of the control. You reference this value in the component's code.
sling:resourceType String granite/ui/components/
foundation/form/textfield
Defines the control as a text field. 
value String Touch UI Web Services
Defines the default value for this field that is displayed in the Touch UI dialog.  

31. Click on the following node:

/apps/weatherapp/components/heroweather/cq:dialog/content/items/herotext
/items/column/items
.

32. Right click and select Create, Create Node. Enter the following values:

  • Name: zip
  • Type: nt:unstructured

33. Click on the following node:

Name Type Value Description
fieldLabel Value USA ZIP
Defines the label associated with the input control
name String ./jcr:zip Defines the name of the control. You reference this value in the component's code.
sling:resourceType String granite/ui/components/
foundation/form/textfield
Defines the control as a text field. 
value String 90210 Defines the default value that is displayed in the dialog field.  

Modify the weathertemplate JSP to call the methods specified in the OSGi bundle

After you build and deploy the OSGi bundle, you can call its methods from the JSP that is part of the Touch UI component. In this development article, the weathertemplate.jsp calls methods defined in the OSGi bundle that invoke operations exposed by the WSDL.

Modify the JSP located at the following location:

/apps/weatherapp/components/heroweather/heroweather.jsp

Add the following code.

<%@include file="/libs/foundation/global.jsp"%>


  <h1><%=properties.get("jcr:Heading") %></h1> 




<h2>Here is an AEM service created from Apache CXF Java proxy classes:</h2>
<%
  



com.aem.ws.Weather weather = new com.aem.ws.Weather(); 
 
com.aem.ws.WeatherSoap wsoap = weather.getWeatherSoap(); 

com.aem.ws.WeatherReturn wr = null; 
String zip = (String)properties.get("jcr:zip") ; 

  if (properties.get("jcr:zip") == null)
		 wr = wsoap.getCityWeatherByZIP("90210");
  else
         wr = wsoap.getCityWeatherByZIP(zip);


%>
  
<h2>The following describes the weather for <%= zip %> ZIP Code</h2>
<h3><%= "The city is " +wr.getCity()%></h3>
<h3><%= "The state is " +wr.getState()%></h3>
<h3><%= "The description is " +wr.getDescription()%></h3>
<h3><%= "The wind is " +wr.getWind()%></h3>
<h3><%= "The current temp is " +wr.getTemperature()%></h3>

Notice how a com.aem.ws.Weather object can be created and its methods are called. When a method, such as getCity is invoked, an operation exposed by the WSDL is called. The data returned by the web service is displayed in the JSP.

Create a page that displays data retrieved from the OSGi bundle

The final task that you perform in order to see a web page that displays data retrieved from an OSGi bundle is to create a site that contains a page that is based on the weathertemplate (the template created earlier in this development article).

The following illustration shows the data returned by the OSGi bundle being displayed in the web page. The weather information was returned by the web service.

webServceHTML

To create an AEM web page that uses the Touch UI component, perform these tasks:

  1. Go to the AEM welcome page at http://[host name]:[port]; for example, http://localhost:4502.
  2. Select Sites.
  3. Select the + Icon in the web page. This create a new AEM page. 
  4. Select Create Page.
  5. Select templateWeb from the list of templates that appear. 
  6. Select Next.
  7. Specify the name of the page in the Title field.
  8. Select Create Page and open the new page. 
  9. Drag the heroweather compnent from the AEM side rail into the page. Double click on the component. Enter values into the dialog. Once done, the values are displayed in the AEM web page.

Note:

If the AEM side rail is empty, you can populate it with components under General. For information, see Creating your first Adobe Experience Manager Touch UI component

See also

Congratulations, you have just created an AEM 6 application that consumes web services using a custom Touch UI component. Please refer to the AEM community page for other articles that discuss how to build AEM services/applications.

This work is licensed under a Creative Commons Attribution-Noncommercial-Share Alike 3.0 Unported License  Twitter™ and Facebook posts are not covered under the terms of Creative Commons.

Legal Notices   |   Online Privacy Policy