Sometimes, interviewers ask, “Why Script Action is needed when we already
have Script Include?” This question makes us think why? We will try to
understand this with use-case after knowing about Script Action.
Script Action
Script actions are server-side JavaScript code that is executed when an event
it is listening to is triggered on the specified table. Just like any other server-
side script, script actions have access to all the server-side glide APIs, script
includes, and other server-side resources.
In other words,
Script Actions are server-side scripts that execute in response to specific
events. They act as event handlers, allowing you to automate tasks or modify
data when certain actions occur within the system, such as record updates or
business rule executions.
Here's a more detailed explanation:
• Event-Driven:
Script Actions are triggered by events, meaning they only run when a
predefined event occurs.
• Server-Side:
They run on the server, giving them access to all server-side APIs, script
includes, and other server-side resources.
• Asynchronous Execution:
Script Actions typically run in the background (asynchronously), allowing the
user interface to remain responsive while the script executes.
SCRIPT ACTION GYANINDRA YADAV
• Customization:
They enable developers to customize ServiceNow's behavior by adding
custom logic and automation to handle specific situations.
• Examples of Use:
• Updating a field on a record after a specific business rule has run.
• Sending an email notification when a new incident is created.
• Modifying data in a related table when a specific action is
performed.
• Creating Script Actions:
You can create Script Actions within the ServiceNow Studio or by navigating to
System Policy > Script Actions in the application navigator.
• Comparison with other scripting options:
While Client Scripts work on the client-side (within the browser) and Script
Includes are reusable server-side code, Script Actions bridge the gap by
allowing you to run server-side logic in response to specific events.
Use Case-1: Create a custom reference field named Affected CI
[u_affected_ci] on the incident table. Reference it to [cmdb_ci_server] table.
While creating an incident, if user selects any Affected CI and some state then
after inserting that incident….… The Comments field of that CI record on
[cmdb_ci_server] table should be updated as per the below conditions –
A. If CI is not changed & Incident is not RESOLVED, then update the
Comments fields of that CI as –
This CI is attached to INC0010074 on 2025-06-18 23:16:26. Incident state is: In
Progress
SCRIPT ACTION GYANINDRA YADAV
B. If CI is changed and Incident is RESOLVED, then –
This CI is removed from INC0010074 on 2025-06-18 23:17:16. Incident state on
the time of removal was: In Progress
C. When Incident got RESOLVED then –
This INC0010074 is resolved on 2025-06-18 23:19:06.
Since we can achieve scenario using the Business Rule also but here, we will
be using SCRIPT ACTION.
First create a field named Affected CI on Incident table.
Then, create an event. (Say update.cmdb_ci_server.comments)
Now create a Business Rule on Incident Table (Name: Update affected CI
comments) and add filter conditions.
SCRIPT ACTION GYANINDRA YADAV
In Script section, get all the value like previousCI, currentCI, changeCIFlag and
pass it to the gs.eventQueue() with current record object.
Script:
(function executeRule(current, previous /*null when async*/ ) {
// Add your code here
var previousCI = previous.u_affected_ci;
var currentCI = current.u_affected_ci;
var changeCIFlag;
if (previousCI == currentCI) {
changeCIFlag = 'false';
} else {
changeCIFlag = 'true';
gs.eventQueue('update.cmdb_ci_server.comments', current, changeCIFlag,
previousCI);
SCRIPT ACTION GYANINDRA YADAV
})(current, previous);
Save the Business Rule.
Now, Create the Script Action and select that event.
The Script:
var changeCIFlag = event.parm1;
var prevCISysID = event.parm2;
var currentCISysID = current.u_affected_ci;
var incNumber = current.number;
updateCIComment(changeCIFlag, prevCISysID);
function updateCIComment(changeCIFlag, prevCISysID) {
//When CI is not changed & INC is not resolved.
if (current.state != 6 && changeCIFlag == 'false') {
var getAffCI = new GlideRecord('cmdb_ci_server');
getAffCI.initialize();
getAffCI.addQuery('sys_id', currentCISysID);
getAffCI.query();
SCRIPT ACTION GYANINDRA YADAV
if (getAffCI.next()) {
getAffCI.comments = "This CI is attached to " + incNumber + " on " +
gs.nowDateTime() + ". Incident state is: " + current.state.getDisplayValue() +
"\n" + getAffCI.comments;
getAffCI.update();
//When CI is changed & INC is not resolved.
if (current.state != 6 && changeCIFlag == 'true') {
var getAffCI = new GlideRecord('cmdb_ci_server');
getAffCI.initialize();
getAffCI.addQuery('sys_id', currentCISysID);
getAffCI.query();
//Through we are updating the comments of existing Attached CI
if (getAffCI.next()) {
getAffCI.comments = "This CI is attached to " + incNumber + " on " +
gs.nowDateTime() + ". Incident state is: " + current.state.getDisplayValue() +
"\n" + getAffCI.comments;
getAffCI.update();
SCRIPT ACTION GYANINDRA YADAV
//Through this we are updating the removed affected CI
getAffCI.initialize();
getAffCI.addQuery('sys_id', prevCISysID);
getAffCI.query();
if (getAffCI.next()) {
getAffCI.comments = "This CI is removed from " + incNumber + " on " +
gs.nowDateTime() + ". Incident state on the time of removal was : " +
current.state.getDisplayValue() + "\n" + getAffCI.comments;
getAffCI.update();
//When INC is resolved.
if (current.state == 6) {
var getAffCI = new GlideRecord('cmdb_ci_server');
getAffCI.initialize();
getAffCI.addQuery('sys_id', currentCISysID);
getAffCI.query();
if (getAffCI.next()) {
getAffCI.comments = "This " + incNumber + " is resolved on " +
gs.nowDateTime() + "\n" + getAffCI.comments;
getAffCI.update();
SCRIPT ACTION GYANINDRA YADAV
}
Save the Script Action.
Now create an Incident with an Affected CI and then check Comments fields
of that CI.
After inserting this record, let me check that CI.
As we can see, Comments field has been updated as we wanted to.
Let’s check 2nd condition. Let me change the CI to DatabaseServer2. Then we
will check both CI page.
SCRIPT ACTION GYANINDRA YADAV
DatabaseServer1 updated –
And check DatabaseServer2 –
It is also updated.
Let’s change the state of that incident to RESOLVED | 6 and then see the CI –
Thus, this use is completed.
Some other use cases of Script Actions:
1. When an incident is assigned to a specific assignment group, send a
custom email notification to the group members with dynamic content.
2. Automatically create a problem record when multiple incidents are
linked to a major incident or when an incident matches a certain
pattern (e.g., keyword match).
3. Send follow-up reminders to the incident assignee if the incident
remains in the “In Progress” state for more than 3 days.
SCRIPT ACTION GYANINDRA YADAV
4. When a security incident is created, trigger alerts to the Security
Operations team and automatically assign the incident based on the
impacted CI's owner.
Why is Script Action needed when Script
Include is already there?
While Script Actions and Script Includes both involve scripting in ServiceNow,
they serve very different purposes. Here’s a clear and industry-relevant
explanation of why Script Actions are needed, even when Script Includes
exist:
Purpose Difference
Feature Purpose
Script Reusable server-side logic—functions or classes that can be
Include invoked from Business Rules, Script Actions, UI Actions, etc.
A specific type of server-side script that runs asynchronously in
Script
response to an event. Used to handle event-driven background
Action
tasks like notifications, record creation, logging, etc.
Think of It This Way:
• Script Include = Reusable Logic Library
• Script Action = Event Handler
You can use a Script Include inside a Script Action, but not the other way
around.
SCRIPT ACTION GYANINDRA YADAV
Why Script Actions Are Needed (Even with Script Includes)
1. Event-Driven Processing
• Use Case: When a problem.created event is fired, you want to log the
problem details in an external table or send a notification.
• Why Not Just Script Include?: Script Includes don’t listen to events. You
still need Script Actions to respond to that event.
2. Asynchronous Execution
• Script Actions run in the background, keeping the main user interaction
fast and smooth.
• Script Includes are usually called synchronously (unless wrapped in
GlideAjax or other methods).
3. Decoupling Logic from Business Rules
• Instead of writing bulky logic directly in Business Rules or Workflows, you
can fire an event and let a Script Action handle it separately.
• This makes your code modular, maintainable, and testable.
Typical Usage Together
You can (and should) use Script Includes inside Script Actions for complex
logic:
var util = new MyReusableUtil(); // Script Include
util.sendCustomNotification(current);
This keeps your Script Action clean and the logic centralized.
SCRIPT ACTION GYANINDRA YADAV
Summary
Can be triggered by Reusable
Feature Asynchronous?
Event? Logic?
Script No (unless
No Yes
Include wrapped)
Script Action Yes Yes Not directly
Conclusion:
Script Actions are necessary for handling event-based, asynchronous tasks,
which Script Includes alone cannot do. They complement each other—not
replace one another.
Here’s a visual flow to explain the relationship and roles of Script Actions and
Script Includes in ServiceNow, particularly in an ITSM use case:
SCRIPT ACTION GYANINDRA YADAV
Visual Flow: Script Action vs Script Include
[1] Incident Assigned to Group
[2] Business Rule detects change
[3] Event is fired (e.g., "incident.assigned")
[4] Script Action (Listens to the Event)
┌───────────────────────────────────
──────┐
│ Inside Script Action: │
│ - Prepare dynamic notification │
│ - OR create/update records │
│ - OR call integration │
└───────────────────────────────────
──────┘
[5] Calls a Script Include (Reusable logic)
┌────────────────────────────────────
─────────┐
│ Script Include: │
│ - Handles actual logic │
│ (e.g., build email body, assign user) │
SCRIPT ACTION GYANINDRA YADAV
│ - Can be reused elsewhere too │
└────────────────────────────────────
─────────┘
Explanation:
Step Component Role
1 User Action User assigns an incident to a group.
2 Business Rule Triggers an event when certain conditions are met.
3 Event System event fired, e.g., incident.assigned.
4 Script Action Listens for that specific event and runs asynchronously.
5 Script Include Called from Script Action for reusable, testable logic.
Example Use Case:
When an incident is assigned to the Network Support group, the system fires
an event and a Script Action sends a custom email using logic from a Script
Include.
SCRIPT ACTION GYANINDRA YADAV