【问题标题】:How to update a table and ignore a computed column if it is computed but update it if it is not computed如果已计算,如何更新表并忽略计算列,但如果未计算则更新它
【发布时间】:2019-06-10 12:04:47
【问题描述】:
我有不同版本的 SQL Server 数据库:
- 在
DB 1 中,“IsReadOnly”列是计算列
- 在
DB 2 中,列“IsReadOnly”是一个非计算列
我需要创建一个适用于两个版本的标准脚本:
IF EXISTS (SELECT 1 FROM sys.columns
WHERE Name = N'IsReadOnly'
AND Object_ID = OBJECT_ID(N'dbo.TableA')
AND is_computed = 0)
BEGIN
UPDATE TableA
SET IsReadOnly = @IsReadOnly
WHERE Id = @ID
END
运行上述时,它适用于 is_computed = 0 的版本。但在 is_computed = 1 的版本上运行时,我得到:
消息 271,第 16 层,状态 1,第 322 行
无法修改“IsReadOnly”列,因为它要么是计算列,要么是 UNION 运算符的结果
非常感谢任何帮助。谢谢
【问题讨论】:
标签:
sql-server
calculated-columns
【解决方案1】:
这是一个编译时与执行时的问题。该错误发生在无法更新值的数据库的编译时。
您可以使用动态 SQL 绕过它:
IF EXISTS( SELECT 1 FROM sys.columns
WHERE Name = N'IsReadOnly'
AND Object_ID = Object_ID(N'dbo.TableA')
AND is_computed = 0
)
BEGIN
EXEC sp_execute_sql N'
Update TableA
Set IsReadOnly = @IsReadOnly
Where Id = @ID',
N'@IsReadOnly int, @ID int', -- guessing at the types
@IsReadOnly=@IsReadOnly, @ID=@ID;
END
不过,更简单的方法可能是 TRY/CATCH 块:
BEGIN TRY
Update TableA
Set IsReadOnly = @IsReadOnly
Where Id = @ID ;
END TRY
BEGIN CATCH
-- Check for the particular error and do something when that occurs
END CATCH;