Jackson 動態過濾屬性
轉載:http://yxb1990.iteye.com/blog/1489712用到的類庫為:Jackson 版本1.9.5, 最近在看Google guava,所以用上了,版本是12.0-rc1
廢話不多說,定義兩個Bean 先
這兩個bean 是父子關系。
java代碼
public class User { PRivate String name; private Date createDate; private Set<Article> articles = Sets.newHashSet(); public String getName() { return name; } public void setName(String name) { this.name = name; } public Date getCreateDate() { return createDate; } public void setCreateDate(Date createDate) { this.createDate = createDate; } public Set<Article> getArticles() { return articles; } public void setArticles(Set<Article> articles) { this.articles = articles; } } Java代碼
public class Article { private String title; private User user; public String getTitle() { return title; } public void setTitle(String title) { this.title = title; } public User getUser() { return user; } public void setUser(User user) { this.user = user; } } 然后自己寫的一個Jackson實用類
Java代碼
public class Jacksons { private ObjectMapper objectMapper; public static Jacksons me() { return new Jacksons(); } private Jacksons() { objectMapper = new ObjectMapper(); // 設置輸入時忽略在JSON字符串中存在但Java對象實際沒有的屬性 objectMapper.disable(DeserializationConfig.Feature.FAIL_ON_UNKNOWN_PROPERTIES); objectMapper.configure(SerializationConfig.Feature.FAIL_ON_EMPTY_BEANS, false); objectMapper.setDateFormat(new SimpleDateFormat("yyyy-MM-dd")); } public Jacksons filter(String filterName, String... properties) { FilterProvider filterProvider = new SimpleFilterProvider().addFilter(filterName, SimpleBeanPropertyFilter.serializeAllExcept(properties)); objectMapper.setFilters(filterProvider); return this; } public Jacksons addMixInAnnotations(Class<?> target, Class<?> mixinSource) { objectMapper.getSerializationConfig().addMixInAnnotations(target, mixinSource); objectMapper.getDeserializationConfig().addMixInAnnotations(target, mixinSource); return this; } public Jacksons setDateFormate(DateFormat dateFormat) { objectMapper.setDateFormat(dateFormat); return this; } public <T> T json2Obj(String json, Class<T> clazz) { try { return objectMapper.readValue(json, clazz); } catch (Exception e) { e.printStackTrace(); throw new RuntimeException("解析json錯誤"); } } public String readAsString(Object obj) { try { return objectMapper.writeValueAsString(obj); } catch (Exception e) { e.printStackTrace(); throw new RuntimeException("解析對象錯誤"); } } @SuppressWarnings("unchecked") public List<Map<String, Object>> json2List(String json) { try { return objectMapper.readValue(json, List.class); } catch (Exception e) { e.printStackTrace(); throw new RuntimeException("解析json錯誤"); } } } 最后是測試:
Java代碼
public class Test { public static void main(String args[]) { User user = new User(); user.setName("chris"); user.setCreateDate(new Date()); Article article = new Article(); article.setTitle("title"); article.setUser(user); Set<Article> articles = Sets.newHashSet(article); user.setArticles(articles); String userJson = Jacksons.me().readAsString(user); String articleJson = Jacksons.me().readAsString(article); System.out.println(userJson); System.out.println(articleJson); } } 1.父子關系引用
直接輸出肯定是報循環錯誤,Jackson 提供了兩個注解
@JsonManagedReference
public Set<Article> getArticles() {
return articles;
}
@JsonBackReference
public User getUser() {
return user;
}
打印結果為:{"name":"chris","createDate":"2012-04-18","articles":[{"title":"title"}]}, {"title":"title"}
2.@JsonIgnore注解
只說父子引用關系的。父子兩邊都加@JsonIgnore打印字符串為:
{"name":"chris","createDate":"2012-04-18"},{"title":"title"}
單向User加該注解
@JsonIgnore
public Set<Article> getArticles() {
return articles;
}
打印結果為:
{"name":"chris","createDate":"2012-04-18"}
{"title":"title","user":{"name":"chris","createDate":"2012-04-18"}}
單向Article 加該注解
@JsonIgnore
public User getUser() {
return user;
}
打印結果:
{"name":"chris","createDate":"2012-04-18","articles":[{"title":"title"}]}
{"title":"title"}
3.@JsonIgnoreType(沒用過)
4.@JsonIgnoreProperties
這個加在類級別上, 用法很簡單@JsonIgnoreProperties({"property1", "property2"})
動態過濾屬性,這個比較麻煩。
有兩種方法。
1.使用@JsonFilter注解
使用方法為先給ObjectMapper添加一個filter,然后還要在需要過濾的類上加@JsonFilter("filterName")注解。
比如說要過濾User 上的name屬性,先
Jacksons.me().filter("myFilter", "name").readAsString(user),具體看Jacksons代碼。并在User類上加@JsonFilter("myFilter")。
有點不爽的是如果用另外一個沒有添加該filter的ObjectMapper解析的話會報錯。
如果這個User類已經添加了@JsonFilter("myFilter")注解,但在另外一個地方又要解析它并不想過濾name 屬性,那只能是
Jacksons.me().filter("myFilter", ""),然后在讀出來。
2.添加混入注解(暫時這么翻譯)
定義一個接口或類先, 在該類上添加@JsonIgnoreProperties("name"), 然后在ObjectMapper的配置項上添加混入注解
輸出為:
String mixInUser = Jacksons.me().addMixInAnnotations(User.class, MixInUser.class).readAsString(user);
System.out.println(mixInUser);