• 締切済み

ストアドから得られるレコードセットを、別のストアドで利用したい

現在、実行するとあるレコードセット(1行1列のみ)を返すストアドプロシージャProc_Aがありますが、このプロシージャを実行して得られる結果を、 別のプロシージャProc_Bで、以下のような形で使用したいと考えています。 ただし、Case文内部でのストアドの実行や、変数へのストアドの実行結果の代入を試しましたが、どちらもうまくいっていません。 なにか、よい解決策があれば、教えていただければ、と思います。 パターンA) Case内部で直接実行 select case Table_A.param_1 when 0 then Exec Proc_A '***','**' else '' end パターンB)いったんパラメータとして取得 declare @values as char(10) execute sp_executesql N'@values = Proc_A ''***'',''**''', N'@values char(10) OUTPUT', @values OUTPUT

みんなの回答

  • xcrOSgS2wY
  • ベストアンサー率50% (1006/1985)
回答No.1

あまり自信はないのですが、なかなか回答が付かないようですので・・・ 私もちょっと試してみたのですが、ストアドプロシージャが返すレコードセットを別のSQL分のパラメータとして使用するのは、普通の方法では無理そうでした。 そこで、「普通の方法では無理」ということを前提にした上で、次の方法はいかがでしょうか。 (1) ストアドプロシージャの構造を変える Proc_Aがレコードセットを返すのではなく変数に値を返す構造になっていれば、問題はないわけです。 ですので、Proc_Aと同じレコードセット(1行1列)をパラメータとして返す新しいストアドプロシージャProc_A'を作成し、それを使用するのはいかがでしょうか。 なお、現状でProc_Aも必要としているのであれば、Proc_AとProc_A'でほぼ同じクエリが重複してしまうので、Proc_AはProc_A'を使用する形に書き直すほうがより好ましいかと思います。 (2) 超が付くほど強引な方法です ストアドプロシージャProc_Aの内容(SQL文)を取得することは可能なので、それをそっくり取得して、その中にあるSELECT ...をSELECT @var=...に変更してダイナミック実行し、取得した値をパラメータとして返すのはいかがでしょうか。 Proc_Aが自前のストアドプロシージャであれば(1)のように書き換えてしまえばいいわけですが、ヨソのストアドプロシージャであって内容がいつどのように変わるか定かではないという場合には、こんな方法を取るのもやむを得ないのかなと思います。

eitetsu
質問者

お礼

ありがとうございます。 結局この件については、(1)の方法で対応を取ることにしました。 もともとのプロシージャに手を加え、オプションの値によって、レコードセットと変数と、値の返し先を変更できるようにしました。 このような感じです。 こうすることで、もともとのプロシージャを利用している部分でも書き換えが不要になりました。 --------------------------------- create proceadure Proc_A @value ..., @opt as int = 0, @out as varchar(100) OUTPUT as ...処理... set @value = 結果 if @opt = 1 set @out = @value else select @value GO ---------------------------------

関連するQ&A

  • MySQLのストアドプロシージャについて

    MySQL5.6のストアドプロシージャが返すSELECT結果のフェッチ方法について教えてください。 delimiter $ create procedure sample_proc() begin select * from TEST_TBL; end$ の様なストアドプロシージャがあり、これを他のストアドプロシージャから呼び出して、 ループしながらフェッチしたいのですが、どうすればよいでしょうか。

  • ストアドプロシージャからストアドプロシージャを呼ぶことはできるか?

    ストアドプロシージャからストアドプロシージャを呼ぶことはできるか? Oracle10g WindowsServer2008 Aというプロシージャ内でEXECコマンドを使ってBというプロシージャを呼ぶようにしたところコンパイルエラーになりました。ストアドプロシージャからストアドプロシージャを呼ぶことはできないのでしょうか?

  • VBでストアドの戻りパラメータを受け取る方法

    VB6.0からADOを利用してSQLServerのストアドプロシージャを呼出し、戻りパラメータを受け取る方法がありましたら教えてください。よろしくお願いします! CREATE PROC TEST ( I_VAL AS INT, O_VAL AS INT OUTPUT ) ~省略~

  • ストアドプロシージャの実行について

    asp.net から sqlserver のストアドプロシージャを実行させる勉強をしています。 作成されているはずのストアドプロシージャを実行できずに困っています。 webformにテキストボックス、ボタン、データグリッドを貼り付け、ストアドプロシージャを作成し下記のプログラムを実行させるのですが上手くいきません。 (テキストボックスに任意で入力された数値のデータをボタンを押すと表示するものです) <エラー内容>→ ストアド プロシージャ 'proc1' が見つかりませんでした Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click Dim cn As New SqlConnection Dim cmd As New SqlCommand cn.ConnectionString = "接続文字列" cmd.Connection = cn cmd.CommandText = "proc1" cmd.CommandType = System.Data.CommandType.StoredProcedure Dim p1 As SqlParameter = cmd.Parameters.Add("@param1", System.Data.SqlDbType.Int) p1.Value = TextBox1.Text cn.Open() Dim dr As SqlDataReader = cmd.ExecuteReader DataGrid2.DataSource = dr DataGrid2.DataBind() dr.Close() cn.Close() end sub ストアドproc1(場所:Northwind)の内容↓ CREATE procedure proc1 @param1 int as select * from products where categoryID=@param1 どなたか原因のわかる方がいれば、宜しくお願いします。

  • ストアドプロシージャの実行

    こんばんは。 C#のアプリケーションからストアドプロシージャの実行を検討 しています。ストアドプロシージャでは複数テーブルを更新する バッチシステムです。 このケースでは、C#側ではエラーをどこまでハンドリングするのが 良いでしょうか?。 「成功と失敗の戻り値だけ」か、それとも「ORA-」のようなエラーまで全てハンドリングすべきか迷っていまして・・。 ご意見お願いします。

  • CSVを取込むストアドプロシージャで、1件目が登録されない現象が起きています

    いつもお世話になっております 古い環境なので大変恐縮ですが、行き詰ってしまったので、 ご教示いただきたいと思います。 環境: WinXP sp2 SQLServer8.0 VB6.0 sp4 VBでCSVのデータ1行について、ストアドプロシージャにて3つのテーブルに格納しようとしています。 トランザクションの管理はVB側で行っています。 1行ごとにCommitを行えば、全行格納されるのですが、 2行以上ごとにCommitを行うと、最初の1行のみが格納されないという現象がおきています。 6800行存在する同じCSVファイルについて、1行ごとにCommitを行った場合は、6800件登録されるのに 処理の最後でCommitをきった場合、6799行しか登録されません。 1行ごとにCommitをきった場合に6800行登録されるので、キー重複は考えられません。 いろいろ試してみたことを下記に書きます 結果はこのような感じです。 CASE1・・・全件登録できます CASE2・・・2件目で重複エラーが発生します CASE3・・・全件 - 1件が登録できます CASE4・・・全件登録できます CASE5・・・全件登録できます CASE2, CASE3 で全件登録できない理由をご教示いただきたく思います。 よろしくお願いいたします。 CASE1(VBでINSERT文を記述)  localConnection.beginTrans localConnection.execute "DELETE FROM TABLE_A" localConnection.execute "DELETE FROM TABLE_B" localConnection.execute "DELETE FROM TABLE_C" FOR i = 1 to 6800 localConnection.execute "INSERT INTO TABLE_A (COL_A1, COL_A2) VALUES ('" & VAL_A1(i) & "','" & VAL_A2(i) & "')" localConnection.execute "INSERT INTO TABLE_B (COL_B1, COL_B2) VALUES ('" & VAL_A1(i) & "','" & VAL_B2(i) & "')" localConnection.execute "INSERT INTO TABLE_C (COL_C1, COL_C2) VALUES ('" & VAL_A1(i) & "','" & VAL_C2(i) & "')" NEXT  localConnection.commitTrans CASE2(ストアドプロシージャ) localConnection.beginTrans localConnection.execute "DELETE FROM TABLE_A" localConnection.execute "DELETE FROM TABLE_B" localConnection.execute "DELETE FROM TABLE_C" ' -- ストアドプロシージャのパラメータ作成 FOR i = 1 to 6800 localConnection.execute NEXT  localConnection.commitTrans CASE3(ストアドプロシージャ) localConnection.beginTrans localConnection.execute "DELETE FROM TABLE_A" localConnection.execute "DELETE FROM TABLE_B" localConnection.execute "DELETE FROM TABLE_C"  localConnection.commitTrans ' -- ストアドプロシージャのパラメータ作成 localConnection.beginTrans FOR i = 1 to 6800 localConnection.execute NEXT  localConnection.commitTrans CASE4(ストアドプロシージャ) localConnection.beginTrans localConnection.execute "DELETE FROM TABLE_A" localConnection.execute "DELETE FROM TABLE_B" localConnection.execute "DELETE FROM TABLE_C"  localConnection.commitTrans ' -- ストアドプロシージャのパラメータ作成 localConnection.beginTrans FOR i = 1 to 6800 localConnection.execute   localConnection.commitTrans   localConnection.beginTrans NEXT  localConnection.commitTrans CASE5(ストアドプロシージャ) localConnection.beginTrans localConnection.execute "DELETE FROM TABLE_A" localConnection.execute "DELETE FROM TABLE_B" localConnection.execute "DELETE FROM TABLE_C"  localConnection.commitTrans ' -- ストアドプロシージャのパラメータ作成 localConnection.beginTrans FOR i = 1 to 6800 localConnection.execute if i = 1 then   localConnection.commitTrans   localConnection.beginTrans end if NEXT  localConnection.commitTrans

  • T-SQLの sp_executesql について

    SQL-Serverでストアドプロシージャを作っています。 EXEC sp_executesql で検索結果をテーブル型変数に格納したいですができるのでしょうか。動的にSQLを発行し、結果を格納する必要がありますのでEXEC sp_executesqlを使わざる得ない状況です。下記にそのサンプルがあります。 Declare @tblAA Table(NO int) declare @strSQL nVarChar(1000) set @strSQL = '' set @strSQL = @strSQL + ' Insert into @tblAA' set @strSQL = @strSQL + ' Select NO from TBLBango' EXEC sp_executesql @strSQL ,N'@tblAA table(No int) OUTPUT', @tblAA OUTPUT Select * from @tblAA これを実行すろと「変数 '@tblAA' を宣言する必要があります。」というエラーがでます。 解決方法を分かる方教えてください。

  • phpMyAdminからストアドプロシージャを

    phpMyAdminからストアドプロシージャを作成したいのですが、エラーが表示され作成できません。 DELIMITER // CREATE PROCEDURE proc1(INT pa char(10)) BEGIN update sum_table set blank = pa; END; // DELIMITER ; これを実行したところ以下のエラーが出ました。 #1064 - You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'INT pa char(10)) BEGIN update sum_table set blank = pa; END' at line 1 -------------------------------------------------------------------------------- そこでソースから「DELIMITER」を消してもう一度実行してみました。 CREATE PROCEDURE proc1(INT pa char(10)) BEGIN update sum_table set blank = pa; END; すると今度は以下のエラーが表示されました。 #1064 - You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'INT pa char(10)) BEGIN update sum_table set blank = pa' at line 1 どこが間違っているかわからず困っております。 初歩的な質問で凝縮ですが、どなたかご教示いただけますでしょうか?

  • Select ~ into ~ で作成した一時テーブルにプライマリキー設定

    SQLServer2005 を使用し、ストアドプロシージャを作成しています。 select ~ into ~ で一時テーブルを作成、データ挿入するのですが、 この命令で作成された一時テーブルにプライマリキーを作成したいと 考えております。 目的は、挿入される件数が多くなりそうなので、 検索を速くする為です。 プライマリキーを作成するのは、 ALTER TABLE ~ CONSTRAINT PK_xxx PRIMARY KEY CLUSTERED ( ~ ) で作成できる事は、理解しております。 これらの処理をストアドプロシージャで行いたいのですが、 注意点としては、当ストアドプロシージャが 並行して実行される事を考慮しておかなくてはなりません。 以下のようなサンプルを作成し、テストしてみたのですが、 セション1でストアドプロシージャ実行後、 セション2でストアドプロシージャを実行してみたのですが、 以下のエラーメッセージが表示されてしまいます。 ここで質問ですが、 制約名をどのようにすれば実現できるのでしょうか。 たとえば、制約名を省略すれば、システム内で一意な名称を 命名してくれるような書き方はないのでしょうか。 ご存じの方、ご回答宜しくお願いします。 -- サンプルストアドプロシージャ create procedure proc_test as select getdate() AS sysdate into #worktable alter table #worktable with nocheck add constraint pk_xxx primary key clustered ([sysdate]) waitfor time '23:59' -- テストの為待機 -- セション1ストアドプロシージャ実行 exec proc_test -- セション2ストアドプロシージャ実行 exec proc_test -- セション2の実行結果 (1 行処理されました) メッセージ 2714、レベル 16、状態 4、プロシージャ proc_test、行 6 データベースに 'pk_xxx' という名前のオブジェクトが既に存在します。 メッセージ 1750、レベル 16、状態 0、プロシージャ proc_test、行 6 制約を作成できませんでした。以前のエラーを調べてください。

  • ユーザー定義関数内でのsp_executesqlプロシージャの使用

    SQLServer2005を使用しています。 今、ユーザー定義関数を作成していて、クエリアナライザにて動作を検証しています。 ユーザー定義関数内で、sp_executesqlを実行しようとすると、 「サーバー : メッセージ 557、レベル 16、状態 2、プロシージャ F_GET_DAY、行 26 関数内から実行できるのは関数と拡張ストアド プロシージャだけです。」 というエラーが出ます。 sp_executesqlは、マスターデータベースの拡張プロシージャに位置づけられているので、実行可能だと思ったのですが・・・。 同じく、マスターデータベースの拡張プロシージャにである「sp_oacreate」の実行を試してみると、関数内で実行できました。 sp_executesqlは、関数内では実行できないのでしょうか。