Java 如何序列化JMS消息?
我正在尝试序列化JMS消息,以便将其转换为BLOB并将其保存到SQL数据库中 我的第一次天真尝试使用了一个可序列化类,将其作为字段,如下所示:Java 如何序列化JMS消息?,java,serialization,jms,Java,Serialization,Jms,我正在尝试序列化JMS消息,以便将其转换为BLOB并将其保存到SQL数据库中 我的第一次天真尝试使用了一个可序列化类,将其作为字段,如下所示: private static class SerializableWrapper implements Serializable{ Message message; private SerializableWrapper(Message message){ this.message = message; }
private static class SerializableWrapper implements Serializable{
Message message;
private SerializableWrapper(Message message){
this.message = message;
}
private Message getMessage() {
return message;
}
private void setMessage(Message message) {
this.message = message;
}
private void writeObject(java.io.ObjectOutputStream out)
throws IOException{
out.writeObject(getMessage());
}
private void readObject(java.io.ObjectInputStream in)
throws IOException, ClassNotFoundException {
setMessage((Message) in.readObject());
}
}
这不起作用,并继续为JMSTextMessage
抛出NotSerializableException
。我不确定是否有其他第三方库可能有助于将其序列化,但我的任务要求完全没有第三方依赖关系
有没有什么好的/合理的方法可以做到这一点而不需要其他依赖项
编辑:我目前正在通过解压每个属性,然后在反序列化时将消息作为一个整体重新构建来实现这一点。在我看来,这种方法还不够理想——有些字段是不可序列化的,我还必须分别处理Message
的不同子类,例如TextMessage
,ByteMessage
等
private void writeObject(java.io.ObjectOutputStream out)
throws IOException{
HashMap<String, Object> properties = new HashMap <String, Object> ();
HashMap<Integer, Object> metaData = new HashMap<Integer, Object>();
try {
Enumeration srcProperties = message.getPropertyNames();
while (srcProperties.hasMoreElements()) {
String propertyName = (String) srcProperties.nextElement ();
properties.put(propertyName, message.getObjectProperty (propertyName));
}
//FIXME text/other body not preserved yet, have to preserve the message type eg Text/Byte etc continue after confirming with aditya
metaData.put(KEY_JMS_CORRELATION_ID, message.getJMSCorrelationID());
metaData.put(KEY_JMS_DELIVERY_MODE, message.getJMSDeliveryMode());
metaData.put(KEY_JMS_EXPIRATION, message.getJMSExpiration());
metaData.put(KEY_JMS_TIMESTAMP, message.getJMSTimestamp());
metaData.put(KEY_JMS_MESSAGE_ID, message.getJMSMessageID());
metaData.put(KEY_JMS_PRIORITY, message.getJMSPriority());
metaData.put(KEY_JMS_REPLY_TO, message.getJMSReplyTo());
metaData.put(KEY_JMS_TYPE, message.getJMSType());
} catch (JMSException e) {
e.printStackTrace();
}
out.writeObject(properties);
out.writeObject(metaData);
}
private void readObject(java.io.ObjectInputStream in)
throws IOException, ClassNotFoundException {
HashMap<String, Object> properties = (HashMap<String, Object>) in.readObject();
HashMap<Integer, Object> metaData= (HashMap<Integer, Object>) in.readObject();
System.out.println("JMSMessageUtility - Retrieving Properties: "+properties);
System.out.println("JMSMessageUtility - Retrieving Metadata: "+metaData);
Message message = null;
try {
ConnectionFactory connectionFactory = new AMQConnectionFactory(CONNECTION_BROKER);
Destination destination = new AMQAnyDestination(QUEUE_ADDRESS);
Connection connection = connectionFactory.createConnection();
Session session = connection.createSession(true, Session.AUTO_ACKNOWLEDGE);
message = session.createMessage();
for(Map.Entry<String, Object> property: properties.entrySet()){
message.setObjectProperty(property.getKey(), property.getValue());
}
message.setJMSCorrelationID(metaData.get(KEY_JMS_CORRELATION_ID) == null? null:(String) metaData.get(KEY_JMS_CORRELATION_ID));
message.setJMSDeliveryMode((Integer) metaData.get(KEY_JMS_DELIVERY_MODE));
message.setJMSDestination(destination);
message.setJMSExpiration((Long) metaData.get(KEY_JMS_EXPIRATION));
message.setJMSTimestamp((Long) metaData.get(KEY_JMS_TIMESTAMP));
message.setJMSMessageID((String) metaData.get(KEY_JMS_MESSAGE_ID));
message.setJMSPriority((Integer) metaData.get(KEY_JMS_PRIORITY));
message.setJMSReplyTo(null); // no idea what to do with this
message.setJMSType(metaData.get(KEY_JMS_TYPE) == null? null:(String) metaData.get(KEY_JMS_TYPE));
} catch (URLSyntaxException e) {
e.printStackTrace();
} catch (JMSException e) {
e.printStackTrace();
} catch (URISyntaxException e) {
e.printStackTrace();
}
setMessage(message);
}
private void writeObject(java.io.ObjectOutputStream out)
抛出IOException{
HashMap属性=新的HashMap();
HashMap元数据=新建HashMap();
试一试{
枚举srcProperties=message.getPropertyNames();
while(srcProperties.hasMoreElements()){
String propertyName=(String)srcProperties.nextElement();
put(propertyName,message.getObjectProperty(propertyName));
}
//FIXME文本/其他正文尚未保留,必须保留消息类型,如文本/字节等,在与aditya确认后继续
put(KEY_JMS_CORRELATION_ID,message.getJMSCorrelationID());
put(KEY_JMS_DELIVERY_模式,message.getJMSDeliveryMode());
put(KEY_JMS_EXPIRATION,message.getJMSExpiration());
put(KEY_JMS_TIMESTAMP,message.getjmstistestamp());
put(KEY_JMS_MESSAGE_ID,MESSAGE.getJMSMessageID());
put(KEY_JMS_PRIORITY,message.getJMSPriority());
put(KEY_JMS_REPLY_TO,message.getJMSReplyTo());
put(KEY_JMS_TYPE,message.getJMSType());
}捕获(JME){
e、 printStackTrace();
}
out.writeObject(属性);
out.writeObject(元数据);
}
私有void readObject(java.io.ObjectInputStream-in)
抛出IOException,ClassNotFoundException{
.readObject()中的HashMap属性=(HashMap);
HashMap元数据=(HashMap)位于.readObject()中;
System.out.println(“JMSMessageUtility-检索属性:“+Properties”);
System.out.println(“JMSMessageUtility-检索元数据:“+元数据”);
Message=null;
试一试{
ConnectionFactory ConnectionFactory=新的AMQConnectionFactory(连接代理);
目的地=新的AMQAnyDestination(队列地址);
Connection=connectionFactory.createConnection();
Session Session=connection.createSession(true,Session.AUTO_-ACKNOWLEDGE);
message=session.createMessage();
对于(Map.Entry属性:properties.entrySet()){
message.setObjectProperty(property.getKey(),property.getValue());
}
message.setJMSCorrelationID(metaData.get(KEY_JMS_CORRELATION_ID)==null?null:(String)metaData.get(KEY_JMS_CORRELATION_ID));
message.setJMSDeliveryMode((整数)metaData.get(KEY_JMS_DELIVERY_MODE));
message.setJMSDestination(目的地);
message.setJMSExpiration((长)metaData.get(KEY_JMS_EXPIRATION));
message.setjmstiestamp((长)metaData.get(KEY_JMS_TIMESTAMP));
message.setJMSMessageID((字符串)metaData.get(KEY_JMS_message_ID));
message.setJMSPriority((整数)metaData.get(KEY_JMS_PRIORITY));
message.setJMSReplyTo(null);//不知道该怎么办
message.setJMSType(metaData.get(KEY_JMS_TYPE)==null?null:(String)metaData.get(KEY_JMS_TYPE));
}捕获(URLSyntaxException e){
e、 printStackTrace();
}捕获(JME){
e、 printStackTrace();
}捕获(URISyntaxException e){
e、 printStackTrace();
}
设置消息(消息);
}
您真的希望所有方法都是私有的吗?--编辑:啊,我在看javadoc。好的,明白了。是的,我正在实现可序列化的接口,但是不知道不可序列化的字段(JMS消息)是如何实现的如果您不序列化消息的有效负载而不是消息本身,也可以进行转换?在Serializable
类中包装一个非Serializable
类并不能神奇地使其可序列化。
您需要序列化它的属性。我的也是,但它是您的代码。一开始就很奇怪。如果您还没有完成消息,
为什么要将其从队列中删除?那么为什么要在其他地方坚持呢?您是否考虑过以某种方式将其放回JMS以供以后使用?