Define a Commerce Composer widget manager class

A widget manager handles the persistence and retrieval of widget extended data other than basic widget properties. We can use a widget manager to add more logic when we are creating, updating, or deleting a widget.

When a Management Center user saves widget property settings, the values for the properties are saved in the PLWIDGETNVP database table. If your widget has properties that must have values that are saved in a different table than the PLWIDGETNVP table, define a widget manager class to handle saving the values for our widget properties. The widget manager class is also used for retrieving the saved property value information from the database. When you define your widget manager class, we must extend the default widget manager class. We must also register our custom widget manager within the definition XML for our widget. If your widget has property values that are saved in only the PLWIDGETNVP table, you do not need to define a custom manager class. By default, when no widget manager class is defined for a widget, the widget uses the com.ibm.commerce.pagelayout.widget.management.impl.DefaultWidgetManager class.

The following diagram shows the hierarchy of the widget manager classes used within the Commerce Composer framework. When we are creating a custom widget, use the widget manager that extends the fewest classes and still provides the functionality that you need to handle the properties for our widget. Your widget can use any of the widget manager classes within the following diagram, however the four most common widget manager class that might consider using are highlighted.

Where

We can review the widget manager classes for the widgets that are provided by default to help us create our own custom class. The following table identifies the widget manager classes available by default:

Widget manager class Widgets that use the class
com.ibm.commerce.pagelayout.widget.management.impl.CategoryRecommendationWidgetManager

This class extends the DefaultContentAndWebActivityWidgetManager class.

  • Category Recommendation widget

com.ibm.commerce.pagelayout.widget.management.impl.ContentRecommendationWidgetManager

This class extends the DefaultContentAndWebActivityWidgetManager class.

com.ibm.commerce.pagelayout.widget.management.impl.DefaultContentAndWebActivityWidgetManager

This class extends the DefaultContentWidgetManager class.

No widget directly uses this class. However, some widgets use a manager class that extends this class.
com.ibm.commerce.pagelayout.widget.management.impl.DefaultContentWidgetManager

This class extends the MarketingWidgetManager class.

No widget directly uses this class. However, some widgets use a manager class that extends this class.
com.ibm.commerce.pagelayout.widget.management.impl.DefaultWidgetManager The following widgets use the default widget manager class to handle any properties that are defined for the widget. By default, not all widgets have properties defined.

com.ibm.commerce.pagelayout.widget.management.impl.IBMProductRecommendationsWidgetManager

This class extends the MarketingWidgetManager class.

com.ibm.commerce.pagelayout.widget.management.impl.MarketingWidgetManager

This class extends the DefaultWidgetManager class.

No widget directly uses this class. However, some widgets use a manager class that extends this class.
com.ibm.commerce.pagelayout.widget.management.impl.ProductListingWidgetManager

This class extends the DefaultContentWidgetManager class.

com.ibm.commerce.pagelayout.widget.management.impl.ProductRecommendationWidgetManager

This class extends the DefaultContentAndWebActivityWidgetManager class.

  • Catalog Entry Recommendation widget

com.ibm.commerce.pagelayout.widget.management.impl.RichTextWidgetManager

This class extends the MarketingWidgetManager class.

  • Text Editor widget

com.ibm.commerce.pagelayout.widget.management.impl.RotatingContentWidgetManager

This class extends the DefaultContentAndWebActivityWidgetManager class.

  • Content Carousel widget

com.ibm.commerce.pagelayout.widget.management.impl.URLLinkWidgetManager

This class extends the MarketingWidgetManager class.

For examples of the properties that these classes handle for the widgets available by default with WebSphere Commerce, see Commerce Composer widget properties.


Procedure

  1. Create a file to define the implementation class for our widget manager. In your new file, extend the DefaultWidgetManager class. To extend the DefaultWidgetManager class, add the following code in your new file:

      /**
      * This is the widget manager associated with my custom widget.
      * It creates, updates, deletes and gets data for my custom widget.
      */
      public class CustomWidgetManager extends DefaultWidgetManager {

  2. Override one or more of the methods of the DefaultWidgetManager class to define how your manager class is to handle properties for our widget. These methods include the following methods:

    • createExtendedData

    • updateExtendedData

    • deleteExtendedData

    • retrieveExtendedData

    Within these methods the following parameters are included:

      LayoutType
      The Layout noun that is passed in.

      WidgetType
      The noun part of the Layout noun that represents the widget.

      ExtendedDataType
      An element of the WidgetType noun part. It contains the data to be created.

      PageLayoutWidget
      The physical data object of the widget. It has all the data stored in the database for this widget.

    For example, the following method overrides the createExtendedData method to define how to create a URL link for a widget:

      public void createExtendedData(LayoutType aLayout, WidgetType aWidget, ExtendedDataType aExtData, PageLayoutWidget aWidgetSDO)
      throws LayoutException {
      
      // Always call super method first so that common extended data type will be handled.
      super.createExtendedData(aLayout, aWidget, aExtData, aWidgetSDO);
      
      String dataType = aExtData.getDataType();
      // Check if the extended data type is 'IBM_CustomURL'
      if (PageLayoutFacadeConstants.WIDGET_EXT_DATA_TYPE_CUSTOM_URL.equals(dataType)) {
      String uniqueId = createURLLink(aWidget, aExtData, aWidgetSDO);
      
      // Return the unique id of the extended data back.
      aExtData.setUniqueID(uniqueId);
      }

    The createURLLink method calls Marketing service to create marketing content to store the URL.

  3. Register the widget manager by setting the widget-manager attribute to the widget in the widget definition XML file. Use the following format to specify a widget manager class:

      <widget-manager j2ee=""/>

    For example, the following code specifies the widget manager class

      <Definition>
      <widget-manager j2ee="com.ibm.commerce.pagelayout.widget.management.impl.URLLinkWidgetManager"/>
      ...
      </Definition>

    The following code is a sample widget definition XML file that defines a widget manager for the Links widget:

      <Definition>
        <widget-property name="widgetRestrictionGroups">
          <value>AnyPage,CatalogEntryPage,CategoryPage,SearchPage</value>
        </widget-property>
        <widget-manager j2ee="com.ibm.commerce.pagelayout.widget.management.impl.URLLinkWidgetManager"/>
        <widget-property name="requireEMS">
          <value>true</value>
        </widget-property>
        <widget-property name="serializeActionPath">
          <value>SerializeLayoutWidget-URLLinkWidget</value>
        </widget-property>
        <widget-property name="isURLLink">
          <value>true</value>
        </widget-property>
        <widget-property name="emsName" required="false" datatype="java.lang.String"/>
      </Definition>  

  4. Use the Data Load utility to load the widget definition into the WebSphere Commerce database to register your widget manager along with our custom widget. For more information about registering your widget, see Registering a Commerce Composer widget.

  5. In the WidgetObjectDefinition.xml file for your widget, include a service to invoke the createExtendedDataService service. The WidgetObjectDefinition.xml file includes the definition of the input field variables for our widget. This object definition file also defines the services for creating, updating, and deleting data for our widget. When you add extended data for our widget, define a create service within this file to save the extended data. By including the following code you create such a service that invokes the createExtendedDataService service.

      <!---
      This definition defines the custom URL child object
      -->
      <ChildObjectDefinition definitionName="plmURLLinkCustomURL"
       objectType="URLLinkCustomURL" idProperty="extDataId"
       displayName="${plmPageLayoutResources.customURL}"
       icon="URLIcon">
       
      <!--- Create service. -->
      <CreateService url="/cmc/CreateWidgetExtendedData">
        <ServiceParam name="storeId"/>
        <ServiceParam name="dataStoreId" parameterName="dataStoreId" parentProperty="true" 
          resolvePrimaryParent="true" propertyName="objectStoreId">
          <EnablementCondition checkObjectDefinition="true" conditionId="objectTypeCondition" 
            enablementValue="URLLinks" negate="true" propertyName="objectType" 
            parentProperty="true" resolvePrimaryParent="false"/>
        </ServiceParam>
        <ServiceParam name="pageLayoutId" propertyName="pageLayoutId" parentProperty="true" />
        <ServiceParam name="type" value="IBM_CustomURL"/>
        <ServiceParam name="widgetId" propertyName="widgetId" parentProperty="true" objectPath="LayoutWidgetAlias"/>
        <ServiceParam name="languageId" resolvePrimaryParent="false" parentProperty="true" propertyName="languageId"/>
      </CreateService>

    Where:

      <ServiceParam name="type" value=""/>
      The type of the extended data for the widget, for example <ServiceParam name="type" value="IBM_CustomURL"/>

    The service call to invoke the createExtendedDataService sends the following URL parameters

      urlType=
      sequenceOrder=
      xExtData_urlText=
      languageId=-
      pageLayoutId=
      timeZoneId=
      requestIdentifier=
      identityId=
      identitySignature=
      type=
      locale=
      storeId=
      widgetId=

    For example,

      urlType=custom
      sequenceOrder=1
      xExtData_urlText=cnn
      languageId=-1
      pageLayoutId=10601
      timeZoneId=America/New_York
      requestIdentifier=1
      identityId=95121
      identitySignature=********
      type=IBM_CustomURL
      locale=en_US
      storeId=10001
      widgetId=6201

    The request BOD of the createExtendedData service call can resemble the following request:

      <oa:Change>
        <oa:ActionCriteria>
          <oa:ActionExpression actionCode="Add" 
           expressionLanguage="_wcf:XPath">/Layout[1]/Widget[1]/ExtendedData[1]</oa:ActionExpression>
        </oa:ActionCriteria>
      </oa:Change>
      <_pgl:Layout>
        <_pgl:LayoutIdentifier>
          <_wcf:UniqueID>10601</_wcf:UniqueID>
        </_pgl:LayoutIdentifier>
        <_pgl:Widget>
          <_pgl:WidgetIdentifier>
            <_wcf:UniqueID>6201</_wcf:UniqueID>
          </_pgl:WidgetIdentifier>
          <_pgl:ExtendedData sequenceOrder="1.0">
            <_pgl:DataType>IBM_CustomURL</_pgl:DataType>
            <_pgl:Attributes language="-1">
              <_pgl:Attribute name="url">cnn.com</_pgl:Attribute>
              <_pgl:Attribute name="urlText">cnn</_pgl:Attribute>
            </_pgl:Attributes>
          </_pgl:ExtendedData>
        </_pgl:Widget>
      </_pgl:Layout>

    For more information about creating the object definition for our widget, see Adding Management Center support for a Commerce Composer widget.