adiddigi
Tera Guru
Options
- Subscribe to RSS Feed
- Mark as New
- Mark as Read
- Bookmark
- Subscribe
- Printer Friendly Page
- Report Inappropriate Content
‎04-09-2013
08:15 AM
I won't lie, I'm obsessed with JSON. I've been working with it and MongoDB for a couple of weeks now.JSON is Simple, portable and with REST protocol it is very easy to use.
The entire post is written thinking we can't pass an Object from a Script Include to a Client side, If you know any ways to pass an entire Glide Object, do let me know. But because of Mozilla Rhino sitting in the middle, I am positive we cannot pass an Object/Array as Arrays will be converted into Native array. Nevertheless, I think sending the data in a JSON is a nice way of exchanging data.
Two reasons to write this post:
I wanted to retrieve more than one value from a table using GlideAjax. You would probably direct me to this post here by John Roberts,where he explains how to pass more than one variables from Server side, encoding it as an XML.
Now, what if I want to access the entire Glide Record as-is. That would require you to encode all the columns, data into an XML and pass it, then on the Client side you will have to probably use XMLDocument or any XML parser to get the data.
We will be doing the same using JSON, and you will see how easy it is.I'll start with encoding your GlideRecord in JSON on server side, and retrieve it in a Business Rule / another script include.
I'm also working on getting structure and MVC to UI Pages/Macros in Service Now,as I don't want to completely attach my data to DOM. So I'm using handlebars.js template engine(don't get me wrong here - Jelly is a powerful template engine in itself, but to use backbone.js to its full potential, you might want to use a client side template engine like handlebars) which is compatible with Backbone.js and underscore.js, as we cannot use the templating function of underscore.js, because of XML restrictions. If you retrieve your data in JSON format, it will be very easy to template it and fill in the DOM easily.I'm going to post that too.
Okay, without delay lets get started:
Let's first encode the JSON data on Server Side, and retrieve it-
(but that you won't be using much - as GlideRecord object will probably give you everything you need. You might ask me, that you can still use the entire GlideRecord in the client script too.Yes! but that is a sync call which will freeze your page)
We'll retrieve a Glide Record object in two formats : As a JSON Object, and as a JSON String.
Name : SendJSON
/* We will have two functions - sendJSON which will encode your table data into a JSON object, and sendJSONAsString which will encode your object into a string */
/* We will have two functions - sendJSON which will encode your table data into a JSON object, and sendJSONAsString which will encode your object into a string */
var SendJSON_temp = Class.create();
SendJSON_temp.prototype = {
sendJSON: function(base_table,enc){
var finalEncoding = {};
var retArr = [];
var gr = new GlideRecord(base_table);
gr.addEncodedQuery(enc);
gr.query();
var grA = new GlideRecord(base_table);
grA.newRecord();
var fields = new GlideRecordUtil().getFields(grA);
var i=0;
while(gr.next()){
var o = {};
i=0;
while(fields<i>){
columnName = fields<i>;
o[columnName] = gr.getValue(columnName);
i++;
}
retArr.push(o);
}
finalEncoding['records'] = retArr;
return finalEncoding;
},
sendJSONO: function(base_table,enc,opt){
var optA = opt.split(',');
gs.log("Array was " + opt);
var finalEncoding = {};
var retArr = [];
var gr = new GlideRecord(base_table);
gr.addEncodedQuery(enc);
gr.query();
var grA = new GlideRecord(base_table);
grA.newRecord();
var fields = new GlideRecordUtil().getFields(grA);
var i=0;
while(gr.next() ){
var o = {};
i=0;
while(optA<i>){
columnName = optA<i>;
if(optA<i>.indexOf('.') != -1){
gs.log(optA<i>);
}
o[columnName] = gr.getValue(columnName);
i++;
}
retArr.push(o);
}
finalEncoding['records'] = retArr;
return finalEncoding;
},
sendJSONAsString:function(base_table,enc,opt){
var encObj;
if(opt == ''){
encObj = this.sendJSON(base_table,enc);
}
else{
gs.log("IN ELSE" + base_table+enc+opt);
encObj = this.sendJSONO(base_table,enc,opt);
gs.log(base_table+enc+opt);
}
var json = new JSON();
var text = json.encode(encObj);
return text;
}
};
Usage : From any Script Include/Business rule, you can call this Script Include method by using
.
new SendJSON().<function_name>
example:
var HelloWorld = Class.create();
HelloWorld.prototype = Object.extendsObject(AbstractAjaxProcessor, {
sendToClient:function(){
var enc = 'your encoded query';
var table = 'incident';
var text =new SendJSON().sendJSONAsString(table,enc);
return text;
}
});
Client Side is easy:
(I'm using the above Script Include, passing in the values from Client side)
var HelloWorld = Class.create();
HelloWorld.prototype = Object.extendsObject(AbstractAjaxProcessor, {
sendToClient:function(){
var enc = this.getParameter('sysparm_enc');
var table = this.getParameter('sysparm_tbl');
var text =new SendJSON().sendJSONAsString(table,enc);
return text;
}
});
Now on the client side, you can call this Script Include. A sample will be something like this :
var ga = new GlideAjax('HelloWorld');
ga.addParam('sysparm_name','sendToClient');
ga.addParam('sysparm_tbl','incident');
ga.addParam('sysparm_enc','sys_idSTARTSWITH75c5752ac46c4500b2fbeb58d4daf38e');
ga.addParam('sysparm_opt','str');
ga.getXML(HelloWorldParse);
function HelloWorldParse(response) {
var answer = response.responseXML.documentElement.getAttribute("answer");
console.log(answer);// Console log the string - using Firefox/Chrome - For me, I use Chrome.
/*Converting string into JSON Object with evalJSON(), and then each with iterate over the Array of Objects - Then you can use the columns directly*/
/* Prototype.js provides this beauty, evalJSON() which converts your JSON string into an Object.
Check it out here http://prototypejs.org/learn/json */
answer.evalJSON().records.each(function(obj){
console.log(obj.number);
});
}
}
I'm encoding this in the exact same format that Service Now's JSON Processer sends the JSON format. I'll in some time post on getting MVC into Service Now.
References : Tom's Utility Script Includes. Check them out, they are really well "expressed" 🙂
Edit: I've improved the code a little bit, and also added a new parameter called opt, into which you can pass comma separated columns names you want to retrieve(only), and you will get only those columns encoded rather than all columns. If you leave it blank, then you will get the data of entire columns.
9 Comments
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.