2017-04-26 215 views
1

映射器實例完全是線程安全的,不需要爲單次使用創建映射器,但可以更改映射器的配置。對於傑克遜,如何安全地共享一個ObjectMapper?有沒有不可變的ObjectMapper?

儘管ObjectMapper具有copy函數來複制基於存在映射器的自定義配置,但如果我共享映射器,並不能保證當有人想要自定義映射器時,它們將複製共享映射器。所以我想要一個不可變的映射器來共享,如果有人不小心改變了共享映射器,應該拋出一些異常。

有沒有這樣的事情?

+0

我將創建ObjectMapper公正公開一些必要的功能 – Jerry06

+0

的包裝,相反,我只是想隱藏一些功能爲了防止配置發生變化,這似乎是非常常見的用例,是否存在這種包裝?如果不是,我會爲自己創建一個。 – wener

+0

一個選項可能是共享一個ObjectWriter實例,而不是ObjectMapper。儘管我相信這不是它的預期目的,但這個類似乍一看是不變的。 – Henrik

回答

-1

寫不可變的包裝比我想象的有CGLIB

/** 
* Create a immutable mapper, will hide some config change operation 
*/ 
@SuppressWarnings("unchecked") 
static <T extends ObjectMapper> T immutable(T mapper) { 
    Enhancer enhancer = new Enhancer(); 
    enhancer.setSuperclass(ObjectMapper.class); 
    enhancer.setCallback((InvocationHandler) (proxy, method, args) -> { 
     if (Modifier.isPublic(method.getModifiers())) { 
      // banned operation 
      String name = method.getName(); 
      boolean match = name.startsWith("set") || 
       name.startsWith("add") || 
       name.startsWith("clear") || 
       name.startsWith("disable") || 
       name.startsWith("enable") || 
       name.startsWith("register") || 
       name.startsWith("config"); 

      if (match) { 
       throw new UnsupportedOperationException(
        "Can not modify the immutable mapper, copy the mapper first"); 
      } 
     } 
     if (!method.isAccessible()) { 
      method.setAccessible(true); 
     } 
     return method.invoke(mapper, args); 
    }); 
    return (T) enhancer.create(); 
} 

由於配置得到映射是不可改變的容易,所以我不需要隱藏吸氣。

0

一種方法是不共享ObjectMapper實例,而是正確地配置它,然後共享由ObjectMapper創建的ObjectWriterObjectReader實例。

ObjectMapper om = new ObjectMapper(); 
// Configure to your needs 
om.enable(...); 
om.disable(...); 

// Distribute these to the parts of the program where you fear configuration changes. 
ObjectWriter writer = om.writer(); 
ObjectReader reader = om.reader(); 

這也似乎是由傑克遜的開發商青睞的辦法:https://stackoverflow.com/a/3909846/13075

相關問題