2011-11-22 15 views
7

¿Hay alguna forma de registrar un filtro de propiedad global en ObjectMapper? Global significa que se aplicará a todos los beans serializados. No puedo usar anotaciones (no puedo modificar los beans serializados) y no sé qué propiedades tienen los beans. El filtrado debe basarse en el nombre.Filtro de propiedad global en Jackson

Mi primera idea fue escribir un serializador personalizado, pero no sé qué debería pasar al constructor.

Respuesta

9

Haría uso de un FilterProvider. Es un poco complicado, pero no demasiado difícil de manejar.

import org.codehaus.jackson.annotate.JsonAutoDetect.Visibility; 
import org.codehaus.jackson.annotate.JsonMethod; 
import org.codehaus.jackson.map.ObjectMapper; 
import org.codehaus.jackson.map.ObjectWriter; 
import org.codehaus.jackson.map.annotate.JsonFilter; 
import org.codehaus.jackson.map.ser.FilterProvider; 
import org.codehaus.jackson.map.ser.impl.SimpleBeanPropertyFilter; 
import org.codehaus.jackson.map.ser.impl.SimpleFilterProvider; 

public class JacksonFoo 
{ 
    public static void main(String[] args) throws Exception 
    { 
    Bar bar = new Bar(); 
    bar.id = "42"; 
    bar.name = "James"; 
    bar.color = "blue"; 
    bar.foo = new Foo(); 
    bar.foo.id = "7"; 
    bar.foo.size = "big"; 
    bar.foo.height = "tall"; 

    ObjectMapper mapper = new ObjectMapper().setVisibility(JsonMethod.FIELD, Visibility.ANY); 
    System.out.println(mapper.writeValueAsString(bar)); 
    // output: 
    // {"id":"42","name":"James","color":"blue","foo":{"id":"7","size":"big","height":"tall"}} 

    String[] ignorableFieldNames = { "id", "color" }; 

    FilterProvider filters = new SimpleFilterProvider().addFilter("filter properties by name", SimpleBeanPropertyFilter.serializeAllExcept(ignorableFieldNames)); 

    mapper = new ObjectMapper().setVisibility(JsonMethod.FIELD, Visibility.ANY); 
    mapper.getSerializationConfig().addMixInAnnotations(Object.class, PropertyFilterMixIn.class); 
    ObjectWriter writer = mapper.writer(filters); 

    System.out.println(writer.writeValueAsString(bar)); 
    // output: 
    // {"name":"James","foo":{"size":"big","height":"tall"}} 
    } 
} 

@JsonFilter("filter properties by name") 
class PropertyFilterMixIn 
{ 

} 

class Bar 
{ 
    String id; 
    String name; 
    String color; 
    Foo foo; 
} 

class Foo 
{ 
    String id; 
    String size; 
    String height; 
} 

Para otros enfoques y más información, recomiendo los siguientes recursos.

+0

funciona como un encanto :) Hay un montón de sitio para la mejora en la documentación Jackson. – DAN

+0

Para los interesados, registré una solicitud de mejora en http://jira.codehaus.org/browse/JACKSON-724 para simplificar la configuración necesaria para filtrar las propiedades por nombre. –

+0

@DAN ¡Absolutamente! ¡Las contribuciones son ESPECIALMENTE bienvenidas para la documentación! (incluyendo enlaces a buenos artículos, actualizaciones de la wiki) – StaxMan

Cuestiones relacionadas