我无法使用指定的命名配置将对象呈现为JSON。我做错了什么?
我在Bootstrap.groovy init方法中定义了一个命名配置
import com.appromocodes.Project
import com.appromocodes.Promocode
import grails.converters.JSON
class BootStrap {
def init = { servletContext ->
JSON.createNamedConfig('apiCheck', {
JSON.registerObjectMarshaller(Promocode) { Promocode promocode ->
def map= [:]
map['code'] = promocode.code
map['allowedUses'] = promocode.allowedUses
map['customInfo'] = promocode.customInfo
return map
}
})
}
def destroy = {
}
}
然后我有一个经典的控制器(不是REST,而是简单的控制器):
import grails.converters.JSON
class ApiV1Controller {
def apiV1Service
def check() {
log.info("check");
def resultMap = apiV1Service.checkPromocode(params.projectKey, params.code)
if (resultMap.statusCode != ResponseStatus.PROMOCODE_USED) {
}
def p = Promocode.get(1)
JSON.use('apiCheck', {
render p as JSON
})
}
}
我希望调用check动作只会输出apiCheck命名配置中指定的三个属性,而是获取所有bean属性以及metaClass属性“class”和“id”。
如果我没有指定命名配置,那么JSON正确呈现只显示三个属性的bean。
有什么问题?是否可以在非REST控制器中使用namedConfig?
答案 0 :(得分:7)
DefaultConverterConfiguration
因为带有默认配置的JSON作为参数传递给闭包。 That configuration has to be used to registerObjectMarshaller
。所以闭包必须如下实现(注意闭包的参数)。
JSON.createNamedConfig('apiCheck', { config ->
config.registerObjectMarshaller(Promocode) { Promocode promocode ->
def map= [:]
map['code'] = promocode.code
map['allowedUses'] = promocode.allowedUses
map['customInfo'] = promocode.customInfo
return map
}
})
更简单,更清晰,更实用的实现方式是:
JSON.createNamedConfig( 'apiCheck' ) {
it.registerObjectMarshaller( Promocode ) { Promocode promocode ->
[
code : promocode.code,
allowedUses : promocode.allowedUses,
customInfo : promocode.customInfo
]
}
}