0

SQL Server 2005/2008 R2 を使用しています

私のSQLスクリプトは次のとおりです。

UPDATE MyView 
SET MyColumn = 'My new value' 
WHERE ID = 7

エラーメッセージ:

メッセージ 271、レベル 16、状態 1、行 1
列 "MyColumn" は、計算列であるか、UNION 演算子の結果であるため、変更できません。

私はそれMyColumnがベーステーブルから計算された列であることを知っています(FullNameから計算されたときのようにLastName + ', ' + FirstName

私の目的は、スクリプトが実行され続けるようにエラーをキャッチすることです。

次のスクリプトを試してみましたが、うまくいきませんでした。エラーはキャッチされません:

BEGIN TRY
    UPDATE MyView 
    SET MyColumn = 'My new value' 
    WHERE ID = 7
END TRY 
BEGIN CATCH
    -- Error occurred while updating view. The script will keep running
END CATCH

問題を解決しようとして、次のスクリプトを確認しましたが、うまくいきませんでした。

スクリプト 1

SELECT is_computed 
FROM sys.columns c, sys.views v
WHERE c.object_id = v.object_id
AND v.name = 'MyView'

前のスクリプトは、すべての結果に対して 0 を返します (これは正しくありません。列の 1 つが計算列です)。

スクリプト 2:

SELECT * 
FROM INFORMATION_SCHEMA.COLUMNS 
WHERE table_name = 'MyView'`

また、返されたスクリプトから、「計算された列」または「ユニオンの結果」操作に関係するフィールドを見つけることができませんでした。

4

2 に答える 2

1

まず第一に、システム ビューやテーブルでは、ビューのどの列が派生列であるか計算列であるかを実際に知ることはできません。ほとんどの場合、実行時にのみ検出できます。また、powershell スクリプトなどを使用して SQL の外部で検出することもできます。

例外が発生した後もスクリプトを続行したい場合は、goto を使用できますが、これはお勧めできません。


begin try
   select 1/0
end try
begin catch
   Print 'error occurred'
   goto MarkPoint
end catch
select * from sys.columns
MarkPoint: 
  select top 1 * from sys.tables
于 2013-03-22T20:40:07.593 に答える
0

役に立つというわけではありませんが、SQL Server 2012 を実行している場合は、

sp_describe_first_result_set N'select * from View'

そして、正しい情報が提供されます (つまり、is_updateable が 0 に設定され、is_computed_column が 1 に設定されます)。

以下は、実際にはベース テーブルの計算列であるビュー内のすべての列を返す、100% 信頼できるわけではないクエリです。

    SELECT c.name FROM sys.objects AS O
   INNER JOIN sys.sql_expression_dependencies SED ON SED.referenced_id=O.object_id
    INNER JOIN sys.objects O2 ON O2.object_id=SED.referencing_id
    INNER JOIN sys.columns c on c.object_id = o.object_id
    where
     QUOTENAME(O2.name) = 'MyView'
     and c.is_computed = 1

その sql_expression_dependencies テーブルは完全に最新の状態に保たれておらず、クエリを完全に「読み取る」ことができないため、100% 信頼できるわけではありません (関数呼び出し内の関数呼び出しなどを見逃すなど)。しかし、標準の「ビュー =テーブルからの列」オブジェクト、正常に動作します。

于 2013-03-22T20:44:56.753 に答える