我试图阻止在我的表中插入重复数据。为了做到这一点,我尝试将以下语句放入MyBatis XML文件
<insert id="insertResource" parameterType="TopologyResource">
DO
$do$
BEGIN
IF (SELECT count(*) FROM discovery_graph.topology_resources
WHERE resourceType = #{type} AND resourceSubType = '#{subType} AND storageTechnology = #{storageTechnology} ABD name = #{name} AND attributes = #{attributes} AND nativeData = #{nativeData}) = 0
THEN
INSERT into discovery_graph.topology_resources (
id,
resourceType,
resourceSubType,
storageTechnology,
name,
attributes,
nativeData
)
values ( #{resourceId,javaType=java.util.UUID,jdbcType=OTHER,typeHandler=UUIDTypeHandler}, #{type}, #{subType}, #{storageTechnology}, #{name}, #{attributes}, #{nativeData}
)
ELSE
RAISE NOTICE 'Edge already exists';
END IF;
END
$do$
同样的语句通过PSQL执行没有任何问题(使用真实数据而不是占位符),但是当我尝试通过MyBatis执行此语句时,它失败并显示错误:
### Error updating database. Cause: org.postgresql.util.PSQLException: The column index is out of range: 1, number of columns: 0.
### The error may involve TopologyResourcesMapper.insertResource-Inline
### The error occurred while setting parameters
### SQL: DO $do$ BEGIN IF (SELECT count(*) FROM discovery_graph.topology_resources WHERE resourceType = ? AND resourceSubType = ? AND storageTechnology = ? ABD name = ? AND attributes = ? AND nativeData = ?) = 0 THEN INSERT into discovery_graph.topology_resources ( id, resourceType, resourceSubType, storageTechnology, name, attributes, nativeData ) values ( ?, ?, ?, ?, ?, ?, ? ) ELSE RAISE NOTICE 'Edge already exists'; END IF; END $do$
### Cause: org.postgresql.util.PSQLException: The column index is out of range: 1, number of columns: 0.; SQL []; The column index is out of range: 1, number of columns: 0.; nested exception is org.postgresql.util.PSQLException: The column index is out of range: 1, number of columns: 0.] with root cause
MyBatis只执行INSERT语句没有问题,但是IF失败了。我想知道我做错了什么?
答案 0 :(得分:0)
这实际上是一个临时的 PL / pgSQL 语句,我怀疑 MyBatis 是否存在问题。 psql 是围绕 libpq 的更薄的包装器,并具有一些增强的脚本执行功能(以及其他特殊功能,如\copy
),这可能就是为什么它在那里工作正常。
通常我使用 PL / pgSQL 和 MyBatis 的方法是将函数定义为完整的 PL / pgSQL 函数直接在数据库中,然后通过 MyBatis 调用它。
在这种情况下,您可以使用该函数将上面 MyBatis INSERT
中当前参数作为参数。然后,您可以将其从{em> XML 中的INSERT
切换为SELECT
,然后使用SELECT foo(arg1, arg2)
形式作为标记内容调用该函数。
这将调用函数服务器端,它将执行
如果满足INSERT
条件,则使用提供的参数包含IF
。