Can someone Explain why JSON returns empty unless I use " + ' ' "?

Hasnaat Khan
Tera Contributor

Hey guys so I've created an object as a script include and sent it to my client script as a JSON object to read and use the values.

        while (gr.next()) { //find viewed record data based on sys_id passed in from client
            obj.address_line_1 = gr.address_line_1 + ''; //JSON stringify returns empty unless quotations used at end
            obj.address_line_2 = gr.address_line_2 + '';
            obj.county = gr.county + '';
            obj.post_code = gr.post_code + '';
            obj.city = gr.city + '';
            return JSON.stringify(obj); //convert object to json and send to client
        }
    },

So to send it back into my client script I used JSON.stringify but it would always return "{}" or empty unless I use " + ' ' "

I fiigured it out from this thread here and I was just wondering if anyone can explain why?

https://community.servicenow.com/community?id=community_question&sys_id=56725bbedbfda740afc902d5ca961997

1 ACCEPTED SOLUTION

-O-
Kilo Patron
Kilo Patron

It is because properties of GlideRecord objects that represent fields are in fact objects of "type" GlideElement. So when you write

gr.address_line_1

address_line_1 is an object of type GlideElement. But it is not a genuine JavaScript object, it does not look to the run-time as if it had any enumerable properties, so it is serialized (stringified) as if it were an empty object. There are two ways a GlideElement "gives up" its underlying loaded value: by calling its toString() method, or - in global scope - by calling its getValue() method (not to be confused with its parent GlideRecord's getValue() method).

So when you write

obj.address_line_1 = gr.address_line_1;

you are attributing an (GlideElement) object reference to obj.address_line_1 which JSON.stringify() cannot inspect and so cannot serialize (stringify), whereas when you write

obj.address_line_1 = gr.address_line_1 + '';

which is the same as

obj.address_line_1 = gr.address_line_1.toString();

you are attributing a primitive string value to obj.address_line_1 which JSON.stringify() is for sure able to inspect and serialize.

Whenever you see gr.<a field name> used and it works, it is because it is used in a place where a string is expected and thus gr.<a field name>.toString() is automatically called by the run-time and thus the underlying value is "extracted" and used. That is why for instance gs.debug(gr.number); (assuming gr is a valid task GlideRecord) would print the number of the task in Scripts - Background: gs.debug() internally at some point, when it tries to print the debug message, it expects a string. If the message passed in as 1st parameter is not a string, it will first convert it to a string, by calling the passed in value's toString() method and thus getting the underlying value. In the end it is as if one wrote gs.debug(gr.number.toString()).

View solution in original post

5 REPLIES 5

You're welcome, I'm glad it helped! 🙂