Skip to content
snhackery

Adventures in mangling the ServiceNow platform

  snhackery
  • Home
  • About
  • Disclaimer
  • Update Sets

Month: February 2023

Service Account Management, Part XVII

Posted on February 20, 2023 | by snhackery

“Energy and persistence conquer all things.”
— Benjamin Franklin

Last time, we were about to throw together a little dashboard of Service Account information when we ran into a little problem with the Content Selector Configuration Editor. Actually, it turned out to be a problem with the snh-form-field tag, but now that we have taken the time to fix that, we should be able to get back to where we were and continue on. So let’s get back into the configurator tool and try one more time to create a new configuration script.

Creating the Requester perspective

Well, that’s much better! Now we can see all of the fields again in the modal pop-up as well as both of the buttons, so things are back to normal with the newer version. After creating the Requester perspective, we go through the process again to create the Fulfiller perspective.

Requester and Fulfiller perspectives

Now, we could have used slightly different names, such as Owner and Provider, but again, this is just a sample of what could be; your mileage may vary. One thing that we did do on the Fulfiller perspective, though, was to add the itil role so that only actual fulfillers would have access to that portion of the dashboard.

Next, we need to add some states, and for our purpose, the states of Active, Retired, and Pending should suffice.

Adding all of the desired states

With that out of the way, now we can start completing the Tables section. Clicking on the Add a new Table button in the Requester tab will bring up the modal Table Selector pop-up.

Adding a new Table

Once the Table has been added, we can fill in all of the rest of the configuration data.

Completing the configuration for the new table

For the Active state, we will use following fields:

number,type,user_id,owner,owning_group

… and the following filter:

active=true^ownerDYNAMIC90d1921e5f510100a9ad2572f2b477fe^ORowning_groupDYNAMICd6435e965f510100a9ad2572f2b47744

For the Retired tab, we will just change the above filter from active=true to active=false. Everything else can remain the same. For accounts in the pending state, there will be no record on the Service Account table just yet, so we can just set the filter to 1=0, which should always find no records. To see the pending accounts, we will need to add another table. We can deal with that later, though, so for now let’s just focus on the Service Account table and then see how it all comes out.

Basically, we go through pretty much the same process for the Fulfiller tab, and once we save all of our input, we end up with the following configuration script.

var ServiceAccountDashboardConfig = Class.create();
ServiceAccountDashboardConfig.prototype = Object.extendsObject(global.ContentSelectorConfig, {
	initialize: function() {
	},

	perspective: [{
		name: 'requester',
		label: 'Requester',
		roles: ''
	},{
		name: 'fulfiller',
		label: 'Fulfiller',
		roles: 'itil'
	}],

	state: [{
		name: 'active',
		label: 'Active'
	},{
		name: 'retired',
		label: 'Retired'
	},{
		name: 'pending',
		label: 'Pending'
	}],

	table: {
		requester: [{
			name: 'x_660634_service_0_service_account',
			displayName: 'Service Account',
			active: {
				filter: 'active=true^ownerDYNAMIC90d1921e5f510100a9ad2572f2b477fe^ORowning_groupDYNAMICd6435e965f510100a9ad2572f2b47744',
				fields: 'number,type,user_id,owner,owning_group',
				svcarray: [],
				aggarray: [],
				btnarray: [],
				refmap: {
					sys_user: 'user_profile'
				},
				actarray: []
			},
			retired: {
				filter: 'active=false^ownerDYNAMIC90d1921e5f510100a9ad2572f2b477fe^ORowning_groupDYNAMICd6435e965f510100a9ad2572f2b47744',
				fields: 'number,type,user_id,owner,owning_group',
				svcarray: [],
				aggarray: [],
				btnarray: [],
				refmap: {
					sys_user: 'user_profile'
				},
				actarray: []
			},
			pending: {
				filter: '1=0',
				fields: 'number',
				svcarray: [],
				aggarray: [],
				btnarray: [],
				refmap: {},
				actarray: []
			}
		}],
		fulfiller: [{
			name: 'x_660634_service_0_service_account',
			displayName: 'Service Account',
			active: {
				filter: 'active=true^type.fulfillment_groupDYNAMICd6435e965f510100a9ad2572f2b47744',
				fields: 'number,type,user_id,owner,owning_group',
				svcarray: [],
				aggarray: [],
				btnarray: [],
				refmap: {
					sys_user: 'user_profile'
				},
				actarray: []
			},
			retired: {
				filter: 'active=false^type.fulfillment_groupDYNAMICd6435e965f510100a9ad2572f2b47744',
				fields: 'number,type,user_id,owner,owning_group',
				svcarray: [],
				aggarray: [],
				btnarray: [],
				refmap: {
					sys_user: 'user_profile'
				},
				actarray: []
			},
			pending: {
				filter: '1=0',
				fields: 'number',
				svcarray: [],
				aggarray: [],
				btnarray: [],
				refmap: {},
				actarray: []
			}
		}]
	},

	type: 'ServiceAccountDashboardConfig'
});

Now all we need to do is to create a Portal Page that will use the configuration script and we can take it out for a spin. That sounds like a good project for our next installment.

Posted in Projects | Tagged Content Selector, Data Table Widget, Form Fields, Portal Page, Service Account

SNH Data Table Widgets on Share, Corrected (again)

Posted on February 16, 2023 | by snhackery

“We learn from failure, not from success!”
— Bram Stoker

A while back I was working on my Collaboration Store project when I discovered a problem with the SNH Form Fields when running on my Tokyo instance. At the time, I was not able to diagnose the source of the problem, but I did manage to come up with a work-around, which I implemented on the page that I was developing at the time. What I did not do was to go back and refactor all of the other widgets that utilize the snh-form-field tag to implement the work-around on those as well, nor did I invest any time in actually hunting down the source of the actual problem with the tag, correcting it, and producing a new version.

Recently, I was working on my little Service Account Management app, and was rudely reminded of this unfortunate oversight. Initially, I thought that there was something wrong with my modal pop-up box, but after further review I realized this was the same snh-form-field issue that I had run into earlier on the other project. Clearly, it was long since time to address it.

To implement the work-around, I brought up a list of all of the Service Portal widgets that contained the text ‘snh-form-field’ in the Body HTML template property. Then one by one, I pulled them up in the editor, searched for the tag, and then wrapped a SPAN around each one, mitigating the problem. For example, here is the original HTML for the Aggregate Column Editor widget:

<div>
  <form name="form1">
    <snh-form-field
      snh-model="c.widget.options.shared.label"
      snh-name="label"
      snh-required="true"/>
    <snh-form-field
      snh-model="c.widget.options.shared.name"
      snh-name="the_name"
      snh-label="Name"
      snh-required="true"/>
    <snh-form-field
      snh-model="c.widget.options.shared.heading"
      snh-name="heading"/>
    <snh-form-field
      snh-model="c.widget.options.shared.table"
      snh-name="table"
      snh-type="reference"
      snh-change="buildFieldFilter();"
      snh-required="true"
      placeholder="Choose a Table"
      table="'sys_db_object'"
      display-field="'label'"
      display-fields="'name'"
      value-field="'name'"
      search-fields="'name,label'"/>
    <snh-form-field
      snh-model="c.widget.options.shared.field"
      snh-name="field"
      snh-type="reference"
      snh-required="true"
      placeholder="Choose a Field"
      table="'sys_dictionary'"
      display-field="'column_label'"
      display-fields="'element,reference'"
      value-field="'element'"
      search-fields="'column_label,element'"
      default-query="c.data.fieldFilter"/>
    <snh-form-field
      snh-model="c.widget.options.shared.filter"
      snh-name="filter"/>
    <snh-form-field
      snh-model="c.widget.options.shared.source"
      snh-name="source"/>
    <snh-form-field
      snh-model="c.widget.options.shared.hint"
      snh-name="hint"/>
    <snh-form-field
      snh-type="reference"
      snh-model="c.widget.options.shared.page_id"
      snh-name="page_id"
      placeholder="Choose a Portal Page"
      table="'sp_page'"
      display-field="'title'"
      display-fields="'id'"
      value-field="'id'"
      search-fields="'id,title'"/>
  </form>
  <div style="width: 100%; padding: 5px 50px; text-align: right;">
    <button ng-click="cancel()" class="btn btn-default ng-binding ng-scope" role="button" title="Click here to cancel this edit">Cancel</button>
    &nbsp;
    <button ng-click="save()" class="btn btn-primary ng-binding ng-scope" role="button" title="Click here to save your changes">Save</button>
  </div>
</div>

… and here is the updated HTML with the work-around implemented:

<div>
  <form name="form1">
   <span>
    <snh-form-field
      snh-model="c.widget.options.shared.label"
      snh-name="label"
      snh-required="true"/>
   </span>
   <span>
    <snh-form-field
      snh-model="c.widget.options.shared.name"
      snh-name="the_name"
      snh-label="Name"
      snh-required="true"/>
   </span>
   <span>
    <snh-form-field
      snh-model="c.widget.options.shared.heading"
      snh-name="heading"/>
   </span>
   <span>
    <snh-form-field
      snh-model="c.widget.options.shared.table"
      snh-name="table"
      snh-type="reference"
      snh-change="buildFieldFilter();"
      snh-required="true"
      placeholder="Choose a Table"
      table="'sys_db_object'"
      display-field="'label'"
      display-fields="'name'"
      value-field="'name'"
      search-fields="'name,label'"/>
   </span>
   <span>
    <snh-form-field
      snh-model="c.widget.options.shared.field"
      snh-name="field"
      snh-type="reference"
      snh-required="true"
      placeholder="Choose a Field"
      table="'sys_dictionary'"
      display-field="'column_label'"
      display-fields="'element,reference'"
      value-field="'element'"
      search-fields="'column_label,element'"
      default-query="c.data.fieldFilter"/>
   </span>
   <span>
    <snh-form-field
      snh-model="c.widget.options.shared.filter"
      snh-name="filter"/>
   </span>
   <span>
    <snh-form-field
      snh-model="c.widget.options.shared.source"
      snh-name="source"/>
   </span>
   <span>
    <snh-form-field
      snh-model="c.widget.options.shared.hint"
      snh-name="hint"/>
   </span>
   <span>
    <snh-form-field
      snh-type="reference"
      snh-model="c.widget.options.shared.page_id"
      snh-name="page_id"
      placeholder="Choose a Portal Page"
      table="'sp_page'"
      display-field="'title'"
      display-fields="'id'"
      value-field="'id'"
      search-fields="'id,title'"/>
   </span>
  </form>
  <div style="width: 100%; padding: 5px 50px; text-align: right;">
    <button ng-click="cancel()" class="btn btn-default ng-binding ng-scope" role="button" title="Click here to cancel this edit">Cancel</button>
    &nbsp;
    <button ng-click="save()" class="btn btn-primary ng-binding ng-scope" role="button" title="Click here to save your changes">Save</button>
  </div>
</div>

It was not difficult work, but it was rather tedious. Eventually, I got through the entire list. Then I put together a new Update Set for the SNH Data Table Widgets and posted the new version (2.4) out on Share. Unfortunately, it wasn’t until I had already posted it out there that I realized that I had left out a critical widget in the build, so I had to build the Update Set a second time. It did not look like there was any way to replace the Update Set on Share for the 2.4 version, so I called the corrected Update Set 2.4.1. But that is not a legal version name on that site, so on Share, that version is known as 2.41. Anyway, it’s out there now, so if you are running, or planning to run, on Tokyo or Utah, you should definitely go out to Share and pull down the latest Update Set. But stay away from version 2.4, because that was just an error, and shouldn’t even be out there.

Oh, and if you run into any issues with the 2.4.1 version, please provide some details in the discussion section on Share, or in the comments below. Thanks!

Posted in Cool Stuff | Tagged Data Table Widget, Form Fields, HTML, Service Account, Service Portal, Share, Testing, Update Set, Widget

Service Account Management, Part XVI

Posted on February 14, 2023 | by snhackery | 2 Comments on Service Account Management, Part XVI

“Inside of every problem lies an opportunity.”
— Robert Kiposaki

Last time, we wrapped up all of the work on the Service Account requisition process, although we left a number of things that could have improved the process to some mythical future effort. Unlike the SNH Form Fields or SNH Data Table Widgets, which were intended to be used as is, without the need to touch any of the provided code, the Service Account Management app is more of a sample of what could be done, with the understanding that implementers would want to craft their own account types, notice templates, and fulfillment Flows based on their unique requirements. Since it is just an example, and more of a concept than a product, we don’t need to solve every issue or build out every conceived improvement. We created enough pieces to demonstrate that it works, and that pretty much addresses the intent of the project.

So what’s left? One thing that we will want to do once a Service Account has been delivered will be to check back every so often and ensure that it is still needed. This is actually a common practice for a number IT artifacts, and the applications for such a process go well beyond the realm of Service Accounts. Periodically checking to see if a thing is still needed is something that could be applied to servers deployed for a development project, or access granted to vendors or contractors, or laptops issued to temporary staff, or communications links established with outside entities, or any number of other items that are deployed, granted, or procured for a limited purpose. That actually could be a stand-alone product that one could use out of the box, and one that could potentially have quite a few applications in an IT organization. In fact, for our little exercise here, let us assume that such a product exists, and we won’t bother to build out that capability here. However, one day we might tackle the development of such a product, and if we do, we can then use our Service Account Management app as one example of how such a product might be employed. But that’s not today’s worry.

So, again, what is left for us to do. So far, we have created our Scoped Application, built out all of our database tables, and created a process through which someone can request a new Service Account. If we assume that the periodic process though which these accounts will be reviewed will be handled by a separate product, then what is left for our product?

One thing that would be useful would be series of table views from both the requester’s perspective and the fulfiller’s perspective. Each might want to see a list of active accounts, retired accounts, and pending accounts. This is something for which the SNH Data Table Widgets were designed, so let’s see if we can use that product to produce a single dashboard that would contain all of these interrelated lists.

To begin, we will select Content Selector Configurator from the Tools menu (which is only there because we have previously installed SNH Data Table Widgets).

Selecting the Content Selector Configurator from the Tools menu

On the initial screen of the configurator, we will want to click on the Create a new Content Selector Configurator button.

Creating a new Content Selector Configurator

We will call our new script ServiceAccountDashboardConfig and use the Add a new Perspective button to create two perspectives, Requester and Fulfiller. We may want to add a third at some point for an Admin view, but for now, let’s just focus on the two primary user perspectives. Once we click on the Add a new Perspective button, a modal dialog pops up where we can enter the details of our new perspective.

Incomplete modal pop up for adding a new perspective

Well, that’s not right! The modal pop-up box is supposed to have several input fields and it is only tall enough to show the first one. There doesn’t seem to be any way to drag down the bottom of the box to reveal the rest of the form, either, so you can’t even get to the buttons that should be down at the bottom. This is probably another Tokyo thing that I am going to have to resolve, so it looks like it is time to set this project aside and dig into this little issue.

It’s always something.

OK, well, I will see if I can’t figure out what is going on here, and once I do, we will get back to this in a future installment. Hopefully, this will be a quick break!

Posted in Projects | Tagged Data Table Widget, Flow Designer, Form Fields, Scoped Application, Service Account, Testing

Service Account Management, Part XV

Posted on February 1, 2023 | by snhackery

“It’s a bad plan that admits of no modification.”
— Publilius Syrus

Last time, we wrapped up changes to our primary new Service Account request fulfillment Flow, and our second example Subflow for manually creating a new Active Directory account. Now we need to test everything all over again to make sure that we didn’t break anything, and to see if we finally have a working approach to the manual fulfillment process. Once again, let’s start with the automated example first, as that is the one that was working previous to all of these changes.

Testing the automated fulfillment process once again

… and it looks like that one still works, even with all of the alterations that we just did.

Successful account creation and task closure

Now let’s try the same thing with the manual fulfillment example.

Testing the manual fulfillment process

Under this scenario, the Requested Item will remain open until someone closes the task issued to the fulfillment group.

Requested Item waiting for manual fulfillment

So let’s hunt down the task, pretend that we created the account manually, and then close it and see what happens.

Closing the manual fulfillment task

Now the Requested Item shows completed, which also closes out the Request.

Completed manual fulfillment process

So now both the automated and manual example Subflows appear to do what they are supposed to do, which should complete the work on the Service Account creation process. Before we go, however, we should check the password emails sent out for both, just to make sure that those are working as they should as well. Here is the email sent out for the automated example.

Password email for the automated example test

And here is the email for the manual example.

Password email for the manual example test

Both look good, so it would appear that we have a successful strategy for fulfilling the requests for new Service Accounts of any type. To create a new type, you would just need to add the new record for the type to the table and then specify the appropriate Subflow on the new type record. This would make the new type appear on the catalog item drop-down list and the primary fulfillment Flow would then launch the Subflow specified in the type record during fulfillment.

As mentioned earlier, there is some work that we could do to streamline this process with a little bit of refactoring, but since it does work, we will leave that for another day at this point and move on to other things. In fact, those other things will be the subject of our next installment.

Posted in Projects | Tagged Catalog Requests, Email Notification, Service Account, Service Catalog, Subflow, Testing

Recent Posts

  • Periodic Review, Part XI
  • Periodic Review, Part X
  • Periodic Review, Part IX
  • Periodic Review, Part VIII
  • Periodic Review, Part VII

Recent Comments

  • snhackery on Service Account Management, Part XVI
  • Jennifer Schoenhoeft on Service Account Management, Part XVI
  • snhackery on Service Portal Form Fields, Broken
  • Joe Blogs on Service Portal Form Fields, Broken
  • Joe Blogs on Service Portal Form Fields, Broken

Archives

  • February 2024
  • September 2023
  • August 2023
  • July 2023
  • June 2023
  • May 2023
  • April 2023
  • March 2023
  • February 2023
  • January 2023
  • December 2022
  • November 2022
  • October 2022
  • September 2022
  • August 2022
  • July 2022
  • June 2022
  • May 2022
  • April 2022
  • March 2022
  • February 2022
  • January 2022
  • December 2021
  • November 2021
  • October 2021
  • September 2021
  • August 2021
  • July 2021
  • June 2021
  • May 2021
  • April 2021
  • March 2021
  • February 2021
  • January 2021
  • December 2020
  • November 2020
  • October 2020
  • September 2020
  • August 2020
  • July 2020
  • June 2020
  • May 2020
  • April 2020
  • March 2020
  • February 2020
  • January 2020
  • December 2019
  • November 2019
  • October 2019
  • September 2019
  • August 2019
  • July 2019
  • June 2019
  • May 2019
  • April 2019
  • March 2019
  • February 2019
  • January 2019
  • December 2018

Categories

  • Cool Stuff
  • Discoveries
  • General
  • Hackery
  • Projects

Meta

  • Log in
  • Entries feed
  • Comments feed
  • WordPress.org

Subscribe to snhackery via Email

Enter your email address to subscribe to snhackery and receive notifications of new posts by email.

Useful ServiceNow links:
Main web site: https://servicenow.com
Developer site: https://developer.servicenow.com
Annual Conference:   https://knowledge.servicenow.com