【问题标题】:Is there a way to write a BLOB using Spring Integration's jdbc:oubound-channel-adapter?有没有办法使用 Spring Integration 的 jdbc:oubound-channel-adapter 编写 BLOB?
【发布时间】:2017-06-06 06:44:35
【问题描述】:

我收到带有字符串有效负载的传入消息,但数据库(我无法控制)将此数据记录为 BLOB。有没有办法让 Spring Integration 将字符串按摩到 CLOB 或 BLOB 中?

我有一个出站通道适配器进行数据库插入,它(简化)看起来像:

<int-jdbc:outbound-channel-adapter channel="inboundTraffic"
                                   datasource="localDataSource"
                                   query="insert into MESSAGES (DATA, SAVE_DATE)
                                          values (:payload, :saveDate)"
                                   sql-parameter-source-factory="spelSource" />

<bean id="spelSource" class="o.s.i.j.ExpressionEvaluatingSqlParameterSourceFactory">
    <property name="parameterExpressions">
         <map>
              <entry key="payload" value="payload" />
              <entry key="saveDate" value="new java.util.Date()" />
         </map>
    </property>
</bean>

但是我在负载上得到了 SQLException:

ORA-01461 只能绑定 LONG 值,以便插入到 LONG 列中。

频道。文档的 18 有一个 blob 示例,将整个内容重写为服务激活器而不是 oubound-channel-adapter,并从文件流式传输......这似乎有点过头了,但 BLOB 和 CLOBS 应该是这样的在框架内完成?

感谢您的帮助!

【问题讨论】:

    标签: spring oracle spring-integration


    【解决方案1】:

    这个怎么样:

    <entry key="payload" value="new org.springframework.jdbc.core.support.SqlLobValue(payload)" />
    

    ?

    查看它的 JavaDoc:

     * Object to represent an SQL BLOB/CLOB value parameter. BLOBs can either be an
     * InputStream or a byte array. CLOBs can be in the form of a Reader, InputStream
     * or String. Each CLOB/BLOB value will be stored together with its length.
     * The type is based on which constructor is used. Objects of this class are
     * immutable except for the LobCreator reference. Use them and discard them.
    

    更新

    “SqlLobValue 只支持 SQL 类型 BLOB 和 CLOB”,源于 SqlLobValue.setTypeValue(...) 方法。

    看起来SqlLobValue 没有默认的sqlType,所以我们应该在SqlParameterSource 级别手动执行一些操作,因为它提供了getSqlType() 合约。

    我们可以简单地使用ExpressionEvaluatingSqlParameterSourceFactory 扩展来做到这一点:

    public class MyExpressionEvaluatingSqlParameterSourceFactory extends ExpressionEvaluatingSqlParameterSourceFactory {
        @Override
        public SqlParameterSource createParameterSource(Object input) {
            AbstractSqlParameterSource parameterSource =
                    (AbstractSqlParameterSource) super.createParameterSource(input);
            parameterSource.registerSqlType("payload", Types.BLOB);
            return parameterSource;
        }
    }
    

    随时提出JIRA 以向ExpressionEvaluatingSqlParameterSourceFactory 添加setSqlTypes() 支持。

    【讨论】:

    • 感谢您的回复!不幸的是,它似乎不起作用 - 您收到错误的 IllegalArgumentException “SqlLobValue 仅支持 SQL 类型 BLOB 和 CLOB”,它源自 SqlLobValue.setTypeValue(...) 方法。如果没有设置 sqlType,即 BLOB 或 CLOB,就会出现这种情况。向后追溯,如果没有准备好的语句,我看不到将其注入 bean 的方法......
    • 好收获!请参阅我的回答中的 UPDATE
    • 是的,解决了,谢谢 Artem,我很感激!
    猜你喜欢
    • 1970-01-01
    • 2017-04-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-07-21
    • 1970-01-01
    • 2017-07-03
    • 1970-01-01
    相关资源
    最近更新 更多