web-dev-qa-db-ja.com

エラー時のストアドプロシージャからの戻り値

SQL Serverにspがあり、エラーが-4を返す

-4の意味?可能な戻り値が何であるかを説明する表がどこかにありますか?


いくつかの標準が必要です

例えば

declare @RetVal int  
EXEC @RetVal = stpTest  
select @RetVal

stpTestが "SELECT 1/0"の場合、-6を返します。

-6は何かを意味する必要があります!


-4を返したspには、UPDATEおよびSELECT INTOステートメントのみが含まれています。

どの時点でも「SELECT -4」を実行しないので、「特定のストアドプロシージャで-4の意味を見つける」にはどうすればよいですか?

また、標準がない場合、ゼロ除算エラーは常に-6を返すのはなぜですか?


何も返さないspがある場合、つまり、selectステートメントが含まれていない場合は、次のようにします。

declare @RetVal int  
EXEC @RetVal = yourSPName  

その場合、@ RetValの値は0になります。

エラーが発生した場合、@ RetValはゼロ以外の値になります。たとえば、spが実行するのが「SELECT 1/0」だけの場合、@ RetValは-6になります。

試して見て

私の質問は、これらの戻り値の意味を教えてください。彼らはいくつかの論理的な意味を持っている必要があります!

24
Steve

明示的な戻り値を持つRETURNステートメントがある場合、それはもちろん戻り値です。

ただし、RETURNステートメントはないが実行中にエラーが発生した場合、戻り値は10からエラーの重大度レベルを引いたものになります。ゼロによる除算はレベル16なので、戻り値は-6です。権限エラーは一般的なレベル14であるため、戻り値は-4です。

ご想像のとおり、これはそれほど有用ではありませんが、0は成功、それ以外はすべてエラーです。

28

戻りコードに標準はありません。その特定のストアドプロシージャで-4が何を意味するかを調べる必要があります。実際、すべての戻りコードがエラーであるとは限りません。


EDIT:counter-example

SET ANSI_NULLS ON
GO

SET QUOTED_IDENTIFIER ON
GO

CREATE PROCEDURE [dbo].[RetValTest] 
AS
BEGIN
    select 1/0;
END

GO

実行:

DECLARE @return_value int

EXEC    @return_value = [dbo].[RetValTest]

SELECT  'Return Value' = @return_value

GO

結果:

Msg 8134, Level 16, State 1, Procedure RetValTest, Line 9
Divide by zero error encountered.

これはSQL Server 2008での機能です。


一部の調査では、この動作はSQL Server 6.0から残っている可能性があることが示唆されています。それが事実である場合、彼らがずっと前にそれを文書化するのを止めた(そしてその正確さの保証をやめた)ことを考えると、あなたはそれがどれほど信頼できるかを自分で決めることができます。


私の "研究"は、SQL Server MVP Tibor Karaszi に感謝します。彼の出典はSQL Server 6.5のBooks Onlineです。 "" Control-Of-Flow Language "、RETURN"の下で、彼は

"SQL Serverは、正常な戻りを示すために0を予約し、失敗のさまざまな理由を示すために-1から-99までの負の値を予約します。ユーザー定義の戻り値が提供されない場合、SQL Server値が使用されます。ユーザー定義の戻りステータス値SQL Serverによって予約されている値と競合しないようにする必要があります。0〜-14の値が現在使用されています。
10
John Saunders

例えば

declare @RetVal int  
EXEC @RetVal = stpTest  
select @RetVal

ここで、stpTestSELECT 1/0は-6を返します。

-6は何かを意味する必要があります!

何も返さないspがある場合、つまり、selectステートメントが含まれていない場合は、次のようにします。

declare @RetVal int  
EXEC @RetVal = yourSPName  

次に@RetValの値は0になります。

エラーがある場合は@RetValはゼロ以外の値になります。たとえば、spが行うのがSELECT 1/0、次に@RetValは-6になります。

試して見て


まず最初に、-6を返す例を作ってくれてありがとう。

ここに ドキュメントが-6について言っていること

-6その他のユーザーエラーが発生しました。

-6は、SQL Serverが返す最もアモルファスなコードである可能性があります。
なぜ?エラーコード-6は、基本的にエラーを呼び出しスタックのより深いところに隠しているためです。

このエラーを自分でトラブルシューティングした後、このエラーのトラブルシューティングのヒントを次に示します。

  1. DALまたはアプリケーションレイヤーがこのエラーを生成する場合は、SQL Server Management StudioでSQLコードをアプリケーションユーザーとして実行し、独自のnot SQL Server ID。[理由は?あなたの許可は同じではないかもしれないからです。]
  2. 検査中のSQLコードをできるだけ読みやすくします。 [なぜ?このエラーは、コールスタックの深いところに潜んでいる可能性があるためです。]
  3. それ以外の場合は、コードの半分をコメント化します。エラーはまだ発生していますか?残りのコードの50%をコメント化します。すすぎ、繰り返します。
4
Jim G.

質問は編集して質問する必要があると思います-

ストアドプロシージャにRETURNステートメントがない場合、デフォルトの戻り値は何ですか?

私が見つけたものはこのリンクからのものでした www.redware.com/handbooks/sql_server_handbook/sql_server_stored_procedures.html

SQL Serverはデフォルトで戻り値をゼロにします。戻り値は通常、ストアドプロシージャからステータスフラグを返すために使用されます。ゼロ以外の値は通常、処理中の失敗を示します。

ODBCを使用して戻り値にアクセスすることは困難です。これらの使用は、他のストアドプロシージャと通信するときにストアドプロシージャの成功または失敗を返す場合にのみお勧めします。

このリンクから- sqlserverpedia.com/wiki/Stored_Procedures_-_Output_Parameters_&_Return_Values

戻り値-99から0は、SQL Serverの内部使用のために予約されています。呼び出し元のプログラムに戻すことができる独自のパラメーターを作成できます。

また、@ Erland Sommarskogからの別のリンク(おそらく) www.sommarskog.se/error-handling-I.html

ストアドプロシージャからの戻り値

すべてのストアドプロシージャには、RETURNステートメントによって決定される戻り値があります。 RETURNステートメントは、オプションの引数を1つ取ります。これは数値でなければなりません。値を指定せずにRETURNと言った場合、実行中にエラーが発生しなければ戻り値は0になります。プロシージャの実行中にエラーが発生した場合、戻り値は0になる場合と、負の数になる場合があります。プロシージャにRETURNステートメントがまったくない場合も同様です。戻り値が負の数の場合や0の場合があります。

これらの負の数値に意味があるかどうかは、少しわかりにくいです。以前は、戻り値-1〜-99がシステム生成の戻り値用に予約されていたため、以前のバージョンのSQL ServerのBooks Onlineでは、値-1〜-14の意味が指定されていました。ただし、SQL 2000のBooks Onlineは、このような予約については何も述べておらず、-1〜-14の意味については説明していません。

MicrosoftがSQL Serverに同梱しているシステムストアドプロシージャは、ときどき例外がありますが、成功を示すには0を返し、ゼロ以外の値はすべて失敗を示します。

エラー情報の取得

また、エラーが何であるか(-6の意味ではなく)を見つける必要がある場合は、sqlをtryキャッチに入れてみてください。

begin try

    select 1/0 as 'an error'

end try

begin catch

    select ERROR_NUMBER() as 'ERROR_NUMBER', 
           ERROR_SEVERITY() as 'ERROR_SEVERITY',
           ERROR_STATE() as 'ERROR_STATE',
           LEFT(ERROR_PROCEDURE(),50) as 'ERROR_PROCEDURE',
           ERROR_LINE() as 'ERROR_LINE' , 
           LEFT(ERROR_MESSAGE(),40) as 'ERROR_MESSAGE'    
end catch 
3
Paul Rowland