json - Grails:从请求中解析 JSON 的简单有效的方法

标签 json grails grails-plugin

如果这是一个重复的问题,请原谅我。我已经完成了一些具有类似要求的问题/答案,但同时不知何故有点不知所措和困惑。我的要求是:

  • 我得到一个 JSON 字符串/对象作为请求参数。 (例如:params.timesheetJSON)
  • 然后我必须解析/迭代它。

  • 这是我的 grails Controller 将收到的 JSON:
    {
        "loginName":"user1",
        "timesheetList":
        [
            {
                "periodBegin":"2014/10/12",
                "periodEnd":"2014/10/18",
                "timesheetRows":[
                    {
                        "task":"Cleaning",
                        "description":"cleaning description",
                        "paycode":"payCode1"
                    },
                    {
                        "task":"painting",
                        "activityDescription":"painting description",
                        "paycode":"payCode2"
                    }
                ]
            }
        ],
        "overallStatus":"SUCCESS"
    }
    

    问题:
  • 如何从请求中检索整个 JSON 字符串? request.JSON 在这里好吗?如果是这样,request.JSON.timesheetJSON 会产生我想要作为 JSONObject 的实际 JSON 吗?
  • 解析从请求中获得的 JSON 对象的最佳方法是什么?是 grails.converters.JSON 吗?或者有没有其他简单的解析方法?就像一些 API 通过自动处理解析将 JSON 作为对象集合返回。还是以编程方式解析 JSON 对象是唯一的方法?

  • 就像我说的,如果这个问题听起来很模糊,请原谅我。任何使用 grails 解析 JSON 的好的引用在这里也可能会有所帮助。

    编辑:我现在获取 JSON 字符串的方式发生了变化。我将 JSON 字符串作为请求参数。
    String saveJSON // This holds the above JSON string.
    
    def jsonObject = grails.converters.JSON.parse(saveJSON) // No problem here. Returns a JSONObject. I checked the class type.
    def jsonArray = jsonArray.timesheetList // No problem here. Returns a JSONArray. I checked the class type.
    println "*** Size of jsonArray1: " + jsonArray1.size() // Returns size 1. It seemed fine as the above JSON string had only one timesheet in timesheetList
    
    def object1 = jsonArray[1] // This throws the JSONException, JSONArray[1] not found. I tried jsonArray.getJSONObject(1) and that throws the same exception.
    

    基本上,我现在希望无缝地遍历 JSON 字符串。

    最佳答案

    我写了一些代码来解释如何做到这一点,你可以在下面看到,但要清楚,首先是你问题的答案:

  • 您在上面编写的 JSON 字符串将是您的 POST 有效负载的内容到其余 Controller 。 Grails 将使用其数据绑定(bind)机制将传入的数据绑定(bind)到您应该准备的 Command 对象。它必须具有与 JSON 字符串中的参数相对应的字段(见下文)。将命令对象绑定(bind)到实际的域对象后,只需对字段和列表进行操作
  • 即可获得所需的所有数据。
  • 通过 JSON 对象解析的方法如下面的示例所示。传入的请求本质上是一个嵌套映射,可以通过点
  • 简单地访问

    现在一些代码说明了如何做到这一点。
    在您的 Controller 中创建一个接受“YourCommand”对象作为输入参数的方法:
    def yourRestServiceMethod (YourCommand comm){
        YourClass yourClass = new YourClass()
        comm.bindTo(yourClass)
    
        // do something with yourClass
        // println yourClass.timeSheetList
    }
    

    该命令如下所示:
    class YourCommand {
        String loginName
        List<Map> timesheetList = []
        String overallStatus
    
        void bindTo(YourClass yourClass){
            yourClass.loginName=loginName
            yourClass.overallStatus=overallStatus
            timesheetList.each { sheet ->
                TimeSheet timeSheet = new TimeSheet()
                timeSheet.periodBegin = sheet.periodBegin
                timeSheet.periodEnd = sheet.periodEnd
                sheet.timesheetRows.each { row ->
                    TimeSheetRow timeSheetRow = new TimeSheetRow()
                    timeSheetRow.task = row.task
                    timeSheetRow.description = row.description
                    timeSheetRow.paycode = row.paycode
                    timeSheet.timesheetRows.add(timeSheetRow)
                }
    
                yourClass.timeSheetList.add(timeSheet)
            }
        }
    }
    

    它的“bindTo”方法是理解如何从传入请求中获取参数并将其映射到常规对象的关键逻辑部分。该对象的类型是“YourClass”,它看起来像这样:
    class YourClass {
        String loginName
        Collection<TimeSheet> timeSheetList = []
        String overallStatus
    }
    

    属于该类的所有其他类:
    class TimeSheet {
        String periodBegin
        String periodEnd
        Collection<TimeSheetRow> timesheetRows = []
    }
    

    最后一个:
    class TimeSheetRow {
        String task
        String description
        String paycode
    }
    

    希望这个例子对你来说足够清楚并回答你的问题

    编辑:根据新要求扩展答案

    查看您的新代码,我发现您在写那篇文章时可能有一些拼写错误
    def jsonArray = jsonArray.timesheetList
    

    应该:
    def jsonArray = jsonObject.timesheetList
    

    但是您显然在代码中正确地使用了它,否则它将无法正常工作,那么与“println”的那一行相同:
    jsonArray1.size()
    

    应该是:
    jsonArray.size()
    

    和基本修复:
    def object1 = jsonArray[1]
    

    应该
    def object1 = jsonArray[0]  
    

    你的数组大小==1,索引从0开始。//有那么容易吗? ;)

    那么“object1”又是一个 JSONObject,因此您可以使用“.”访问字段。或作为 map ,例如这样:
    object1.get('periodEnd')

    关于json - Grails:从请求中解析 JSON 的简单有效的方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22468380/

    相关文章:

    hibernate - Grails deleteAll() 因 hibernate 异常而失败

    grails - grails spring安全登录不起作用

    grails - Grails邮件传递在本地工作正常,但在具有相同配置的实时服务器(Jelastic)上失败

    javascript - AngularJS 应用程序为多个 Controller 加载和处理一次 JSON 数据

    php - 如何在json中进行int和double和url

    python - JSON序列化以元组为键的字典

    hibernate - 在 grails/hibernate 中使用 uuid 或 guid 作为 id

    arrays - 在 Play2 和 Scala 中解析没有数据类型的 JSON

    grails - Grails:对于已经存在的父记录,保存子记录失败

    grails - 在 Elasticsearch Grails 中解码域类错误