Name
global.AllowedHostnameHelper
Description
No description available
Script
var AllowedHostnameHelper = Class.create();
AllowedHostnameHelper.prototype = {
initialize: function() {
this.ALLOWED_HOSTNAME_TABLE = "sys_cs_hostname_allow_list";
this.existingHostnames = this._getExistingHostnamesFromAllowListTable();
this.WILDCARD = '*.';
},
/*
* Ex 1. url: https://www.abc.service-now.com
* output hostname: abc.service-now.com
*
* Ex 2. url: https://support.microsoft.com
* output hostname: *.microsoft.com
*/
extractHostnameFromURL: function(url) {
var logUtil = new LinkUnfurlingLoggingUtils();
if (gs.nil(url)) {
logUtil.atWarn(url).log("The provided URL {0} for parsing is empty or invalid.", url);
return;
}
var hostname = this._stripProtocolFromURL(url);
if (gs.nil(hostname)) {
logUtil.atWarn(url).log("The hostname {0} in URL is empty or undefined.", hostname);
return;
}
return this._processHostname(hostname);
},
/*
* Get the hostname from a given URL and always keep the http / https. e.g.
* Input url: https://www.service-now.com/docs/troubleshooting.html
* Output hostname: https://www.service-now.com
*/
extractHostnameFromURLWithProtocol: function(url) {
if (gs.nil(url)) {
new LinkUnfurlingLoggingUtils().atWarn(url).log("The provided URL {0} for parsing is empty or invalid.", url);
return;
}
return this._removePathFromURL(url);
},
insertHostname: function(hostname) {
if (gs.nil(hostname))
return;
var allowedDomainGr = new GlideRecord(this.ALLOWED_HOSTNAME_TABLE);
allowedDomainGr.setValue('hostname', hostname);
allowedDomainGr.setValue('active', true);
allowedDomainGr.insert();
},
checkHostnameExists: function(hostname) {
if (gs.nil(hostname))
return false;
return this.existingHostnames.indexOf(String(hostname)) >= 0;
},
/*
* Given a URL https://www.google.com
* check if URL is in allow list
* else get the hostname, check if hostname exists in the allow list with wildcard
*/
isURLAllowedForUnfurling: function(url) {
if (gs.nil(url))
return false;
var hostname = '';
hostname = this._stripProtocolFromURL(url);
if (gs.nil(hostname))
return false;
if (this.checkHostnameExists(hostname))
return true;
else {
hostname = this._processHostname(hostname);
return this.checkHostnameExists(hostname);
}
},
_getExistingHostnamesFromAllowListTable: function() {
var existingHostnames = [];
var hostnameGr = new GlideRecord(this.ALLOWED_HOSTNAME_TABLE);
hostnameGr.addActiveQuery();
hostnameGr.addDomainQuery(this._getDomainQuery(gs.getUser().getDomainID()));
hostnameGr.query();
while (hostnameGr.next())
existingHostnames.push(hostnameGr.getValue('hostname'));
return existingHostnames;
},
_getDomainQuery: function(domainId) {
/*If the user uses the domain picker to switch to the global domain, gs.getUser().getDomainID() returns the string "global".
For all other domains, the method returns the sys_id of that domain.*/
if (gs.nil(domainId) || domainId === 'global')
return 'global';
else {
var domainGr = new GlideRecord('domain');
domainGr.get(domainId);
return domainGr;
}
},
_stripProtocolFromURL: function(url) {
var urlParts = url.replace('http://','').replace('https://','').split(/[/?#]/);
return urlParts[0];
},
_removePathFromURL: function(url) {
var urlParts = url.split(/[/?#]/);
if (url.startsWith("http"))
return urlParts[0] + "//" + urlParts[2];
return urlParts[0];
},
_processHostname: function(hostname) {
var parts = hostname.split('.');
var domain = parts.slice(-2).join('.');
if (domain.indexOf('service-now.com') === 0)
return hostname;
else
return this.WILDCARD + domain; //append the wild card for domains
},
type: 'AllowedHostnameHelper'
};
Sys ID
b35328d473522010f14a063f34f6a7fd