what's the simplest way to respond in json using grails?
E.G. the following doesn't work.
boolean a = false
render a as JSON
Grails requires that the target of the JSON converter be something that can be represented as a collection of name/value pairs or an ordered list. So an object such as a map or list would work. And non-primitive objects should also work, since they can be represented as a map of properties.
In your case, something like this would work:
def a = []
a << false
render a as JSON
directly from the documentation, something like
render(contentType: "text/json") {
hello = "world"
}
render(contentType: "application/json"){
message{
a.each{val->
value(val)
}
}
}
Use grails.converter.JSON and you can build the json map directly
http://manbuildswebsite.com/2010/02/08/rendering-json-in-grails-part-2-plain-old-groovy-objects-and-domain-objects/
Related
I need a way to remove leading square brackets from a json file. Im doing it in SAP cloud platform integration (CPI). Currently I was thinking of using groovy but can't seem to find a way to do it. Heres the JSON example:
[{
"salesOrderNumber": "1234567",
"orderStatus": "Complete",
"customerPONumber": "7654321",
"soldToID": "ABC",
"soldToName": "CBA"
}
]
Thank you in advance
The Code I used for getting just one element, But I need to get multiple in case there are any.
def Message processData(Message message) {
def body = message.getBody(String.class);
def jsonParser = new JsonSlurper();
def jsonObject = jsonParser.parseText(body);
def json = JsonOutput.toJson(jsonObject[0]);
println(json);
message.setBody(json);
return message;
}
You have a list of objects in json. Remove square brackets means get rid of the list and keep only one element of this list.
Btw, what if there are several or zero elements in the list?
So, your algorithm
parse json
get first element list[0]
serialize result back into json
As a code reference look at this documentation: https://groovy-lang.org/json.html
I am trying to do the following:
render [assignedSchol:assignedSchol,scholType:scholType] as JSON
assignedSchol is an object, and scholType is just a value. I get a "No map entry allowed at this place error". any help?
When you use one liner like you did you must put the conversion in braces like this:
render ( [assignedSchol:assignedSchol,scholType:scholType] as JSON )
But I think the above code returns json data as plain text format so I usually prefer doing it this way:
render(contentType: "text/json") {
[assignedSchol:assignedSchol,scholType:scholType]
}
Which gives me json data with response type json.
This should work:
render(contentType: "application/json") {[assignedSchol:assignedSchol,scholType:scholType]}
I have a json object that gets passed into a save function as
{
"markings": {
"headMarkings": "Brindle",
"leftForeMarkings": "",
"rightForeMarkings": "sock",
"leftHindMarkings": "sock",
"rightHindMarkings": "",
"otherMarkings": ""
}
** EDIT **
The system parses it and passes it to my function as a mapping. I don't actually have the JSON, although it wouldn't be difficult to build up the JSON myself, it just seems like overkill
* END EDIT **
The toString() function ends up putting the results into the database as
"[rightForeMarkings:, otherMarkings:, leftForeMarkings:sock, leftHindMarkings:sock, rightHindMarkings:, headMarkings:brindle]"
I then want to save that as a string (fairly easy) by calling
params.markings.toString()
From here, I save the info and return the updated information.
My issue is that since I am storing the object in the DB as a string, I can't seem to get the markings back out as a map (to then be converted to JSON).
I have tried a few different things to no avail, although it is completely possible that I went about something incorrectlywith these...
Eval.me(Item.markings)
evaluate(Item.markings)
Item.markings.toList()
Thanks in advance for the help!
Throwing my tests.
Using JSON converters in Grails, I think this should be the approach: (synonymous to #JamesKleeh and #GrailsGuy)
def json = '''{
"markings": {
"headMarkings": "Brindle",
"leftForeMarkings": "",
"rightForeMarkings": "sock",
"leftHindMarkings": "sock",
"rightHindMarkings": "",
"otherMarkings": ""
}
}'''
def jsonObj = grails.converters.JSON.parse(json)
//This is your JSON object that should be passed in to the method
print jsonObj //[markings:[rightForeMarkings:sock, otherMarkings:, leftForeMarkings:, leftHindMarkings:sock, rightHindMarkings:, headMarkings:Brindle]]
def jsonStr = jsonObj.toString()
//This is the string which should be persisted in db
assert jsonStr == '{"markings":{"rightForeMarkings":"sock","otherMarkings":"","leftForeMarkings":"","leftHindMarkings":"sock","rightHindMarkings":"","headMarkings":"Brindle"}}'
//Get back json obj from json str
def getBackJsobObj = grails.converters.JSON.parse(jsonStr)
assert getBackJsobObj.markings.leftHindMarkings == 'sock'
If I understand correctly, you want to convert a String to a JSON object? You can actually bypass converting it to a map, and parse it directly as a JSON object:
import grails.converters.JSON
def json = JSON.parse(Item.markings)
This will give you your entire JSON object, and then you can just reference the values as you would a map.
Edit #2:
So apparently there is no "safe" way to convert that string back to a map without something custom. I would recommend saving the structure in the database as it originally comes in. If you can do that, then all you would need is JSON.parse()
I have been trying to evaluate GWT Autobean feature to decode/encode JSON object to domain objects for REST calls.
Following the example : http://code.google.com/p/google-web-toolkit/wiki/AutoBean#Quickstart
I was able to convert a singular JSON object to a domain object:
AutoBean<Person> personBean = AutoBeanCodex.decode(factory, Person.class, JsonResources.INSTANCE.json().getText());
where JsonResources.INSTANCE.json() is returning a JSON string.
However, I haven't been successful to convert a list of Person objects from JSON.
It would be helpful, if anyone has an example of this?
Thanks!
Well the only way I can think of is to create a special autobean, which will have List<Person> property. For example:
public interface Result {
void setPersons(List<Person> persons);
List<Person> getPersons();
}
And example json string:
{
persons:[
{"name":"Thomas Broyer"},
{"name":"Colin Alworth"}
]
}
UPDATE:
Workaround when input JSON is an array ( as suggested by persons[0] in comments).E.g. JSON looks like this:
[{"name":"Thomas Broyer"},{"name":"Colin Alworth"}]
And parsing code looks like this:
AutoBeanCodex.decode(factory, Result.class, "{\"persons\": " + json + "}").getPersons();
I want every JSON response to post-request to contain a field success. What's the best way to add this field there?
I use code like this to generate JSON responses:
try {
def entity = myService.saveEntity(arg1,arg2)
render entity as JSON //I want to add artificial field 'success = "yes"' here
} catch (ValidationException e) {
render parseErrors(e.errors) as JSON //field 'success = "no"' here
}
I just struggled with this exact issue this week. I wanted to send back a domain class as JSON but at the same time add an 'errorMessage' property that would potentially contain additional information.
Turns out that when using as JSON in grails it sends back a converter object, but its possible to turn that converter instance into a jsonObject using JSON.parse() which we can easily add new values to.
def jsonObject = JSON.parse((entity AS JSON).toString())
jsonObject.put("success", "yes")
render jsonObject as JSON
I think there are a couple of different approaches but this ended up being the easiest for me since I already have custom converters for most of my domain classes and I didn't want to add any other transient properties to my domain object.
Could you return a map containing the success field, and the object wrapped inside a separate variable:
try {
def entity = myService.saveEntity(arg1,arg2)
render [ success:'yes', val:entity ] as JSON
} catch (ValidationException e) {
render [ success:'no', val:parseErrors(e.errors) ] as JSON
}
Not tested it mind...
You can register your own JSON marshaller (at BootStrap.groovy, for example), like:
JSON.registerObjectMarshaller(MyEntity) { MyEntity it ->
return [
someField : it.someField, // you should specify fields for output, or put all '.properties'
success : true // as I understand you always have 'true' for real entity
]
}
where MyEntity is your class you want to use