达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”

在使用达梦数据库管理工具时,我们测试过程中时常需要更新表数据,有时为了便捷,会直接使用管理工具修改表数据的值,但偶尔会遇到“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”的报错,那么这究竟是怎么回事呢。

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第1张图片

一、问题复现:

1.创建一张测试表,并插入数据

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第2张图片

2.使用SQL查询该表数据

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第3张图片

3.修改表数据

在修改表数据的过程中,出现了报错

正常情况下,点击查询结果集这里的“小锁”图标,即可修改数据

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第4张图片

但这里点击时,弹出了报错窗口,报错信息为“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第5张图片

二、问题分析

根据我们的操作可以确认,查询结果集就是出自同一张表。如果查询结果集确实不是出自同一张表(即实际并非本文中的操作方式,而是几张表关联查询),那一定是不可以用这种方式更新表数据的。

所以,根据其报错提示,该问题主要是由于该表查询的列不唯一,也就是说表中不存在主键、唯一约束、唯一索引,无法确定数据唯一性。

进一步排查,在我们操作管理工具执行更新操作前,打开数据库SQL日志,看看操作管理工具,数据库具体执行了什么操作呢?

通过抓取管理工具操作的SQL,查询SQL日志发现,日志中有这样一段SQL:

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第6张图片

格式化该SQL,简单分析下可以得知,该条SQL语句,其实就是看查询的结果集对应的表上是不是有唯一索引(达梦创建唯一键时,会自动创建一条由系统内部维护的唯一索引),且唯一索引在哪些列上。

执行一下该条SQL,该语句对应的参数分别是模式名和表名,根据SQL日志中的PARAMS参数提示,确认两个参数实际为模式名'SYSDBA'和表名'TEST'

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第7张图片

实际的查询结果为空。 

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第8张图片

那么如果在C1列上创建唯一索引,效果会如何呢?

创建唯一索引的方法有很多,可以创建主键,唯一约束,唯一索引(创建主键和唯一约束时,数据库内部都会创建一个由数据库内部自己维护的唯一索引)。

这里创建主键试试:

ALTER TABLE "SYSDBA"."TEST" ADD PRIMARY KEY("C1");

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第9张图片

主键创建完毕,再次执行SQL日志中的那条查询语句,此时已经有结果集了,查询结果显示在SYSDBA模式下的TEST表中C1列上,创建了一个升序排列的唯一索引,索引名为INDEX33649530(该索引由数据库系统自动创建,内部自己维护,用户不可主动删除,删除时会报错“试图删除系统索引”)。当然,如果创建唯一约束和唯一索引,效果是一样的,区别在于如果创建的是唯一索引,这里查询结果显示的就是我们自定义的唯一索引名字了。

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第10张图片

此时再去用管理工具执行修改数据的操作,则不会再报错,可以提交并修改成功

再次查询,数据确认已修改

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第11张图片

三、注意事项

需要注意:

1.如果在执行SQL查询时,查询结果集中的列必须全部包含创建唯一索引时对应的列,否则则会报错。

如下图中,只有SQL1,SQL4,SQL6,SQL7可以更新表数据(即查询结果集必须包含C1列):

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第12张图片

而下图中,只有SQL6,SQL7可以更新表数据(即查询结果集必须包含C1,C3列):

达梦管理工具报错“结果集不可更新,请确认查询列是否出自同一张表,并且包含值唯一的列。”_第13张图片

四、解决方法

解决该问题,有以下三种方法可供参考:

(1)添加主键约束

ALTER TABLE "SYSDBA"."TEST" ADD CONSTRAINT PK_TEST_C1 PRIMARY KEY("C1");
或
ALTER TABLE "SYSDBA"."TEST" ADD PRIMARY KEY("C1");

(2)添加唯一约束

ALTER TABLE "SYSDBA"."TEST" ADD CONSTRAINT "CONS_UNI_TEST_C1" UNIQUE("C1");

(3)创建唯一索引

CREATE UNIQUE INDEX "UIDX_TEST_C1" ON "SYSDBA"."TABLE1"("C1");

你可能感兴趣的:(达梦数据库,1024程序员节,达梦数据库,DM,数据库,运维)