我使用的是grails-1.3.2和hbase-0.2.4。
我有以下域类:
class MyClass{
String val1
String val2
String val3
//----
}
class MyClassController{
def someAction = {
def myClass = new MyClass()
//----
String valAsJson = (myClass as JSON)
render valAsJson
}
}
我的问题是,是否只渲染部分属性(例如渲染除val3属性以外的所有属性)?
答案 0 :(得分:5)
您可以这样做:
def myClass = MyClass.get(1)
//include
render myClass.part(include:['val1', 'val2']) as JSON
//except
render job.part(except:['val2','val3']) as JSON
Bootstrap.groovy:
import org.codehaus.groovy.grails.orm.hibernate.support.ClosureEventTriggeringInterceptor as Events
class BootStrap {
def grailsApplication
def excludedProps = [Events.ONLOAD_EVENT,
Events.BEFORE_DELETE_EVENT, Events.AFTER_DELETE_EVENT,
Events.BEFORE_INSERT_EVENT, Events.AFTER_INSERT_EVENT,
Events.BEFORE_UPDATE_EVENT, Events.AFTER_UPDATE_EVENT]
def init = { servletContext ->
grailsApplication.domainClasses.each{ domainClass ->
domainClass.metaClass.part= { m ->
def map= [:]
if(m.'include'){
m.'include'.each{
map[it]= delegate."${it}"
}
}else if(m.'except'){
m.'except'.addAll excludedProps
def props= domainClass.persistentProperties.findAll {
!(it.name in m.'except')
}
props.each{
map[it.name]= delegate."${it.name}"
}
}
return map
}
}
}
def destroy = {
}
}
如果您知道如何创建我们自己的插件,那么只需为此创建一个插件,以便您可以在所有grails应用程序中使用它。
答案 1 :(得分:3)
如果您只想一直包含特定属性,那么您真的想要使用ObjectMarshaller接口。有关详细信息,请参阅this article。
答案 2 :(得分:3)
或者,您可以创建所需属性的地图,然后将其编码为JSON
Map m = [ 'val1', 'val2' ].inject( [:] ) { map, val -> map."$val" = a."$val" ; map }
render m as JSON
要排除属性,您需要执行类似的操作(UNTESTED)
def exclude = [ 'val3' ]
Map m = new DefaultGrailsDomainClass( MyClass.class ).properties.findAll {
!( it.name in exclude )
}.inject( [:] ) { map, val ->
map."$val.name" = a."$val.name" ; map
}
render m as JSON
答案 3 :(得分:2)
如果您只是想将MyClass
的实例呈现为JSON,排除某些属性,这里是一个使用Grails提供的JSONBuilder
类的解决方案
import grails.web.JSONBuilder
class MyClassController{
def someAction = {
def myClass = new MyClass()
def builder = new JSONBuilder.build {
myClass.properties.each {propName, propValue ->
// Properties excluded from the JSON
def excludes = ['class', 'metaClass', 'val3']
if (!excludes.contains(propName)) {
setProperty(propName, propValue)
}
}
render(text: builder.toString(), contentType: 'application/json')
}
}
答案 4 :(得分:1)
JSON排除Marshaller插件
我最近需要解决这个问题。我继续将解决方案打包成一个插件,允许您轻松地从JSON转换器的输出中排除类属性。它可以在Grails插件门户网站上找到。
在install the plugin之后,您将可以访问grails.converters.JSON类中名为excludeFor *()的方法。
可在此处找到更详尽的文档:How to use the JSON Exclusion Marshaller
但基本上它可以这样使用:
import grails.converters.JSON
def json, resultTeachersWillSee, resultOtherStudentsWillSee
// Given a TestStudent Domain Class
def student = new TestStudent([
firstName: "Tobias",
lastName: "Funke",
gradePointAverage: 3.6,
studentID: "FS-210-7312",
socialSecurityNumber: "555-55-5555"
])
student.save(flush: true)
// When
JSON.excludeForTeachers(TestStudent, ['socialSecurityNumber', 'id', 'class'])
JSON.use('excludeForTeachers') {
json = new JSON(student)
}
resultTeachersWillSee = json.toString()
// Then
assert resultTeachersWillSee == '{"firstName":"Tobias",
"gradePointAverage":3.6, "lastName":"Funke",
"studentID":"FS-210-7312"}'
// And When
JSON.excludeForOtherStudents(TestStudent, ['gradePointAverage', 'studentID',
'socialSecurityNumber', 'id', 'class'])
JSON.use('excludeForOtherStudents') {
json = new JSON(student)
}
resultOtherStudentsWillSee = json.toString()
// Then
assert resultOtherStudentsWillSee == '{"firstName":"Tobias",
"lastName":"Funke"}'
JSON.excludeForTeachers(...)创建一个名为“excludeForTeachers”的命名对象marshaller。 marshaller从生成的JSON输出中排除了student对象的三个属性。 'socialSecurityNumber'属性在类中明确定义,而'id'属性是由GORM在后台添加的。无论如何,教师不需要看到任何这些属性。
这个插件很适合我...我希望其他人也觉得它很有帮助。