MuleSoft向Oracle队列发消息时无法设置JMS类型报错求助
问题:Oracle AQ发布消息触发JMS-108错误
错误详情
JMS-108: Messages of type TextMessage not allowed with Destinations containing payload of type SYS.XMLTYPE
尝试向Oracle队列发布XML消息时出现上述错误,已尝试在JMS发布组件中设置jmsType为BytesMessage,但错误未消除。
相关变量说明
payload.queue:目标Oracle队列名称payload.request_id:整数类型,用作消息关联IDvars.xml:application/xml类型的XML内容变量
当前配置代码
JMS发布组件
<jms:publish doc:name="Publish" doc:id="an id" config-ref="jms_oracle_aq" destination="#[payload.queue]]" sendCorrelationId="ALWAYS"> <jms:message outboundContentType="application/xml" correlationId="#[payload.request_id]" jmsType="BytesMessage"> <jms:body><![CDATA[#[vars.xml]]]></jms:body> </jms:message> </jms:publish>
JMS连接配置
<jms:config name="jms_oracle_aq" doc:name="JMS config" doc:id="an id"> <jms:generic-connection connectionFactory="oraAQConnectionFactory" /> </jms:config>
Spring数据源与连接工厂
<bean id="oraAQDataSource" class="oracle.ucp.jdbc.PoolDataSourceImpl"> <property name="URL" value="jdbc:oracle:thin:@//${oracle.aq.host}:${oracle.aq.port}/${oracle.aq.sid}" /> <property name="user" value="${oracle.aq.username}" /> <property name="password" value="${oracle.aq.password}" /> <property name="connectionFactoryClassName" value="oracle.jdbc.pool.OracleDataSource" /> <property name="minPoolSize" value="1" /> <property name="maxPoolSize" value="20" /> <property name="connectionWaitTimeout" value="5" /> <property name="validateConnectionOnBorrow" value="true" /> </bean> <bean id="oraAQConnectionFactory" class="oracle.jms.AQjmsConnectionFactory"> <property name="datasource" ref="oraAQDataSource" /> </bean>
依赖版本
mule4 com.oracle.javavm.jrf aqapi 19.3 com.oracle.javavm.jrf ojdbc8 19.3 com.oracle.javavm.jrf oracle.ucp 19.3 org.mule.connectors mule-jms-connector 1.9 mule-plugin
解决方案
1. 适配Oracle XMLType队列要求
Oracle AQ的SYS.XMLTYPE队列不接受普通的TextMessage或BytesMessage,必须传递Oracle原生的XMLType对象。Mule默认的消息序列化无法自动适配,需要显式转换XML内容为XMLType实例。
2. 添加XML类型转换逻辑
使用Groovy脚本将XML字符串转换为Oracle XMLType:
import oracle.xdb.XMLType import java.sql.Connection // 获取XML内容并转换为Oracle XMLType def xmlStr = vars.xml as String def dataSource = ctx.getBean("oraAQDataSource") Connection conn = dataSource.getConnection() def oracleXml = XMLType.createXML(conn, xmlStr) vars.oracleXmlPayload = oracleXml conn.close()
3. 修改JMS发布配置
移除无效的jmsType属性,直接传递XMLType对象作为消息体:
<jms:publish doc:name="Publish" doc:id="an id" config-ref="jms_oracle_aq" destination="#[payload.queue]" sendCorrelationId="ALWAYS"> <jms:message correlationId="#[payload.request_id]"> <jms:body>#[vars.oracleXmlPayload]</jms:body> </jms:message> </jms:publish>
4. 注意事项
- 确保
aqapi、ojdbc8版本与Oracle数据库版本完全匹配,避免类型兼容性问题 - 不要设置
outboundContentType,因为Oracle XMLType队列会自行处理内容类型 - 转换时获取的数据库连接需及时关闭,避免连接池耗尽
内容的提问来源于stack exchange,提问作者Mishael Harrison
相关产品推荐
相关产品推荐

