Correspondence between a JSON string and an EGL variable
This topic describes the EGL record that corresponds to a JavaScript Object Notation (JSON) string. Other topics describe the functions—serviceLib.convertFromJSON() and serviceLib.convertToJSON()—that are used by a Rich UI developer to convert JSON data to or from a variable, as may be necessary to access a third-party REST service. A failure in either function causes a RuntimeException.
JSON and EGL records
{ "EmpNo":10,"LastName":"Smith" }
Record MyRecordPart
EmpNo INT;
LastName STRING;
end
You can use any primitive type other than BLOB or CLOB. An EGL record field is also valid if based on a DataItem part that is, in turn, based on one of the supported primitive types.
{ "Emp-No":10,"LastName":"Smith" }
Record MyRecordPart
EmpNo INT {JSONName = "Emp-No"};
LastName STRING;
end
(You cannot override the value of JSONName when you declare a record that is based on the Record part.)
{"Result":{"aTimestamp":1191871152}}
A general rule is that each bracketed clause in the JSON string is the content of a runtime JSON object, which is equivalent to an EGL record.
Record MyTopPart
Result MyTimestampPart;
end
Record MyTimestampPart
aTimestamp BIGINT;
end
As shown, each JSON identifier (which precedes a colon) requires the presence of a field in a record. If a JSON field name is an EGL reserved word (for example, "TimeStamp"), you must access serviceLib.convertFromJSON() or serviceLib.convertToJSON() by using a dictionary rather than a record. We show this variation later in this topic.
{"Menu":
{ "id": "file", "value": "File", "popup":
{"Menuitem":
[
{"value": "New", "onClick": "CreateNewDoc()"},
{"value": "Open", "onClick": "OpenDoc()"},
{"value": "Close", "onClick": "CloseDoc()"}
]
}
}
}
(At this writing, that example and others are at http://json.org/example.html.)
Record MyTopPart
Menu MyMenuPart;
end
Record MyMenuPart
id STRING;
value STRING;
popup MyPopupPart;
end
Record MyPopupPart
MenuItem MyElementPart[];
end
Record MyElementPart
value STRING;
onClick STRING;
end
To further explore how to use a record when accessing a JSON string, see the Rich UI sample geocode.records.
JSON and EGL dictionaries
myRef Dictionary
{
ID = 5,
lastName = "Twain",
firstName = "Mark"
};
You interact with the dictionary as described in "Dictionary part" and related topics in the EGL help system.
{"Result":{"aTimestamp":1191871152}}
myTime Dictionary;
A general rule is that each bracketed clause in the JSON string is equivalent to an EGL dictionary. In relation to our example JSON string, the function serviceLib.convertFromJSON() treats the symbol at the left of the first colon (:) as the key of a dictionary entry. The key is Result, which is case sensitive. Here (as in all cases) the content to the right of a colon is the value associated with the key whose name is at the left of the colon.
myTime Dictionary
{
Result = new Dictionary{ aTimestamp = 1191871152 }
};
numberOfSeconds BIGINT = myTime.Result.aTimestamp;
{"Result":{"Timestamp":1191871152}}
numberOfSeconds BIGINT = myTime.Result["Timestamp"];
{"Menu":
{ "id": "file", "value": "File", "popup":
{"Menuitem":
[
{"value": "New", "onClick": "CreateNewDoc()"},
{"value": "Open", "onClick": "OpenDoc()"},
{"value": "Close", "onClick": "CloseDoc()"}
]
}
}
}
In this example, the dictionary has a single entry whose key is named Menu. The value associated with that key is an anonymous dictionary, as indicated by the brackets that embed the string "id" and all the strings that follow. That anonymous dictionary includes the keys id, value, and popup, along with the values of those keys. You may never have the kind of complexity introduced by the key called popup, but the problem is workable. You can see the relationships in the example JSON string.
Here is a question for you to consider: What statement is necessary to access the string "OpenDoc()", assuming that the function serviceLib.convertFromJSON() has copied the previous JSON string to a dictionary called myMenu?
myString STRING = myMenu.Menu.popup.MenuItem[2].onClick;
myMenu Dictionary
{ Menu = new Dictionary
{ id = "file",
value = "File",
popup = new Dictionary
{ MenuItem = new Dictionary[]
{ new dictionary {value = "New", onClick = "CreateNewDoc()" },
new dictionary {value = "Open", onClick = "OpenDoc()" },
new dictionary {value = "Close", onClick = "CloseDoc()"}
}
}
}
};
- Each dictionary in a hierarchy of dictionaries is equivalent to a bracketed clause in the JSON string
- Each key is assigned a primitive value, a dictionary, a record, or an array of dictionaries or records.
To further explore how to use a dictionary record when accessing a JSON string, see the Rich UI sample geocode.dictionaries.
JSON and both records and dictionaries
- When you prepare to invoke serviceLib.convertFromJSON() with a record
- When you prepare to invoke serviceLib.convertToJSON() with a record or dictionary
{"Result":{"Timestamp":1191871152}}
Record ResultRecordPart
Result Dictionary;
end
myResult ResultRecordPart;
milliseconds BIGINT;
serviceLib.convertFromJSON(resp.body, myResult);
milliseconds = myResult.Result["Timestamp"] as BIGINT;
{"Menu":
{ "id": "file", "value": "File", "popup":
{"Menuitem":
[
{"value": "New", "onClick": "CreateNewDoc()"},
{"value": "Open", "onClick": "OpenDoc()"},
{"value": "Close", "onClick": "CloseDoc()"}
]
}
}
}
Record MyTopPart
Menu MyMenuPart;
end
Record MyMenuPart
id STRING;
value STRING;
popup Dictionary;
end
popup Dictionary
{ MenuItem = new Dictionary[]
{ new Dictionary {value = "New", onClick = "CreateNewDoc()" },
new Dictionary {value = "Open", onClick = "OpenDoc()" },
new Dictionary {value = "Close", onClick = "CloseDoc()"}
}
}
(We show that dictionary for illustration. The substructure of a Dictionary may be useful when you are invoking serviceLib.convertToJSON(), but is not used when you are invoking serviceLib.convertFromJSON() .)
myTop MyTopPart;
itemString STRING;
serviceLib.convertFromJSON(resp.body, myTop);
itemString = myTop.Menu.popup.MenuItem[2].onClick;