• ベストアンサー

VBからoo4o接続でストアドを呼ぶ方法

お世話になります、 VBからoo4o接続でストアドを呼ぶ方法を探しています。 <現在の状況> ■ストアドパッケージ ・次のように値を返すストアドパッケージがあるとします。これを CreatePLSQLDynaset で実行して、レコードセットを取得します。(OraDynaset) create or replace package testp is procedure GetTestm(key in number, cu out CHAR); end; / create or replace package body testp is procedure GetTestm(key in number,cu out CHAR) is begin select NAME into cu from TEMP where STATUS=key; end; end; / ■VBのボタンイベント Private Sub Command1_Click() Dim dbname Dim cnuser '** サービス、ユーザ設定 dbname = "aaa" cnuser = "bb/bb" '** oo4o 接続 Set GoORASESSION = CreateObject("OracleInProcServer.XOraSession")  Set GoORADATABASE = GoORASESSION.OpenDatabase(dbname, cnuser, &H0) '** リクエリレコードセットオープン Set Recordset = GoORADATABASE.CreatePLSQLDynaset("Begin testp.GetTestm (1,:cu); end;", "cu", &H0) End Sub これを実行したところ以下のようなエラーが出ました <エラー> ____________________________ 実行時エラー '440' SQL実行エラー,ORA-06550:行:1、列:7 PLS-00306:'GETTESTM'の呼び出しで、引数の数または型が正しくありません ORA-06550:行:1、列:7 PL/SQL:Statement ignored _______________________________ というエラーが出てしまいます、引数の数は合っていると思うのですが、どこがお菓子のでしょうか? よろしくお願いします。

noname#1752
noname#1752

質問者が選んだベストアンサー

  • ベストアンサー
  • masabou7
  • ベストアンサー率18% (2/11)
回答No.6

以下にサンプルをご提供します。参考にして下さい。 尚、関数の詳細は、oo4oを使用するVBの専門書か又は、Webで調べて下さい。 ' Oracleに接続 Set OraSession = CreateObject("OracleInProcServer.XOraSession") Set OraDatabase = OraSession.DbOpenDatabase("cims", "test/test", 0&) 'パラメータの型 Const ORAPARM_INPUT = 1 Const ORAPARM_OUTPUT = 2 Const ORAPARM_BOTH = 3 Const ORATYPE_VARCHAR2 = 1 Const ORATYPE_NUMBER = 2 ' SQL実行に使用するVB変数 Dim v_sqlstmt As String Dim v_retcode As Integer 'パラメータのバインド OraDatabase.Parameters.Add "P1", "", ORAPARM_INPUT OraDatabase.Parameters("P1").serverType = ORATYPE_VARCHAR2 OraDatabase.Parameters("P1").Value = "1" OraDatabase.Parameters.Add "P2", "", ORAPARM_INPUT OraDatabase.Parameters("P2").serverType = ORATYPE_NUMBER OraDatabase.Parameters("P2").Value = "1" OraDatabase.Parameters.Add "P3", "", ORAPARM_OUTPUT OraDatabase.Parameters("P3").serverType = ORATYPE_NUMBER OraDatabase.Parameters("P3").MinimumSize = 2 'PL/SQLブロックからプロシージャを呼ぶ v_sqlstmt = "begin test.main(:P1, :P2, :P3); end;" v_retcode = OraDatabase.ExecuteSQL(v_sqlstmt) ' 返り値を表示 MsgBox OraDatabase.Parameters("P1").Value MsgBox OraDatabase.Parameters("P2").Value MsgBox OraDatabase.Parameters("P3").Value 'パラメータリストからパラメータを削除 OraDatabase.Parameters.Remove "P1" OraDatabase.Parameters.Remove "P2" OraDatabase.Parameters.Remove "P3"

その他の回答 (5)

  • TAGOSAKU7
  • ベストアンサー率65% (276/422)
回答No.5

よく見ると[cu]も使用してますねだからストアドの受けにINが必要でした。 ストアドをあんまり見てませんでした・・・ いつもCreatePLSQLDynasetを使用しないで、CreateSqlを使用していたので、結構推測部分が多いアドバイスになってしまいました。 あと GoORADATABASE.Parameters.Add "key", 1, ORAPARM_INPUT ですが、パラメータに1を渡すという意味です。 ですので、 "Begin testp.GetTestm (1,:cu); end;", "cu", &H0 の1を "Begin testp.GetTestm (:key,:cu); end;", "cu", &H0 と変更しました。 環境がないと、正確な事が言えませんね。。。 以後気をつけます。。。m(__)m

  • TAGOSAKU7
  • ベストアンサー率65% (276/422)
回答No.4

1.http://www.fukkey.dyndns.org/pins/search/search.htmlで「くるくるおらくる会議室」で調べる 2.hyu_yaさんの言われたようにサンプルを見る 3.エクスローラのアドレスバーに [Search CreatePLSQLDynaset VB]などと打ちこんで、ネット全体をMSNで検索する いろいろな調べ方がありますよ。

  • hyu_ya
  • ベストアンサー率17% (3/17)
回答No.3

パラメータ(引数)の設定がされてないようですが・・・ 以前、自分も似たような?(その時はVBAでしたが)事が有り 調べてみると身近なところ(自分の端末に!) OO4Oが入っているんですよね?であれば、 [スタート]→[プログラム]→[OracleForWindows xx] →[Oracle Objects for OLE X.X Documentation]より 「パラメータ」とか「ADDメソッド」で検索すると サンプルが載ってます!! 既に知っていて、それでも・・・という場合はごめんなさい。<m(__)m>

  • TAGOSAKU7
  • ベストアンサー率65% (276/422)
回答No.2

追記です。 定数を書くのを忘れてました。 Const ORAPARM_INPUT = 1 Const ORAPARM_OUTPUT = 2 Const ORAPARM_BOTH = 3 Const ORATYPE_VARCHAR2 = 1 Const ORATYPE_NUMBER = 2 Const ORATYPE_SINT = 3 Const ORATYPE_FLOAT = 4 Const ORATYPE_STRING = 5 Const ORATYPE_VARCHAR = 9 Const ORATYPE_DATE = 12 Const ORATYPE_UINT = 68 Const ORATYPE_CHAR = 96 Const ORATYPE_CHARZ = 97

noname#1752
質問者

補足

ストアドを以下のように書き直したところうまくいきました <改良したストアド> create or replace package testp as cursor c1 is select * from TEMP; type testmcu is ref cursor return c1%rowtype; procedure GetTestm(key in varchar2, cu in out testmcu); end; / create or replace package body testp is procedure GetTestm(key in varchar2, cu in out testmcu) is begin open cu for select * from TEMP where STATUS = TO_NUMBER(key); end; end; / 質問であげているストアドは何がいけなかったんでしょうか?

  • TAGOSAKU7
  • ベストアンサー率65% (276/422)
回答No.1

オラクル環境が、今無いので未検証です。。。 '** DBセット Set GoORADATABASE = GoORASESSION.OpenDatabase(dbname, cnuser, &H0) '** パラメータセット GoORADATABASE.Parameters.Add "key", 1, ORAPARM_INPUT GoORADATABASE.Parameters("key").ServerType = ORATYPE_NUMBER GoORADATABASE.Parameters.Add "cu", 0, ORAPARM_OUTPUT GoORADATABASE.Parameters("cu").ServerType = ORATYPE_CHAR '** リクエリレコードセットオープン Set Recordset = GoORADATABASE.CreatePLSQLDynaset("Begin testp.GetTestm (:key,:cu); end;", "cu", &H0)

noname#1752
質問者

補足

パラメタセットを行っても同じエラーが出てしまいます、 ちなみに GoORADATABASE.Parameters.Add "key", 1, ORAPARM_INPUT の「1」とは何を意味しているのでしょうか? VBの関数一覧みたいな情報ってどこで見ればいいのでしょうか?

関連するQ&A

  • PL/SQLのOPEN cursor_name FOR文でCLOSEは必要?

    お世話になります、 Orcacleのストアドで質問があります。 以下のようなストアドを組んだ場合「Close cu1;」は必要なのでしょうか? カーソルをクローズしないとOracleエラー「カーソルが最大数を超えました。。。」というエラーが出るそうなのですが。 ちなみにClose cu1;を入れるとVBからストアドを呼んだ場合に 以下のOracleエラー 「ORA-01403:データがありません」のエラーが出てしまいます。 アドバイス等、よろしくお願いします。 CREATE OR REPLACE PACKAGE MASTERS as CURSOR c1 IS select * from userTable; TYPE type1 IS REF CURSOR RETURN c1%ROWTYPE; PROCEDURE GetD( cu1 OUT type1); end; / -- CREATE OR REPLACE PACKAGE BODY MASTERS IS PROCEDURE GetD( cu1 OUT type1) IS BEGIN OPEN cu1 FOR select * from userTable ; これが必要?→ Close cu1; END GetD; END MASTERS; /

  • VBからストアドの動的SQLを呼んで値をレコードセットで取得する方法

    お世話になります。 VBからストアドの動的SQLを呼んで、VB側で値をレコードセットで取得する方法を探しています。 ■ストアド CREATE OR REPLACE PACKAGE SAMPLE as CURSOR c2 IS select A from TBL; TYPE TANTOYOSANDATA IS REF CURSOR RETURN c2%ROWTYPE; PROCEDURE GetNUMBER(C IN NUMBER,           CU OUT TANTOYOSANDATA); end; / -- CREATE OR REPLACE PACKAGE BODY SAMPLE IS PROCEDURE GetNUMBER(C IN NUMBER,             CU OUT TANTOYOSANDATA) IS CUR INTEGER; STATUS INTEGER; ROW_PROCESSED INTEGER; A NUMBER; BEGIN --カーソルをOPENする CUR :=DBMS_SQL.OPEN_CURSOR; DBMS_SQL.PARSE(CUR,'SELECT A FROM TBL ',DBMS_SQL.V7); DBMS_SQL.DEFINE_COLUMN(CUR,1,A); ROW_PROCESSED :=DBMS_SQL.EXECUTE(CUR); STATUS :=DBMS_SQL.FETCH_ROWS(CUR); WHILE (STATUS <> 0) LOOP DBMS_SQL.COLUMN_VALUE(CUR,1,A); STATUS :=DBMS_SQL.FETCH_ROWS(CUR); END LOOP; END; END SAMPLE; / ■VB側 Set GoORASESSION = CreateObject("OracleInProcServer.XOraSession") Set GoORADATABASE = GoORASESSION.OpenDatabase(dbname, cnuser, ORADB_DEFAULT) Set Recordset = GoORADATABASE.CreatePLSQLDynaset("Begin SAMPLE.GetTANTOINFO(1,:CU)); end;", "CU", ORADYN_DEFAULT) ' If Recordset.EOF Then Do While Not Recordset.EOF Label11.Caption = Recordset(0) Recordset.movenext  Loop 復帰値をRecordSetで受けて それをまわしながら1レコードずつ取得する方法を探しています よろしくお願いします。

  • ストアドについて質問

    質問をご覧いただきまして有難うございます。 初めてストアドプロシージャを作成しており、サンプルでいろいろと作ってみようと思い、作成コードを実行しようとしたんですが、以下のようなメッセージが表示され、正常に実行できません。 ORA-00001: 一意制約(OES4.PK_SITT_IKO_LOG)に反しています ORA-06512: "OES2.PRA002",行16 ORA-06512: 行4 以下はストアドです。 CREATE OR REPLACE PROCEDURE PRACTICE001 IS BEGIN DECLARE --ループ CNT NUMBER; BEGIN CNT := 0; LOOP EXIT WHEN CNT >= 10; CNT := CNT + 1; insert into LOG_TBL values(systimestamp,'test','comments are...'); END LOOP; END; END; テーブル(LOG_TBL)定義は次のようになっています。 LOG_TIME timestamp NOT NULL COMMENT1 varchar2(20) COMMENT2 varchar2(200) タイムスタンプであれば重複もないと思うんですが。。。 原因がよくわからないです。。。 宜しくお願い致します!

  • PerlからOracleのストアドを呼びたいのですが、パラメータに配列は使えますか?

    Perl(5.005_03) からOracle(8i)のストアドを呼びたいのですが、パラメータに配列は使えますか? 使えるのなら、以下のようなストアドをPerl側から呼ぶには、どうすればよいでしょうか? ---------------------------------------------------------------------- /* 配列型 */ CREATE OR REPLACE PACKAGE text_util IS   TYPE vc_arr IS TABLE OF VARCHAR2(10)   INDEX BY BINARY_INTEGER; END; / /* 呼びたいストアド */ CREATE OR REPLACE PROCEDURE TEST_PROC ( v_DATA in text_util.vc_arr, i_IDX in INTEGER ) IS END; / ---------------------------------------------------------------------- よろしくお願いします。 【環境】sun4-solaris, apache

  • ストアドの戻り値(配列)について

    ストアドをコールして配列型の戻り値を取得したいのですが、 エラーが出てしまい原因が分かりません。 どなたかご教授頂けないでしょうか? ★PL/SQL★ CREATE OR REPLACE TYPE TBL_NUM10 AS VARRAY(10) OF NUMBER(10); CREATE OR REPLACE PACKAGE TEST_PKG IS TYPE TBL_NUM10 IS VARRAY(10) OF NUMBER(10); PROCEDURE HAIRETU(O_CNT OUT TBL_NUM10); END TEST_PKG; / CREATE OR REPLACE PACKAGE BODY TEST_PKG IS PROCEDURE HAIRETU(O_CNT OUT TBL_NUM10) IS TMP_CNT TBL_NUM10; BEGIN TMP_CNT := TBL_NUM10(0,0,0,0,0,0,0,0,0,0); TMP_CNT(1) := 1; TMP_CNT(2) := 2; TMP_CNT(3) := 3; O_CNT := TMP_CNT; EXCEPTION WHEN OTHERS THEN DBMS_OUTPUT.PUT_LINE(SQLERRM); END HAIRETU; END TEST_PKG; / DECLARE O_CNT TBL_NUM10; BEGIN TEST_PKG.HAIRETU(O_CNT); DBMS_OUTPUT.PUT_LINE(O_CNT(1)); DBMS_OUTPUT.PUT_LINE(O_CNT(2)); DBMS_OUTPUT.PUT_LINE(O_CNT(3)); END; / ★実行結果★ SQL実行中に以下のエラーが発生しました。 ORA-06550: 行4、列4: PLS-00306: 'HAIRETU'の呼出しで、引数の数または型が正しくありません。 ORA-06550: 行4、列4: PL/SQL: Statement ignored よろしくお願いします。

  • VB6 + OO4O プロシージャの実行&複数行を受け取る方法

    VB6 + OO4O プロシージャの実行&複数行を受け取る方法 現在、VB6でOracleデータベースを操作しようと試みている最中で、 OO4Oで接続しています。 (表現誤っているかもしれません。。。) Oracleは今回初めてで、今まではSQLserverだったのですが、 SQLserverで、  1.ストアドを実行(パラメータあり)  2.レコードセット(複数行)を受け取る  3.ループで全件処理   ・・・ というような処理をしていました。 たとえば、あるテーブルの、ある条件に一致したレコード(複数あり)を全件取得 など。 「引数を渡してストアドプロシージャを実行し、複数行を結果として受け取る」ということがしたく、 Oracleでどのように実現させるかを調べてみたのですが、 「SQL文を記述し、受け取る」  例)strSQL = "select * from tbl"    Set OraDynaset = OraDatabase.CreateDynaset(strSQL, 0) というようなサンプルしか見つけられませんでした。 where句で条件を記述すれば同じなのかもしれませんが、 そういったこまごました記述をストアドプロシージャに記載しておき、 呼び出す際はパラメータだけ指定する、ということを想定しています。 ストアドを実行するサンプルは複数見つけたのですが、戻り値が1つのみか、戻り値なしのもので、 複数行を結果として受け取るようなサンプルが見あたりませんでした。 ストアド(PL/SQL)も作成してみたのですが、 単純に  select * from TBL; とするとエラーで、  select * BULK COLLECT INTO vTBl from TBL;  for i in 1 .. vTBl.count loop   -- 全レコードの項目「name」を表示する。   dbms_output.put_line(vTBl(i).name);  end loop; というように1件1件処理させていく方法しか見つけれませんでした。 Oracleのストアドは、今までのSQLServerの考え方はいけないのでしょうか? 調べるとしたら、どのような単語で調べたらよろしいでしょうか? 「VB6」「oo4o」「複数行」「プロシージャ」など、いろいろ努力はしたつもりなのですが。。。 ご指導よろしくお願いいたします。

  • ストアド実行時のエラー「参照しているコレクションは初期化されていません」

    以下のようなパッケージを作っています。 CREATE OR REPLACE PACKAGE "TEST"."TEST_P" as type test_type1 is table of TEST.TEST_TABLE%ROWTYPE; procedure test2 (ret OUT test_type1 ) ; end; ----------------------------------- 本体 ----------------------------------- CREATE OR REPLACE PACKAGE BODY "TEST"."TEST_P" as procedure test2( ret OUT test_type1 ) is cursor basic_cusor is select * from TEST.TEST_TABLE; BEGIN open basic_cusor; loop fetch basic_cusor into ret(0); exit when basic_cusor%notfound; END loop; END TEST3; end; ---------------------------------------- これをSQL Pluseから set serveroutput on; declare  arg1 TEST.TEST_P.test_type1; begin TEST.TEST_P.test2(arg1); dbms_output.put(arg1(0).coulm1); end; のように実行するとエラーが出ます。 初期化処理とはどのように行えばいいのでしょうか? 最終的にはSQLServerのストアドようにテーブル のような構造で値を返えせればいいです。

  • Oracle: PACKAGE BODY の分割

    業務用に10個以上作成したストアドプロシージャ/ファンクションをパッケージとしてまとめようとしています。保守性の観点から、PACKAGE BODY内の各ストアドを、以下のようなイメージで別々のファイルで管理したいと思っています。 が、PACKAGEとBODYの分割はできたものの、BODY内のストアドを別々にすると、エラーとなってしまいます。 そういうことはできないのでしょうか? [xxx_pkg.SQL] CREATE OR REPLACE PACKAGE xxx_pkg IS PROCEDURE procedure_a; PROCEDURE procedure_b; PROCEDURE procedure_c; END xxx_pkg; [xxx_pkg.procedure_a.SQL] PROCEDURE procedure_a IS -- aの処理 END procedure_a; [xxx_pkg.procedure_b.SQL] PROCEDURE procedure_b IS -- aの処理 END procedure_a; [xxx_pkg.procedure_c.SQL] PROCEDURE procedure_c IS -- aの処理 END procedure_c;

  • ASPでoo4o接続ができません。

    WindowsXPpro(IIS6.0) + Orale9i + ASPで開発をしていますが、 oo4o接続がうまくいかず困っています。 IISとDBサーバは同マシン内の同ドライブ(C)にあり、 現在、やむを得ず、DBサーバにて開発を行っています。 色々調べ、以下のことは全て試してみましたが、 どうしても以下のエラーが出てしまいます。 なお、VB6.0で同じDBにoo4oで接続するサンプルを作って試しましたが、 そちらはうまくいきました。 わかる方、どうかご教授ください。 【試したこと&確認したこと】 ・oo4oはインストールされている ・oip9.dll のレジストリ登録(念のため) ・ora92フォルダに、インターネットゲストアカウントの  読み取り実行&書き込みのアクセス許可を与える  (ちなみにフルコントロール許可を与えてもダメでした) ・SQLNET.oraファイルを以下のように書き換え  SQLNET.AUTHENTICATION_SERVICES= (NONE) 【global.asa】 <OBJECT RUNAT=Server SCOPE=Application ID=OraSession PROGID="OracleInProcServer.XOraSession"> </OBJECT> <SCRIPT LANGUAGE=VBScript RUNAT=Server> Sub Session_OnStart 'OO4O用の設定(Net*8を使用してOracle8に接続する) Set Session("OraDatabase") = OraSession.DbOpenDatabase ("sun151_ora803", "scott/tiger", Clng(3)) Set Session("OraDynaset") = Session ("OraDatabase").DbCreateDynaset("select * from emp order by empno", Clng(4)) End Sub Sub Session_OnEnd Set Session("OraDynaset") = Nothing Set Session("OraDatabase") = Nothing End Sub </SCRIPT> 【エラー内容】 Microsoft VBScript 実行時エラー (0x800A01FB) 例外が発生しました。: 'OraSession.DbOpenDatabase'

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

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