Enable UI Formatters on Service Portal Form Widget

mspeirs
Mega Expert

Because the Service Portal does not support UI Macros, it instead allows us to create and use widgets in their place on Catalog Items. But did you know you can do something similar for forms that use UI Formatters based on UI Macros? If you take a look at the Form (widget-form) widget's server script, you will see the following lines:

...

data.f = $sp.getForm(data.table, data.sys_id, data.query, data.view);

// Activity formatter is hardcoded to set specific options

for (var f in data.f._formatters) {

        var fm = data.f._formatters[f];

        if (fm.formatter == "activity.xml") {

                  fm.hardcoded = true;

                  fm.widgetInstance = $sp.getWidget('widget-ticket-conversation',

                                                                                                            {table: data.table,

                                                                                                            sys_id: data.sys_id,

                                                                                                            includeExtended: true,

                                                                                                            title: "${Activity}",

                                                                                                            use_dynamic_placeholder: true,

                                                                                                            btnLabel: "${Post}"});

                  } else

                            fm.widgetInstance = $sp.getWidget(fm.widget, data);

}

...

The first line uses $sp.getForm to retrieve the data needed to render the form. After this call, there will be an object data.f._formatters that can hold data about formatters. The next section of code loops over any formatters in the object and gets the widget specified for rendering on the page when it loads. We see that individual widgets can be called with specific inputs like the Activity formatter in the code.

One way to set this up to render a custom formatter would be to make sure we have an entry for it in the data.f._formatters object. We could put the following code between the $sp.getForm call/assignment and the comment beneath it:

...

data.f = $sp.getForm(data.table, data.sys_id, data.query, data.view);

/* ----- Custom code ----- */

try { // Prevent our code from interfering with ServiceNow code, should it fail

        if(data.table == 'incident') { // Conditions for adding our formatter widget to rendered Form widget such as specific table

                  var formatterObj = {"formatter":"<ui macro name>.xml","widget":"<widget sys_id>"}; // Specifies which widget to use for which ui macro (formatter)

                  data.f._formatters['<formatter sys_id>'] = formatterObj; // Add entry to _formatters object

        }

} catch(e) {

}

/* ----- End custom code ----- */

// Activity formatter is hardcoded to set specific options

for (var f in data.f._formatters) {

...

Note: You cannot edit the Out-of-Box widget but you can clone it, edit the copy and replace the Out-of-Box version on the portal page. The <ui macro name>, <widget sys_id> and <formatter sys_id> should be populated with actual values. Also, it is important that the formatter is added on the form/view that we will be using in the Service Portal.

When this is all set up, our customized Service Portal Form widget should load the specified formatter widget just as the platform form view loads the ui macro version. The Form widget is used on the Form portal page and the URL would look something like this: xxxxx.service-now.com/sp?id=form&sys_id=<sys_id_of_task_record>&view=<view name (e.g., sp)>&table=<task_table_name (e.g., incident)>.

For reference:

Create a formatter

Embedding widgets in Service Catalog

UI macro is not visible on Portal?

1 ACCEPTED SOLUTION

Erich1
Kilo Expert

You do not need to edit the baseline Form widget to map your Formatters to Widgets. 

Use the table Service Portal UI Formatters (sp_ui_formatter) for the mapping.

View solution in original post

9 REPLIES 9

david_hreben
Giga Expert

Hello mspeirs,

 

I had tried wat you did but it does not seem to work. Is there anything missing? Thanks!

 

tonycosentino
Kilo Contributor

Hi mspeirs,

Is there a way to make this work without editing the form widget ?

Calling $sp.getForm() should know about our custom formatters but it doesn't ! Hence your customization.. Why ?

$sp.getForm() knows about your formatters, but it won't know what widget to associate with it.

In the code, the following line will successfully retrieve your custom formatter:

var fm = data.f._formatters[f];

but the widget property for your custom formatter (i.e. fm.widget) is undefined. So the line below won't retrieve anything:

fm.widgetInstance = $sp.getWidget(fm.widget, data);

mspeirs is suggesting you need to populate fm.widget somehow. You need to somehow associate your custom formatter with a widget.

Erich1
Kilo Expert

You do not need to edit the baseline Form widget to map your Formatters to Widgets. 

Use the table Service Portal UI Formatters (sp_ui_formatter) for the mapping.