C# や Java などのプログラムから SQL を実行するときはバインド変数を使用して SQL インジェクション対策を行い、データを守るようにすることが一般的だと思いますが、Oracle データベース上で実行される PL / SQL から SQL を発行するときも同様です。Oracle が勝手に対策してくれるわけではありません。
スポンサーリンク
また、「ヘッポコプログラマが一般論を語るな!」という指摘は心が痛みます。きっと的確な指摘なのでしょう。
参照系サンプル
CREATE OR REPLACE PROCEDURE TEST_PROCEDURE(pDeptCd VARCHAR2)
IS
vSql VARCHAR2(1024); -- SQL格納バッファ
type cur_emp_type is ref cursor; -- カーソル変数のオブジェクト定義
cur_emp cur_emp_type; -- カーソル変数定義
user_rcd test_user_mst%rowtype; -- ユーザーマスターテーブルのレコード変数
BEGIN
/*
* カーソル変数オープン
* プロシージャのパラメータをバインドしている。
* バインド変数名(:dept_cd)は何でも良いが、人が理解できるようにつける
*/
open cur_emp for 'select * from test_user_mst where dept_cd = :dept_cd' using pDeptCd;
loop
-- 取得したレコードをを変数に代入。
fetch cur_emp into user_rcd;
-- レコードの終了を判定する
exit when cur_emp%notfound;
-- 取得したレコードからのカラムを出力する
-- ドット(.)でレコード変数とカラム名を連結して指定する
dbms_output.put_line('ユーザーコード:' || user_rcd.test_user_cd);
dbms_output.put_line('ユーザー名 :' || user_rcd.test_user_name);
end loop;
END;
/
更新系サンプル
CREATE OR REPLACE PROCEDURE TEST_PROCEDURE(
pCd VARCHAR2, -- パラメータ1
pName VARCHAR2) -- パラメータ2
IS
vSql VARCHAR2(1024); -- SQL 格納バッファ
BEGIN
/*
* SQLを作成する。バインド変数は :CDと:NAMEである。
* 名前に意味はないが、わかりやすい名称を使用する
*/
vSql := 'insert into test_table(CD, NAME) values(:CD, :NAME)';
/*
* EXECUTE IMMEDIATE で SQLを実行し、USING IN でバインド変数に
* 値を設定している。
*/
EXECUTE IMMEDIATE vSql USING IN pCd, pName;
-- Insertした件数を取得。Update文であれば、更新したレコード数
DBMS_OUTPUT.PUT_LINE('インサート件数 : ' || SQL%ROWCOUNT || '件');
-- コミット(必要であれば)する。
-- トランザクションの制御は外部で行うことも多いだろう
COMMIT;
END;
/