Created
April 22, 2021 18:08
-
-
Save vetsin/d5022c21006b57f3ee4c79efdbecc1f1 to your computer and use it in GitHub Desktop.
ServiceNow utlitiy class for making sane HTTP requests from scoped script
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
Usage Examples and etc.: | |
Basic GET: | |
``` | |
var request = new Request(); | |
request.get('https://httpbin.org/get', function(hasError, response, body) { | |
gs.info(body); | |
}); | |
``` | |
Basic POST: | |
``` | |
var options = { | |
body: 'x=y' | |
} | |
request.post('https://httpbin.org/post', options, function(hasError, response, body) { | |
gs.info(body); | |
}); | |
``` | |
Or like so: | |
``` | |
var options = { | |
uri: 'https://httpbin.org/post', | |
form: {'x':'y'} | |
} | |
request.post( options, function(hasError, response, body) { | |
gs.info(body); | |
}); | |
``` | |
All options are... optional. | |
``` | |
var options = { | |
// can use `uri` OR `url` | |
uri: 'https://httpbin.org/post', | |
// instead of uri one can specify `host` OR `hostname` | |
host: 'httpbin.org', | |
schema: 'http', // defaults to `https`, used only with host | |
path: '', // defaults to `/`, used only with host | |
// auth supports `profile` || `user` || `custom` | |
auth: { | |
'profile': { // same as setAuthenticationProfile(type, id) | |
'type': '...', | |
'profileId': '...' | |
} | |
// OR | |
'user': { // basic authentication | |
'user': 'username', 'pass': 'password' | |
} | |
// OR | |
'custom': { // just some custom type | |
custom: function(params, restMessage) { | |
// for example: | |
restMessage.setHeader('Auth: custom AAAAZZZZ') | |
} | |
} | |
} | |
// standard query | |
query: { | |
'key': 'value' | |
} | |
// `body` || `form` || `json` in that order. | |
body: 'raw body data', | |
form: { 'x':'y', 'key': 'value '}, // encoded to `x=y&key=value` with proper header | |
json: { 'key': 'value ' }, // sent as json with proper header | |
// ignores `Host` header if specified | |
headers: { 'header', 'value' } | |
} | |
``` | |
*/ | |
var Request = Class.create(); | |
Request.prototype = { | |
initialize: function(debug) { | |
this.debug = debug || false; | |
}, | |
_initParams: function(uri, options, callback) { | |
if(this.debug) gs.debug('_initParams(' + uri + ', ' + options + ', ' + callback + ')') | |
if (typeof options === 'function') { | |
callback = options | |
} | |
var params = {} | |
if (typeof options === 'object') { | |
params = options; | |
params.uri = uri; | |
} else if (typeof uri === 'string') { | |
params.uri = uri; | |
} else { | |
params = uri; | |
} | |
params.callback = callback || params.callback; | |
// calculate URI if it's not provided | |
params = this._setup_uri(params); | |
return params; | |
}, | |
_setup_uri: function(params) { | |
// People use this property instead all the time, so support it | |
if(!params.uri && params.url) { | |
params.uri = params.url; | |
delete params.url; | |
} | |
if(!params.uri && (params.host || params.hostname)) { | |
var schema = params.schema || 'https' | |
var host = params.host || params.hostname; | |
var uri = '' + schema + '://' + host; | |
var path = params.path || '/' | |
uri = uri + path; | |
params.uri = uri; | |
} | |
return params; | |
}, | |
get: function(uri, options, callback) { | |
var params = this._initParams(uri, options, callback); | |
params.method = 'GET'; | |
return this._execute(params); | |
}, | |
post: function(uri, options, callback) { | |
var params = this._initParams(uri, options, callback); | |
params.method = 'POST'; | |
return this._execute(params); | |
}, | |
put: function(uri, options, callback) { | |
var params = this._initParams(uri, options, callback); | |
params.method = 'PUT'; | |
return this._execute(params); | |
}, | |
del: function(uri, options, callback) { | |
var params = this._initParams(uri, options, callback); | |
params.method = 'DELETE'; | |
return this._execute(params); | |
}, | |
_execute: function(params) { | |
var req = this._prepareRequest(params); | |
try { | |
var response = req.execute(); | |
if(this.debug) { | |
gs.debug('response.haveError: ' + response.haveError()); | |
if(response.haveError()) { | |
gs.debug('response.errorMessage: ' + response.getErrorMessage()); | |
} | |
gs.debug('response.code: ' + response.getStatusCode()); | |
gs.debug('response.body: ' + response.getBody()); | |
} | |
var hasError = response.haveError() || (response.getStatusCode() > 400); | |
if(params.callback) { | |
return params.callback(hasError, response, response.getBody()); | |
} | |
} catch (e) { | |
if(params.callback) { | |
return params.callback(true, e, ''); | |
} | |
} | |
return undefined; | |
}, | |
_prepareRequest: function(params) { | |
var rm = new sn_ws.RESTMessageV2(); | |
rm.setHttpMethod(params.method || 'GET'); | |
rm.setEndpoint(params.uri); | |
if(this.debug) gs.debug('' + params.method + ' ' + params.uri); | |
if('auth' in params) { | |
var authobj = params.auth; | |
if ('profile' in authobj) { | |
rm.setAuthenticationProfile(authobj.profile.type, authobj.profile.profileId); | |
} else if ('user' in authobj) { | |
// assume we have a pass too... | |
rm.setBasicAuth(authobj.user, authobj.pass); | |
} else if ('custom' in authobj) { | |
// Cause AWS and stuff | |
authobj.custom(params, rm); | |
} | |
} | |
var query_params = []; | |
for (var q in params.query) { | |
rm.setQueryParameter(q, params.query[q]); | |
query_params.push([q, encodeURIComponent(params.query[q])].join('=')); | |
} | |
if(this.debug) gs.debug('query_params: ' + JSON.stringify(query_params)); | |
if(params.body) { | |
rm.setRequestBody(params.body); | |
} else if (params.form) { | |
if(this.debug) gs.debug('Processing FORM request'); | |
rm.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded'); | |
var form_params = []; | |
for(var p in params.form) { | |
form_params.push([p, encodeURIComponent(params.form[p])].join('=')); | |
} | |
if(this.debug) gs.debug(form_params.join('&')); | |
rm.setRequestBody(form_params.join('&')); | |
} else if (params.json) { | |
if(this.debug) gs.debug('Processing json request'); | |
rm.setRequestHeader('Content-Type', 'application/json'); | |
rm.setRequestBody(JSON.stringify(params.json)); | |
} | |
if(this.debug) gs.debug('Extra Headers: ' + JSON.stringify(params.headers, null, 2)); | |
for (var h in params.headers) { | |
//rm.setRequestHeader(h, encodeURIComponent(params.headers[h])); | |
if(h === 'Host') continue; // don't really want this one... | |
rm.setRequestHeader(h, params.headers[h]); | |
} | |
return rm; | |
}, | |
type: 'Request' | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment