BATSQL (バッチ SQL) バッチ・コマンド
目的
直接発行することができる SQL ステートメント (DELETE、INSERT、または UPDATE) を実行します。ステートメントによって多くの行数が変更される場合があるため、ターゲット Db2® 表におけるロック・エスカレーションが問題になります。ロック・エスカレーション問題を避けるために、ステートメントは 3 ステージのプロセスで実行されます。
- SQL SELECT ステートメントが生成されます。このステートメントの結果表には、DELETE、INSERT、または UPDATE の対象である行のすべてが入ります。
- 結果表の行が取り出され、要求された操作 (DELETE、INSERT、または UPDATE) が行ごとに適用されます。行は一度に 1 つずつ取り出されるか、または行セットで (一度に複数の行が) 取り出されます。
- 規定された行数が処理された後で、保留されているロックを解除するために Db2® コミットが出されます。
使用
FM/Db2 バッチ SQL ユーティリティーは、以下のアクションを実行できます。
- 指定された表から行を削除します。WHERE 節が指定されていない場合、すべての行が削除される可能性があります。
- 指定された表の行を更新します。WHERE 節が指定されていない場合、すべての行が更新される可能性があります。
- 完全な SELECT による結果表を使用して、挿入される行を生成することによって、指定された表に行を挿入します。
- 指定された数の変更が行われた後で、Db2® コミットを出します。
BATSQL はバッチ専用の関数で、これに相当するフルスクリーン・オプションはありません。BATSQL 関数は単一の SQL DELETE、INSERT、または UPDATE 操作を実行します。
- 1 TYPE=DELETE, UPDATE
- 2 TYPE=INSERT
- 3 TYPE=DELETE
- 4 TYPE=UPDATE
- AUTOCOMMIT=cnt
- 自動 Db2® コミットが出されるまでに処理される正常な操作の数。値ゼロは、すべての行が処理されるまで Db2® コミットは出されないことを示します。有効な値は 0 から 2147483647 です。
行を結果表から読み取るために使用される Db2® カーソルは「WITH HOLD (保留)」で宣言されているため、Db2® コミットはこのカーソルをクローズしません。変更アクティビティーに関連付けられているロックは、Db2® コミットによって解除されます。
- ISOLATION=value
- 結果表にアクセスするカーソルが宣言されている場合に組み込まれる、オプションの分離仕様。デフォルトは、NONE です。
指定できる値については、SQL 解説書で SELECT ステートメントの isolation 節の説明を参照してください。
UNCOMMREAD (UR) は TYPE=DELETE、UPDATE に指定できますが、無視されて CS に変換されます。
- MAXERRORS=errcnt
- Db2® ロールバックが実行されて関数処理が終了するまでに発生できるエラーの最大数。行が処理される場合、負の SQLCODE はエラーとみなされ、エラー・カウントが 1 ずつ増えていきます。行セットが処理される場合、負の SQLCODE はエラーとみなされ、エラー・カウントが現在の行セットの行数だけ増加します。有効な値は 0 から 2147483647 です。
- DELETEALL=<YES|NO>
- すべての行を表から削除する意図を示す、削除処理の仕様。where 節のない TYPE=DELETE 処理では、DELETEALL=YES を指定する必要があります。
where 節なしで DELETE が指定されると、すべての行を表から削除しようと試みるため、このオプションは安全な機能です。
- OBJIN=location.owner.name
- 以下の 3 つの項目を指定します。
- オブジェクトがある Db2® リモート・サーバーの名前 (location、オプション)。
- オブジェクトの所有者の名前 (owner、オプション)。
- 処理されるオブジェクト名 (name)。
location が指定されていない場合、現在の (ローカル) Db2® サーバーが使用されます。owner が指定されていない場合、オブジェクト名は現在の SQLID で修飾されます。
完全修飾名が JCL デックの単一行に納まる場合、OBJIN を使用してください。最後の使用可能列は列 71 です。完全修飾名が JCL デックの単一行に納まらない場合は、OBJILOCN、OBJIOWNR、OBJINAME キーワード (複数可) を使用して、オブジェクトを指定します。
- OBJILOCN=location
- オブジェクトがある Db2® リモート・サーバーの名前 (location、オプション)。Db2 オブジェクト名 の指定を参照してください。
- OBJIOWNR=owner
- 処理されるオブジェクトの所有者の名前 (owner、オプション)。Db2 オブジェクト名 の指定を参照してください。
- OBJINAME=name
- 処理されるオブジェクトのオブジェクト名 (name)。Db2 オブジェクト名 の指定を参照してください。注: TYPE=DELETE および TYPE=UPDATE には OBJIN、OBJILOCN、OBJIOWNR、および OBJINAME を指定します。
- ROWSET=<YES|NO>
- FM/Db2 が行を取り出す (また多くの場合、行を削除および更新する) ときに、行セット処理を使用するかどうかを示す仕様。
- YES
- 行セット処理が使用されます。行セットごとの行数は、AUTOCOMMIT に指定されている値と同じです。AUTOCOMMIT キーワードが省略されると、行セットのサイズはデフォルト (100 行) になります。有効な行セットのサイズは 2 から 10000 です。AUTOCOMMIT 値がこの範囲にない場合、単一行処理が自動的に選択されます。
- NO
- 単一行処理を使用します。
- OBJOUT=location.owner.name
- 以下の 3 つの項目を指定します。
- ターゲット・オブジェクトがある Db2® リモート・サーバーの名前 (location、オプション)。
- ターゲット・オブジェクトの所有者の名前 (owner、オプション)。
- 処理されるターゲット・オブジェクト名 (name)。
location が指定されていない場合、現在の (ローカル) Db2® サーバーが使用されます。owner が指定されていない場合、ターゲット・オブジェクト名は現在の SQLID で修飾されます。
完全修飾名が JCL デックの単一行に納まる場合、OBJOUT を使用してください。最後の使用可能列は列 71 です。完全修飾名が JCL デックの単一行に納まらない場合は、OBJILOCN、OBJIOWNR、OBJINAME キーワード (複数可) を使用して、ターゲット・オブジェクトを指定します。
- OBJOLOCN=location
- ターゲット・オブジェクトがある Db2® リモート・サーバーの名前 (location、オプション)。Db2 オブジェクト名 の指定を参照してください。
- OBJOOWNR=owner
- 処理されるターゲット・オブジェクトの所有者の名前 (owner、オプション)。Db2 オブジェクト名 の指定を参照してください。
- OBJONAME=name
- 処理されるターゲット・オブジェクトのオブジェクト名 (name)。Db2 オブジェクト名 の指定を参照してください。注: TYPE=INSERT には OBJOUT、OBJOLOCN、OBJOOWNR、および OBJONAME を指定します。
- SQLDDWHR=ddinwhr (TYPE=DELETE, UPDATE)
- 有効な SQL where 節を参照する、オプションの DD 名。
このキーワードが省略されると、where 節は、DD DDINWHR で指定されたものと想定されます。
TYPE=DELETE であれば、NULL の where 節を指定できますが、DELETE ステートメントを処理するためにキーワード DELETEALL=YES も組み込む必要があります。
- SQLDDSET=ddinset (TYPE=UPDATE)
- 有効な SQL set 節を参照する、オプションの DD 名 (TYPE=UPDATE の場合のみ)。
このキーワードが省略されると、set 節は、DD DDINSET で指定されたものと想定されます。
SET 節を指定する必要があります。
- SQLDDINS=ddinins (TYPE=INSERT)
- 次のような SQL insert ステートメントに対応する有効な列リストを参照する、オプションの DD 名。
INSERT INTO <object> (column name1, column name2, ..)
このキーワードが省略されると、列リストは、DD DDININS で指定されたものと想定されます。
列名のリストはオプションです。列名のリストが指定されないと、(SQLDDSEL を使用して指定された) SELECT ステートメントによる結果表には、ターゲット表の列と同じ数の列が入るはずです。リストの中の列名はそれぞれ、ターゲット表の列名でなければなりません。
- SQLDDSEL=ddinsel (TYPE=INSERT)
- ターゲット・オブジェクトに挿入される行の結果表を指定する SELECT ステートメントを参照する、オプションの DD 名。
このキーワードが省略されると、SELECT ステートメントは、DD DDINSEL で指定されたものと想定されます。挿入される行を識別する SELECT ステートメントが必要です。
- SQLRECSZ=recsz
- すべての入力データ・セットのオプションのレコード・サイズ。デフォルトは 72です。SQL 節がインラインで JCL デックに指定されている場合、72 より大きい値は指定しないでください。有効な値は 40 から 32760 です。
ヒント
2 から 10000 までの AUTOCOMMIT 値が指定されている場合、行セット処理が自動的に選択されます。
DELETE、INSERT、UPDATE 処理では、FM/Db2 は、1 回の取り出しで行セットの行数を取り出します。DELETE 処理および UPDATE 処理の場合のみ、FM/Db2 は 1 つの SQL ステートメントを使用して、行セットの行数を削除または更新しようと試みます。
INSERT では、それぞれの行が常に 1 行の INSERT ステートメントで挿入されます。
行セット処理で大きな行セット・サイズを使用する場合、大きな領域サイズが必要になる可能性があります。FM/Db2 は、指定された行セットの行数のデータを保管するために十分なストレージを必要とします。
行セットを使用する DELETE 処理および UPDATE 処理では、それらの行セットに対する DELETE 操作または UPDATE 操作が失敗する可能性があります。この障害が発生すると、FM/Db2 は単一行処理を使用して、行セットの行ごとに DELETE 操作および UPDATE 操作を再試行します。行セットの DELETE 操作または UPDATE 操作で検出されたエラーが、エラー・カウンターを増やすことはありません。ただし、単一行の DELETE または UPDATE に対するエラーは、エラー・カウンターを増やします。
例(X)
これらの例は、以下の表定義を参照します。
CREATE TABLE RFM0681A."Names"
("Name_Identifier" INTEGER NOT NULL
,"Last_Name" VARCHAR(16) NOT NULL
,"First_Name" VARCHAR(16) NOT NULL
,"Second_Name" VARCHAR(16) NOT NULL
,"Sex" CHAR(1) NOT NULL
,"Date_Of_Birth" DATE NOT NULL
);
CREATE TABLE RFM0681B."Names"
("Name_Identifier" INTEGER NOT NULL
,"Date_Of_Birth" DATE
,"Sex" CHAR(1)
,"First_Name" VARCHAR(16)
,"Second_Name" VARCHAR(16)
,"Last_Name" VARCHAR(16)
);
例 1
有効な性別 (「F」または「M」) を持っていない行のすべてを表から削除します。50 個の削除操作が完了するたびに、Db2® コミットを出します。何らかのエラーがあれば、停止します。
//FMNDB2 EXEC PGM=FMNDB2,PARM=('SSID=DFXX,SQID=XXXXXXX')
//SYSPRINT DD SYSOUT=*
//FMNTSPRT DD SYSOUT=*
//DDINWHR DD *
WHERE ("Sex" <> 'M'
AND "Sex" <> 'F')
/*
//SYSIN DD *
$$FILEM BATSQL TYPE=DELETE,
$$FILEM OBJIN=RFM0681A."Names",
$$FILEM AUTOCOMMIT=50,
$$FILEM MAXERRORS=1
例 2
以下の項目を持つ行のすべてを表で更新します。
- 姓「Smith」
- 性別「m」
これらの行を、以下の項目を持つように変更します。
- 姓「SMITH」
- 名前「JAMES」
- セカンドネームなし
- 性別「M」
100 個の更新操作が完了するたびに、Db2® コミットを出します。10 個を超えるエラーがあれば、停止します。
//FMNDB2 EXEC PGM=FMNDB2,PARM=('SSID=DFXX,SQID=XXXXXXX')
//SYSPRINT DD SYSOUT=*
//FMNTSPRT DD SYSOUT=*
//DDINSET DD *
SET ("Last_Name", "First_Name", "Second_Name", "Sex") =
('SMITH', 'JAMES', '', 'M')
/*
//DDINWHR DD *
WHERE "Last_Name" = 'Smith'
AND "Sex" = 'm'
/*
//SYSIN DD *
$$FILEM BATSQL TYPE=UPDATE,
$$FILEM OBJIN=RFM0681A."Names",
$$FILEM AUTOCOMMIT=100,
$$FILEM MAXERRORS=10
/*
例 3
RFM0681A."Names" に対する SELECT を使用して行を RFM0681B."Names" に挿入し、結果表を作成します。
"Name_Identifier" の値が 100,000 以下である場合のみ、行を挿入します。
//FMNDB2 EXEC PGM=FMNDB2,PARM=('SSID=DFXX,SQID=XXXXXXX')
//SYSPRINT DD SYSOUT=*
//FMNTSPRT DD SYSOUT=*
//DDININS DD *
(
"First_Name",
"Second_Name",
"Last_Name",
"Sex",
"Date_Of_Birth",
"Name_Identifier"
)
/*
//DDINSEL DD *
SELECT
"First_Name",
"Second_Name",
"Last_Name",
"Sex",
"Date_Of_Birth",
"Name_Identifier"
FROM RFM0681A."Names"
WHERE "Name_Identifier" <= 100000
/*
//SYSIN DD *
$$FILEM BATSQL TYPE=INSERT,
$$FILEM OBJOUT=RFM0681B."Names",
$$FILEM AUTOCOMMIT=50,
$$FILEM MAXERRORS=100
/*