2012-02-21 25 views
11

: @JsonFilter ek açıklamasının çalışma zamanında kullanılmasını seçici olarak belirlemek mümkün mü?@JsonFilter "JsonMappingException: BeanPropertyFilter'ı çözemiyor"

Filtreyi vermediğimde JsonMappingException istisnası alıyorum (aşağıya bakın).

Geçmiş:

ben dinamik fasulye özellikleri tefrika alma filtrelemek için @JsonFilter kullanabilirsiniz recent StackOverflow post öğrendi. Bu harika çalışıyor.

// shortened for brevity 
FilterProvider filters = new SimpleFilterProvider().addFilter("apiFilter", SimpleBeanPropertyFilter.filterOutAllExcept(filterProperties)); 

return mapper.filteredWriter(filters).writeValueAsString(user); 

sorun: Alan sınıfına ve benim jax-rs hizmetinde bu kodu (CXF uygulamasını kullanarak) eklenmesiyle @JsonFilter("apiFilter") ekledikten sonra, Dinamik benim RESTful API tarafından döndürülen özelliklerini süzmek mümkün duyuyorum Filtreyi hiç uygulamak istemediğim farklı servis çağrıları var mı? Bu durumlarda, herhangi bir özelliği filtrelemeden tüm etki alanı sınıfını döndürmek istiyorum.

Caused by: org.codehaus.jackson.map.JsonMappingException: Can not resolve BeanPropertyFilter with id 'apiFilter'; no FilterProvider configured 

at org.codehaus.jackson.map.ser.BeanSerializer.findFilter(BeanSerializer.java:252) 
at org.codehaus.jackson.map.ser.BeanSerializer.serializeFieldsFiltered(BeanSerializer.java:216) 
at org.codehaus.jackson.map.ser.BeanSerializer.serialize(BeanSerializer.java:140) 

cevap

6

Hepinize özelliklerini istediğiniz yerde durumlar için boş bir serialize filtresi tanımlayan süzülmüş yazar yanıltabilirsiniz düşünüyorum: durumunda sadece şöyle bir istisna alıyorum alanı sınıfını dönmek için deneyin nerede seralized: motor @JsonFilter notunu tanımlanan "apiFilter" filtresi arar

FilterProvider filters = new SimpleFilterProvider().addFilter("apiFilter", SimpleBeanPropertyFilter.serializeAllExcept(emptySet)); 

Bu şekilde, onu bulur, ama (bütün özelliklerini serialize gibi) herhangi bir etkisi olmayacaktır.

DÜZENLEME Ayrıca, filteredWriter() yerine fabrika yöntemini writer() çağırabilirsiniz:

ObjectWriter writer=null; 
if(aplyFilter) { 
    FilterProvider filters = new SimpleFilterProvider().addFilter("apiFilter", SimpleBeanPropertyFilter.filterOutAllExcept(filterProperties)); 
    writer=mapper.filteredWriter(filters); 
} else { 
    writer=mapper.writer(); 
} 

return writer.writeValueAsString(user); 

Ben gerçekten iyi bu son çözüm yolu daha temiz olduğunu düşünüyorum ve.

+0

, her jax-rs servis çağrısında hangi yazar yönteminin çağrılacağını kontrol etmek için kodu eklemem gerekir mi? Bazı servis yöntemlerinde bir String yerine gerçek bir Kullanıcı nesnesi döndürürüm. Girişiniz için çok teşekkürler! – Justin

+1

Tamam, bir şans verdim. önerdiğin "hile" işe yarıyor ama ikinci "temiz" önerinizi işe alamadım. Bu durumda hala "FilterProvider yapılandırılmış" hatası alıyorum. Tekrar teşekkürler. – Justin

+0

@Justin: iyi, IMO, bir sorunu çözen bir "temiz" olmayan bir "temiz" olmayan bir çözüm daha "temiz" bir çözümdür :). Umarım sorununun çözülmesine yardımcı olur. –

18

Ben zaten cevaplanmış biliyorum ancak herhangi newcommers için Jackson aslında eksik filtreleri (JACKSON-650) kazanırsak yeteneği ekledi: Sadece SimpleFilterProvider.setFailOnUnknownId(false) aramak gerekir ve bu durum almazsınız
.

+0

Cevabınız için teşekkürler. Bu yararlı – Justin

+4

Elbette kullandığınız mapper ile hiç filtreleme kullanmayacaksanız bile bir SimpleFilterProvider yapılandırmanız gerekiyor. Oh iyi. – Jules

0

Aynı Özel Durumu alıp benzer bir sorunla karşılaştım, ancak kabul edilen yanıt benim durumumda gerçekten yardımcı olmadı.

benim kurulumda

Böyle özel bir JacksonSerializer kullanıyordu: İşte benim için çalıştı çözüm

@JsonSerialize(using = MyCustomSerializer.class) 
private Object someAttribute; 

Ve bu serileştirici böyle uygulandı:

public class MyCustomSerializer extends JsonSerializer<Object> { 
    @Override 
    public void serialize(Object o, JsonGenerator jgen, SerializerProvider provider) throws IOException, JsonProcessingException { 
    if (o != null) { 
     jgen.writeObject(o); 
    } 
    } 
} 

bu sorun Bu, herhangi bir filtre kullanmadığınız sürece çalışır. Ayrıca, ilkelleri seri hale getirirseniz, örneğin jgen.writeString(..)'u kullanırsanız çalışır. Filtreler kullanırsanız, bu kod yanlıştır, çünkü filtreler JsonGenerator'da değil SerializerProvider'un içinde bir yerde saklanır. Bu durumda json jeneratörünü doğrudan kullanırsanız, filtreler hakkında bilmeyen yeni bir SerializerProvider dahili olarak yaratılır. Yani daha kısa olan jgen.writeObject(o) yerine provider.defaultSerializeValue(o, jgen)'u aramanız gerekir.Bu, filtrelerin kaybolmamasını ve uygulanabilmesini sağlayacaktır. Düzenlenmiş örneğinizde

İlgili konular