Skip to content

Instantly share code, notes, and snippets.

@paulsena
Last active February 18, 2021 19:35
Show Gist options
  • Save paulsena/10121675 to your computer and use it in GitHub Desktop.
Save paulsena/10121675 to your computer and use it in GitHub Desktop.
Service Now Email Attachment Processor.Allows ServiceNow to accept attachments via email and process them through a data source/import set/ transform map.
/*
* Script include to process multiple attachments in an email through OOB Data Source process.
* Attaches to existing data source, dynamically creates a schedule import entry and runs.
* Processes attachments synchronously to prevent issues with multiple attachments
*
* Source: Fruition Partners
* Author: [email protected]
* Author: [email protected]
*/
var AttachmentImportProcessor = Class.create();
AttachmentImportProcessor.prototype = {
record: null,
scheduledImportRecord: null,
dataSourceRecord: null,
attachmentTypes: [],
debug: true,
log: null,
initialize: function(record, dataSourceSysId) {
this.record = record;
this._getDatasource(dataSourceSysId);
this.log = new GSLog("com.ally.ecm.log", "AttachmentImportProvider");
if (this.debug) { this.log.setLevel('debug') };
},
setAttachmentTypes: function(types){
for (var i = 0; i < types.length; i++) {
this.attachmentTypes.push(types[i]);
}
},
processAttachments: function () {
if (!this.dataSourceRecord) {
return false;
}
var sourceTable = this.record.sys_class_name.toString();
var sourceID = this.record.sys_id.toString();
var targetTable = this.dataSourceRecord.getTableName();
var targetID = this.dataSourceRecord.sys_id.toString();
var gr = this._getAttachments(sourceTable, sourceID);
this._logDebug("Num Attachments sent: " + gr.getRowCount());
this._logDebug("Valid Attachment Types: " + this.attachmentTypes);
while (gr.next()) {
if (this._isAttachmentValidType(gr)) {
this._copyAttachment(gr, targetTable, targetID);
this._logDebug("Processing attachment: " + gr.file_name);
this._processImportSynchronous();
}
}
},
_getDatasource: function(dataSourceSysId){
this.dataSourceRecord = new GlideRecord("sys_data_source");
if (this.dataSourceRecord.get(dataSourceSysId) == false) {
this.dataSourceRecord = null;
}
},
_getAttachments: function(sourceTable, sourceID){
var gr = new GlideRecord("sys_attachment");
gr.addQuery("table_name", sourceTable);
gr.addQuery("table_sys_id", sourceID);
gr.query();
return gr;
},
_isAttachmentValidType: function(gr){
if (this.attachmentTypes == null || this.attachmentTypes.length == 0) {
return true;
} else {
var isValid = false;
var type = gr.content_type.toString();
for (var i = 0; i < this.attachmentTypes.length; i++) {
if (this.attachmentTypes[i] == type) {
isValid = true;
break;
}
}
if (!isValid) {
this._logDebug("Rejected Attachment Type: " + type);
}
return isValid;
}
return false;
},
_copyAttachment: function (gr, targetTable, targetID) {
var attachment = Packages.com.glide.ui.SysAttachment();
attachment.deleteAll(this.dataSourceRecord);
gr.table_name = targetTable;
gr.table_sys_id = targetID;
var oldid = gr.sys_id.toString();
var newid = gr.insert();
var doc = new GlideRecord("sys_attachment_doc");
doc.setWorkflow(false);
doc.addQuery("sys_attachment", oldid);
doc.query();
while (doc.next()) {
doc.setValue("sys_attachment", newid);
doc.insert();
}
},
_processImportSynchronous: function () {
var retVal = false;
this._getImportRecord();
if (this.scheduledImportRecord != null && this.scheduledImportRecord.isValidRecord()) {
var trigger = "";
var triggerGr = new GlideRecord("sys_trigger");
trigger = Packages.com.snc.automation.TriggerSynchronizer.executeNow(this.scheduledImportRecord);
triggerGr.get(trigger);
while (triggerGr.isValidRecord()) {
triggerGr = new GlideRecord("sys_trigger");
triggerGr.get(trigger);
}
retVal = true;
} else {
//Log
}
return retVal;
},
_getImportRecord: function () {
this.scheduledImportRecord = new GlideRecord("scheduled_import_set");
this.scheduledImportRecord.addQuery("name", this.dataSourceRecord.name);
this.scheduledImportRecord.addQuery("data_source", this.dataSourceRecord.sys_id);
this.scheduledImportRecord.query();
if (!this.scheduledImportRecord.next()) {
this.scheduledImportRecord = new GlideRecord("scheduled_import_set");
this.scheduledImportRecord.initialize();
this.scheduledImportRecord.name = this.dataSourceRecord.name.toString();
this.scheduledImportRecord.active = false;
this.scheduledImportRecord.data_source = this.dataSourceRecord.sys_id.toString();
this.scheduledImportRecord.post_script_bool = true;
this.scheduledImportRecord.post_script = "";
this.scheduledImportRecord.insert();
this._logDebug("Scheduled Import created.");
} else {
this._logDebug("Scheduled Import set found: " + this.scheduledImportRecord.sys_id.toString());
}
},
_logDebug: function(msg){
this.log.logDebug(msg);
},
_logError: function (msg) {
this.log.logErr(msg);
},
type: 'AttachmentImportProvider'
}
/*
* Inbound email action script for processing Attachments sent via Email.
* Attaches to a data source, then runs a scheduled import against it.
* Author: [email protected]
* Uses Script Include: AttachmentImportProcessor - Also by Fruition Partners
*/
//Settings - Update the data source with the appropriate SYS ID that has the Transform Map we want to use.
var dataSourceSysId = '42686ebffdec29803750565f39c4cb74';
var validAttachments = ['application/vnd.ms-excel','text/csv'];
//-----Do not need to change anything below this-----
//Query for the sys_email record (incoming email) that contains the attachment and attach to data source
var grEmailLog = new GlideRecord('sys_email');
grEmailLog.addQuery('uid', email.uid);
grEmailLog.orderByDesc('sys_created_on');
grEmailLog.query();
if (grEmailLog.next()) {
var processor = new AttachmentImportProcessor(grEmailLog, dataSourceSysId);
processor.setAttachmentTypes(validAttachments);
processor.processAttachments();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment