Tutorial: Embed an existing widget

Enable the user to view and purchase Service Catalog items in the Quick Order widget by embedding the SC Catalog Item widget.

Before you begin

Role required: admin or sp_admin

About this task

Instead of duplicating code, you can embed widgets to leverage pre-existing functionality. The SC Catalog Item widget is a base system widget that enables the user to view and purchase Service Catalog items.

Procedure

  1. Inspect the SC Catalog Item widget.
    Before embedding the SC Catalog Item widget, inspect the widget to understand what data it needs access to. You may need to update your Quick Order widget client or server script to make sure that the correct data is passed to the embedded widget.
    1. Navigate to <yourInstanceURL>/sp_config?id=widget_edit.
    2. Open the SC Catalog Item widget.
    3. Note that the widget ID is widget-sc-cat-item. You will use this ID to embed the widget model in the client script.
    4. Examine the server script.

      Notice that the data object includes a sys_id property populated by either the input or options objects. If neither input nor options include a sys_id, the $sp.getParameter() method retrieves the sys_id from the request query string.

      To populate the input object, you can pass a catalog item sys_id from the Quick Order widget client script.

  2. From the Widget Editor, open the Quick Order widget.
  3. Replace the Quick Order widget client script with the following script.
    function($location, spUtil) {
      var c = this;
    	
    	c.select = function(item_id) {
    		if (c.openItem == item_id) {
    			c.openItem = null;
    			return;
    		}
    		
    		renderCatalogItemWidget(item_id);
    	}
    	
    	function renderCatalogItemWidget(item_id) {
    		c.catalogItemWidget = null;
    		spUtil.get("widget-sc-cat-item", {sys_id: item_id}).then(function(response){
    			c.catalogItemWidget = response;
    			c.openItem = item_id;
    		});
    	}
    }
    

    This script uses spUtil.get() to retrieve the widget model by ID (widget-sc-cat-item) and define the {sys_id: item_id} object. This object posts to the server script as input.

  4. Replace the HTML template with the following script:
    <div class="panel panel-primary">
      <div class="panel-heading">Request an item from the catalog</div>
      <div class="panel-body">
        <input class="form-control" type="search" placeholder="Start typing here to search the list of catalog items" ng-model="c.data.keywords" ng-change="c.server.update()" ng-model-options="{debounce: 250}" />
        <h5 ng-if="!c.data.keywords">Showing the most popular items</h5>
        <ul class="list-group result-container">
          <li class="list-group-item" ng-repeat="item in c.data.items">
            <a href ng-click="c.select(item.sys_id)">{{item.name}}</a><span class="pull-right">{{item.price}}</span>
            <div class="catalog-item" ng-if="item.sys_id == c.openItem">
                <sp-widget ng-if="c.catalogItemWidget" widget="c.catalogItemWidget" />
            </div>
          </li>
        </ul>
      </div>
      <div class="panel-footer" ng-if="c.data.keywords">
        <ng-pluralize count="c.data.items.length"
                     when="{'0': 'No items found for ',
                         '1': 'One item matching ',
                         'other': 'Found {} items matching '}">
        </ng-pluralize>
        {{c.data.keywords}}
      </div>
    </div>

    This template:

    • Adds on-click behavior using the ng-click directive.
    • Displays the embedded SC Catalog Item widget using the sp-widget directive.
  5. Replace the CSS with the following script:
    .result-container {
      margin-top: 10px;
    }
    
    .catalog-item {
      background-color: #f5f5f5;
      padding: 10px;
      @include border-top-radius($panel-border-radius);
      @include border-bottom-radius($panel-border-radius);
    }
    
  6. Refresh your test page preview to view the changes.

    When you select a search result, the item opens in the embedded SC Catalog Item widget.