2017-08-05 26 views
0

我正在嘗試今年春天的JMS示例,並且它給出了錯誤。 https://spring.io/guides/gs/messaging-jms/ 引起:org.springframework.jms.support.converter.MessageConversionException: Could not find type id property [_type] on message from destination [queue://mailbox] 有趣的是,如果我克隆它並運行一切運行良好。如果我複製並粘貼,它會給出錯誤。引起:org.springframework.jms.support.converter.MessageConversionException:無法找到消息上的類型id屬性[_type]

@Bean // Serialize message content to json using TextMessage 
public MessageConverter jacksonJmsMessageConverter() { 
    MappingJackson2MessageConverter converter = new MappingJackson2MessageConverter(); 
    converter.setTargetType(MessageType.TEXT); 
    converter.setTypeIdPropertyName("_type"); 
    return converter; 
} 

這段代碼實際上導致了錯誤。搜索網頁和文檔,我仍然不知道如何以及如何設置setTypeIdPropertyName值和「_type」在此項目中引用的內容?由於該信息沒有這樣的屬性,那麼它來自哪裏?

回答

3

TypeIdPropertyName是標識實體的屬性的名稱。傑克遜映射器在反序列化傳入的JSON時應該知道使用哪個實體。

請求看起來應該像下面這樣:

{ 
    "_type" : "hello.Email", 
    "to" : "Imran", 
    "from" : "dzatorsky" 
} 

順便說一句,我認爲這不是因爲JMS已經知道使用哪種類型的(你在方法聲明它)的最佳解決方案。另一個缺點是,你要在難以維護的消息中指定實體和包的名稱(每次更改包或實體名稱都會很痛苦)。

這是更強大的配置:

@EnableJms 
@Configuration 
public class JmsListenerConfig implements JmsListenerConfigurer { 

    @Bean 
    public DefaultMessageHandlerMethodFactory handlerMethodFactory() { 
     DefaultMessageHandlerMethodFactory factory = new DefaultMessageHandlerMethodFactory(); 
     factory.setMessageConverter(messageConverter()); 
     return factory; 
    } 

    @Bean 
    public MessageConverter messageConverter() { 
     return new MappingJackson2MessageConverter(); 
    } 

    @Override 
    public void configureJmsListeners(JmsListenerEndpointRegistrar registrar) { 
     registrar.setMessageHandlerMethodFactory(handlerMethodFactory()); 
    } 
} 

此外,如果你使用Spring JmsTemplate的發送郵件,可以將這個組件添加到您的配置:

/** 
* Used to convert JMS messages from/to JSON. Registered in Spring-JMS automatically via auto configuration 
*/ 
@Component 
public class JsonMessageConverter implements MessageConverter { 

    @Autowired 
    private ObjectMapper mapper; 

    /** 
    * Converts message to JSON. Used mostly by {@link org.springframework.jms.core.JmsTemplate} 
    */ 
    @Override 
    public javax.jms.Message toMessage(Object object, Session session) throws JMSException, MessageConversionException { 
     String json; 

     try { 
      json = mapper.writeValueAsString(object); 
     } catch (Exception e) { 
      throw new MessageConversionException("Message cannot be parsed. ", e); 
     } 

     TextMessage message = session.createTextMessage(); 
     message.setText(json); 

     return message; 
    } 

    /** 
    * Extracts JSON payload for further processing by JacksonMapper. 
    */ 
    @Override 
    public Object fromMessage(javax.jms.Message message) throws JMSException, MessageConversionException { 
     return ((TextMessage) message).getText(); 
    } 
} 

有了這個配置,你可以跳過煩人「 _type「字段在您的消息。

+0

似乎就是這樣解決了這個問題。謝謝。不知道爲什麼文檔和樣本沒有任何正確的解釋就有這樣一個有問題的方法。設置typeIdPropertyName的java文檔只是說消息的類型id屬性。它必須設置。但沒有說明應該如何設置。 – Imran

0

自定義(即應用程序級別)「_type」屬性必須是消息(由其生產者)設置的JMS屬性。消息有效載荷不會與類型元數據混雜在一起。要了解JMS消息屬性,一個應該訪問https://docs.oracle.com/javaee/7/api/javax/jms/Message.html

這是不與可以替代地使用,並且必須與基於傑克遜的註解來配置的JSON屬性混淆(例如爲多晶型反序列化)。在這種情況下,實際的消息負載(JSON字符串)會發生更改,並在頂級對象中包含「_type」屬性。

相關問題