Name
sn_cd.cd_TodoProcessor
Description
No description available
Script
var cd_TodoProcessor = Class.create();
cd_TodoProcessor.prototype = {
initialize: function() {},
/** Process content for a content type
* @param contentType string content type value e.g. task'
*/
processContent: function() {
var grContentVisibility = new GlideRecord('sn_cd_content_visibility');
grContentVisibility.addActiveQuery();
grContentVisibility.addNotNullQuery('when_to_process');
grContentVisibility.addNullQuery('approvers').addOrCondition('state', 'published');
grContentVisibility.addQuery('content.content_type.category', 'todo_content');
grContentVisibility.orderBy('when_to_process');
grContentVisibility.query();
if (grContentVisibility.hasNext())
this.processTodos(grContentVisibility);
},
/** Process to-dos for content visibility audience
* @param grContentVisibility GlideRecord [sn_cd_content_visibility] Content visibility record to retrieve audience from
*/
processTodos: function(grContentVisibility) {
var TASK_EVENT_NAME = 'sn_cd.todo.content_todo';
var MAX_RUN_TIME = this._getNumberProperty("sn_cd.todo.max_run_time", 600);
var MAX_ASSIGNEES = this._getNumberProperty("sn_cd.todo.max_assignees", 50000);
var MAX_USERS_PER_EVENT = this._getNumberProperty("sn_cd.todo.max_users_per_event", 10000);
var MAX_EVENTS = this._getNumberProperty("sn_cd.todo.max_events", 50);
var EVENT_STAGGER = this._getNumberProperty("sn_cd.todo.event_stagger", 60);
var cd_Audience = new sn_cd.cd_Audience();
var gdtStart = new GlideDateTime();
var gdtEnd = new GlideDateTime();
gdtEnd.addSeconds(MAX_RUN_TIME);
var eventCount = 0;
while (eventCount < MAX_EVENTS &&
gdtEnd.after(new GlideDateTime()) &&
grContentVisibility.next()) {
var grContentTask = grContentVisibility.content.getRefRecord();
if (!grContentTask.isValidRecord() || !grContentTask.active) {
grContentVisibility.setValue("notification_status", "error");
grContentVisibility.setValue("active", false);
grContentVisibility.update();
gs.warn("Script - " + this.type + ": Failed to find active content for schedule " + grContentVisibility.getUniqueValue());
continue;
}
var assignees;
if (grContentVisibility.getValue('use_adhoc_users') == true)
assignees = grContentVisibility.getValue('users').split(",");
else
assignees = cd_Audience.getAudience(grContentVisibility.getValue("audience"));
var eventsToCreate = Math.ceil(assignees.length / MAX_USERS_PER_EVENT);
// Filter out content visibilities that can never process due to exceeding maximums
if (assignees.length > MAX_ASSIGNEES || eventsToCreate > MAX_EVENTS) {
grContentVisibility.setValue("notification_status", "max_exceeded");
grContentVisibility.setValue("active", false);
grContentVisibility.update();
continue;
}
// Skip if content visibility will exceed leftover event allotment. NOTE: It's possible that every next content visibility exceeds the leftover
if (eventCount + eventsToCreate > MAX_EVENTS)
continue;
// Mark completed_on before creating tasks to prevent duplicate tasks if transaction times out
grContentVisibility.setValue("active", false);
grContentVisibility.setValue("notification_status", "sent"); // This field now acts as Content status
grContentVisibility.completed_on = new GlideDateTime();
grContentVisibility.update();
// Chunk and stagger events
var gdtWhenToProcess = new GlideDateTime(grContentVisibility.when_to_process);
// Adjust this time to now if in the past
if (gdtWhenToProcess.before(gdtStart))
gdtWhenToProcess = new GlideDateTime();
for (var i = 0; i < assignees.length && MAX_USERS_PER_EVENT > 0; i += MAX_USERS_PER_EVENT) {
var assigneesChunk = assignees.slice(i, i + MAX_USERS_PER_EVENT);
gs.eventQueueScheduled(TASK_EVENT_NAME, grContentVisibility, assigneesChunk, null, gdtWhenToProcess);
eventCount++;
gdtWhenToProcess.addSeconds(EVENT_STAGGER);
}
}
},
/** Create tasks for a list of users
* @param grContentVisibility GlideRecord [sn_cd_content_visibility] The visibility record referencing a content to-do to create tasks with
* @param userArray Array List of sys_user sys_id's to create tasks for
*/
createTasks: function(grContentVisibility, userArray) {
if (!userArray || !userArray.length)
return;
var grContentTask = grContentVisibility.content.getRefRecord();
if (!grContentTask.isValidRecord() || !grContentTask.active) {
gs.warn("Script - " + this.type + ": Failed to find active content for schedule " + grContentVisibility.getUniqueValue());
return;
}
for (var i = 0; i < userArray.length; i++) {
var grTask = new GlideRecord("sn_cd_task");
grTask.setValue("assigned_to", userArray[i]);
grTask.setValue("short_description", grContentTask.title.toString());
if (grContentVisibility.due_date.toString())
grTask.due_date.setDateNumericValue(grContentVisibility.due_date.dateNumericValue());
grTask.setValue("content_todo", grContentTask.getUniqueValue());
grTask.setValue("sys_domain", grContentTask.sys_domain.toString());
if (GlidePluginManager.isActive("com.snc.esign"))
grTask.setValue("sn_esign_esignature_configuration", grContentTask.esig_template.toString());
grTask.setValue("created_from_scheduled_content", grContentVisibility.getUniqueValue());
grTask.insert();
}
},
/** Return a number value for a given property
* @param propName String Name of a property
* @param defaultValue Number The default value to use for a property
* @return Number The number value for a given property
*/
_getNumberProperty: function(propName, defaultValue) {
var propValue = Number(gs.getProperty(propName, defaultValue));
if (isNaN(propValue)) {
gs.warn("Script - " + this.type + ": Overriding invalid property value for " + propName);
propValue = defaultValue;
}
return propValue;
},
type: 'cd_TodoProcessor'
};
Sys ID
60db0c42eb721300a9e7e26ac106fe95