001/* 002 * Copyright (c) 2009 The openGion Project. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, 013 * either express or implied. See the License for the specific language 014 * governing permissions and limitations under the License. 015 */ 016package org.opengion.hayabusa.taglib; 017 018import org.opengion.hayabusa.common.HybsSystem; 019import org.opengion.hayabusa.common.HybsSystemException; 020import org.opengion.hayabusa.db.DBTableModel; 021import org.opengion.hayabusa.db.Query; 022import org.opengion.hayabusa.resource.GUIInfo; 023 024import org.opengion.fukurou.util.StringUtil ; 025import static org.opengion.fukurou.util.StringUtil.nval ; 026 027/** 028 * 【廃止】SQL文を直接指定して、データベースに追加/更新/削除を行います(queryType="JDBCPrepared")。 029 * 030 * 存在チェックを行う場合は、tableExist タグと併用してください。 031 * 複雑な処理が必要な場合は、従来より使用しています、PLSQLをCALLする、 032 * plsqlUpdateタグを使用してください。 033 * 034 * ※ このタグは、Transaction タグの対象です。 035 * 036 * @og.formSample 037 * ●形式:<og:update command="…" names="…" queryType="JDBCPrepared" > 038 * {@SQL} 039 * </og:update> 040 * ●body:あり(EVAL_BODY_BUFFERED:BODYを評価し、{@XXXX} を解析します) 041 * 042 * ●Tag定義: 043 * <og:update 044 * queryType 【廃止】Query を発行する為のクラスIDを指定します(初期値:JDBCPrepared) 045 * command 【TAG】コマンド(NEW,RENEW)をセットします(PlsqlUpdateTag,UpdateTag の場合は、ENTRY) 046 * scope 【TAG】キャッシュする場合のスコープ[request/page/session/applicaton]を指定します(初期値:session) 047 * displayMsg 【TAG】検索結果を画面上に表示するメッセージリソースIDを指定します (初期値:VIEW_DISPLAY_MSG[=]) 048 * names 【TAG】PL/SQLを利用する場合の引数にセットすべき データの名称をCSV形式で複数指定します 049 * quotCheck 【TAG】リクエスト情報の クォーティション(') 存在チェックを実施するかどうか[true/false]を設定します(初期値:USE_SQL_INJECTION_CHECK) 050 * tableId 【TAG】(通常は使いません)結果のDBTableModelを、sessionに登録するときのキーを指定します 051 * dbid 【TAG】(通常は使いません)Queryオブジェクトを作成する時のDB接続IDを指定します 052 * xssCheck 【TAG】リクエスト情報の HTMLTag開始/終了文字(><) 存在チェックを実施するかどうか[true/false]を設定します (初期値:USE_XSS_CHECK[=true]) 053 * debug 【TAG】デバッグ情報を出力するかどうか[true/false]を指定します(初期値:false) 054 * > ... Body ... 055 * </og:update> 056 * 057 * ●使用例 058 * ・引数/プロシジャーを他のJSPから渡す場合 059 * 【copy.jsp】 060 * <og:value scope="session" key="names" value="CLM,NAME_JA,LABEL_NAME,KBSAKU,SYSTEM_ID,LANG" /> 061 * <og:value scope="session" key="SQL" > 062 * INSERT INTO GE41 063 * (CLM,NAME_JA,LABEL_NAME,KBSAKU,SYSTEM_ID,LANG, 064 * FGJ,DYSET,DYUPD,USRSET,USRUPD,PGUPD) 065 * VALUES 066 * (?,?,?,?,?,?, 067 * '1','{@USER.YMDH}','{@USER.YMDH}','{@USER.ID}','{@USER.ID}','{@GUI.KEY}') 068 * </og:value> 069 * 070 * 【entry.jsp】 071 * <og:update 072 * command = "{@command}" 073 * queryType = "JDBCPrepared" 074 * names = "{@names}" > 075 * {@SQL} 076 * </og:update> 077 * 078 * <!-- 前画面で指定のSQL文を削除します。(scope="session"なので削除が必要。) --> 079 * <og:value scope="session" key="names" command="REMOVE" /> 080 * <og:value scope="session" key="SQL" command="REMOVE" /> 081 * 082 * ・引数/プロシジャーを直接書く場合 083 * 【entry.jsp】 084 * <og:update 085 * command = "{@command}" 086 * queryType = "JDBCPrepared" 087 * names = "CLM,NAME_JA,LABEL_NAME,KBSAKU,SYSTEM_ID,LANG" 088 * > 089 * INSERT INTO GE41 090 * (CLM,NAME_JA,LABEL_NAME,KBSAKU,SYSTEM_ID,LANG, 091 * FGJ,DYSET,DYUPD,USRSET,USRUPD,PGUPD) 092 * VALUES 093 * (?,?,?,?,?,?, 094 * '1','{@USER.YMDH}','{@USER.YMDH}','{@USER.ID}','{@USER.ID}','{@GUI.KEY}') 095 * </og:update> 096 * 097 * @og.rev 4.0.0.0 (2005/01/31) 廃止 098 * @og.group (廃止)DB登録 099 * 100 * @deprecated 4.0.0 (2005/01/31) 廃止。tableUpdate を利用するようにしてください。 101 * @version 4.0 102 * @author Kazuhiko Hasegawa 103 * @since JDK5.0, 104 */ 105@Deprecated public class UpdateTag extends QueryTag { 106 //* このプログラムのVERSION文字列を設定します。 {@value} */ 107 private static final String VERSION = "4.0.0.0 (2005/01/31)" ; 108 109 private static final long serialVersionUID = 400020050131L ; 110 111 /** command 引数に渡す事の出来る コマンド 登録{@value} */ 112 public static final String CMD_ENTRY = "ENTRY" ; 113 /** command 引数に渡す事の出来る コマンド リスト */ 114 private static final String COMMAND_LIST = CMD_ENTRY; 115 116 /** 117 * Taglibの開始タグが見つかったときに処理する doStartTag() を オーバーライドします。 118 * 119 * @return 後続処理の指示 120 */ 121 @Override 122 public int doStartTag() { 123 dyStart = System.currentTimeMillis(); 124 125 table = (DBTableModel)getObject( tableId ); 126 if( table == null || table.getRowCount() == 0 || 127 ! check( command, COMMAND_LIST ) ) { return(SKIP_BODY); } 128 return( EVAL_BODY_BUFFERED ); // Body を評価する。( extends BodyTagSupport 時) 129 } 130 131 /** 132 * Taglibの終了タグが見つかったときに処理する doEndTag() を オーバーライドします。 133 * 134 * @og.rev 3.5.5.8 (2004/05/20) ErrorMessage オブジェクトを、正常終了時、クリア 135 * 136 * @return 後続処理の指示 137 */ 138 @Override 139 public int doEndTag() { 140 debugPrint(); // 4.0.0 (2005/02/28) 141 142 if( check( command, COMMAND_LIST ) ) { 143 removeSessionAttribute( errMsgId ); 144 } 145 146 executeCount = getParameterRows().length ; // チェック行の数が登録件数と仮定 147 148 // 4.0.0 (2005/01/31) 処理時間集計 149 long dyTime = System.currentTimeMillis()-dyStart; 150 151 // 4.0.0 (2005/01/31) セキュリティチェック(データアクセス件数登録) 152 GUIInfo guiInfo = (GUIInfo)getSessionAttribute( HybsSystem.GUIINFO_KEY ); 153 if( guiInfo != null ) { guiInfo.addWriteCount( executeCount,dyTime,sql ); } 154 155 return(EVAL_PAGE); 156 } 157 158 /** 159 * Query を実行します。 160 * 161 * @og.rev 2.1.2.3 (2002/12/02) データベース更新時に、更新フラグをセットするように変更 162 * @og.rev 3.4.0.0 (2003/09/01) 登録エラー時のキーと値を表示するように変更。 163 * @og.rev 3.5.0.0 (2003/09/17) カラム名ではなく、カラム番号を先に求めておく方式に変更。 164 * @og.rev 3.5.6.0 (2004/06/18) DBRowHeader のパッケージプライベート化に伴なう変更 165 * @og.rev 4.0.0.0 (2005/01/31) getParameterRows() を使用するように変更 166 * 167 * @param query オブジェクト 168 */ 169 @Override 170 protected void execute( final Query query ) { 171 // long st = System.currentTimeMillis(); 172 String[] values = null; 173 int row = 0; 174 try { 175 if( names == null ) { 176 query.execute( null ); 177 } 178 else { 179 int[] rowNo = getParameterRows(); // 4.0.0 (2005/01/31) 180 if( rowNo.length > 0 ) { 181 int[] clmNo = getTableColumnNo( StringUtil.csv2Array( names ) ); 182 values = null; 183 // 逆順にDELETEしないと、行番号がずれてしまう。 184 for( int j=rowNo.length-1; j>=0; j-- ) { 185 row = rowNo[j]; 186 values = getTableModelData( clmNo,row ); // 3.5.0.0 187 query.execute( values ); 188 if( DBTableModel.DELETE_TYPE.equals( table.getModifyType( row ) ) ) { 189 table.removeValue( row ); 190 } 191 else { 192 table.resetModify( row ); 193 } 194 } 195 } 196 } 197// if( query.getUpdateFlag() ) { query.commit(); } 198 if( query.isUpdate() ) { query.commit(); } 199 } 200 catch( HybsSystemException ex ) { 201 query.rollback(); 202 // 3.4.0.0 (2003/09/01) 登録エラー時のキーと値を表示するように変更。 203 String errMsg = "DATABASE ERROR! " 204 + "rowNo=[" + ( row ) + "] " + HybsSystem.CR 205 + "nameArray=[" + names + "]" + HybsSystem.CR 206 + "values=[" + StringUtil.array2csv( values ) + "]" + HybsSystem.CR ; 207 throw new HybsSystemException( errMsg,ex ); // 3.5.5.4 (2004/04/15) 引数の並び順変更 208 } 209 finally { 210 if( query != null ) { query.close(); } 211 } 212 // System.out.println( ( System.currentTimeMillis() - st ) + " ms" ); 213 } 214 215 /** 216 * カラム名配列(String[])より、対応するカラムNo配列(int[])を作成します。 217 * 218 * @og.rev 3.5.0.0 (2003/09/17) 新規追加 219 * 220 * @param nameArray カラム名配列 221 * 222 * @return カラムNo配列 223 */ 224 private int[] getTableColumnNo( final String[] nameArray ) { 225 int[] clmNo = new int[ nameArray.length ]; 226 for( int i=0; i<clmNo.length; i++ ) { 227 clmNo[i] = table.getColumnNo( nameArray[i] ); 228 } 229 return clmNo; 230 } 231 232 /** 233 * 指定の行番号の、カラムNo配列(int[])に対応した値の配列を返します。 234 * 235 * 表示データの HybsSystem.ROW_SEL_KEY を元に、選ばれた 行を 236 * 処理の対象とします。 237 * 238 * @og.rev 3.5.0.0 (2003/09/17) カラム名ではなく、カラム番号を受け取るように修正。 239 * 240 * @param clmNo カラムNo配列 241 * @param row 行番号 242 * 243 * @return 行番号とカラムNo配列に対応した、値の配列 244 */ 245 private String[] getTableModelData( final int[] clmNo,final int row ) { 246 String[] values = new String[ clmNo.length ]; 247 for( int i=0; i<values.length; i++ ) { 248 values[i] = table.getValue( row,clmNo[i] ) ; 249 } 250 return values; 251 } 252 253 /** 254 * 【廃止】Query を発行する為のクラスIDを指定します({@og.doc03Link queryType 初期値:JDBCPrepared})。 255 * 256 * @og.tag 257 * 登録を実行する手段は、Query インターフェースの実装クラスになります。 258 * このタグでは、Query.execute( String[] ) メソッドが複数回呼ばれます。 259 * これは、DBTableModelの選択された行に対して、繰り返し呼ばれます。 260 * 261 * 通常、このタグを使用する場合は、queryType="JDBCPrepared" を指定します。 262 * 263 * タグにより使用できる/出来ないがありますが、これは、org.opengion.hayabusa.db 264 * 以下の Query_**** クラスの **** を与えます。 265 * これらは、Query インターフェースを継承したサブクラスです。 266 * {@og.doc03Link queryType Query_**** クラス} 267 * 268 * @og.rev 3.5.4.2 (2003/12/15) JavaDocコメント用にメソッド追加。 269 * 270 * @param id Query を発行する為の実クラス ID 271 * @see org.opengion.hayabusa.db.Query Queryのサブクラス 272 * @see org.opengion.hayabusa.db.Query#execute( String[] ) 273 * @deprecated クラスが廃止 274 */ 275 @Deprecated public void setQueryType( final String id ) { 276 super.setQueryType( nval( id,"JDBCPrepared" ) ); 277 } 278}