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     */
016    package org.opengion.hayabusa.taglib;
017    
018    import static org.opengion.fukurou.util.StringUtil.nval;
019    
020    import java.io.IOException;
021    import java.io.ObjectInputStream;
022    import java.io.ObjectOutputStream;
023    import java.util.ArrayList;
024    import java.util.HashMap;
025    import java.util.List;
026    import java.util.Locale;
027    import java.util.Map;
028    
029    import javax.script.ScriptEngine;
030    import javax.script.ScriptEngineManager;
031    import javax.script.ScriptException;
032    import javax.servlet.ServletException;
033    
034    import org.opengion.fukurou.db.DBUtil;
035    import org.opengion.fukurou.db.Transaction;
036    import org.opengion.fukurou.db.TransactionReal;
037    import org.opengion.fukurou.model.Formatter;
038    import org.opengion.fukurou.util.ErrorMessage;
039    import org.opengion.fukurou.util.StringUtil;
040    import org.opengion.hayabusa.common.HybsSystem;
041    import org.opengion.hayabusa.common.HybsSystemException;
042    import org.opengion.hayabusa.db.DBTableModel;
043    import org.opengion.hayabusa.resource.ResourceManager;
044    
045    /**
046     * 画面で入力された??タのチェ?を行うためのタグです?
047     *
048     * commandがNEWの場合?検索条件等?リクエストパラメータに対してチェ?を行います?
049     * commandがENTRYの場合?、登録時?DB??ブルモ?に対するチェ?を行います?
050     * (値の取得?、?に選択された行?みにつ?、実行されます?)
051     *
052     * チェ?を行うための定義は、SQL?又? JavaScriptの式が記述可能です?
053     * これら?式?タグのボディー部?記述します?
054     *
055     * SQL?よりチェ?を行う場合?、?件数が返されるように記述して下さ?select count(*) ??? ?
056     * こ?SQL?取得された件数とexistの属?値とを?合しチェ?を行います?
057     * ?れ?場合も、?立時は、正常とみなします?
058     * (?true:存在する? には、データが存在した場合に??で、なければエラーです?)
059     *
060     * JavaScript式を記述する場合?、?true or falseを返す式を?して下さ??
061     * こ?式を評価した結果falseが返される場合?、エラーとみなします?
062     * 式に不等号等を使用する場合?、CDATAセクションで囲??して下さ??
063     *
064     * また??れ?チェ?方法?場合でも?引数部に[カラ?]を用?Hybs拡張SQL?
065     * ?することが可能です?
066     * メ?ージIDの{0},{1}にはそれぞれ[カラ?]?されたカラ?及???タがカンマ区?で
067     * 自動的に設定されます?
068     *
069     * ※ こ?タグは、Transaction タグの対象です?
070     *
071     * @og.formSample
072     * <pre>
073     * ●形式?
074     *       ・&lt;og:dataCheck
075     *                    command       = "{&#064;command}"
076     *                    exist         = "[auto|true|false|one|notuse]"
077     *                    errRemove     = "[true|false]"
078     *                    lbl           = "{&#064;lbl}"
079     *                    lblParamKeys  = "ZY03"      : メ?ージリソースのキーをカンマ区?で??{2} 以降にセ?
080     *                    sqlType       = "{&#064;sqlType}"
081     *                    execType      = "INSERT|COPY|UPDATE|MODIFY|DELETE"  : sqlType を含??合?実?
082     *                    conditionKey  = "FGJ"        : 条件判定するカラ??を指?初期値は columnId )
083     *                    conditionList = "0|1|8|9"    : 条件判定する?のリストを?|"で区?て登録(初期値は、無条件)
084     *                    uniqCheckKeys = "CLM,LANG"   : DBTableModel?のユニ?クキーチェ?を行うためのカラ?
085     *         &gt;
086     *
087     * ●body?あ?EVAL_BODY_BUFFERED:BODYを評価し?{&#064;XXXX} を解析しま?
088     *         (SQL?又? JavaScript?
089     *       ?な? from属?、where属?を使用して、SQL??で作?しま?
090     *
091     * ●Tag定義??
092     *   &lt;og:dataCheck
093     *       command            【TAG】コマン?NEW or ENTRY)をセ?しま?
094     *       exist              【TAG】データベ?スのチェ?方法[auto/true/false/one/notuse]を指定しま?初期値:auto[自動])
095     *       tableId            【TAG?通常は使?せん)結果をDBTableModelに書き込んで、sessionに登録するとき?キーを指定しま?
096     *       dbid               【TAG?通常は使?せん)Queryオブジェクトを作?する時?DB接続IDを指定しま?
097     *       lbl                【TAG】ラベルリソースIDを指定しま?
098     *       lblParamKeys       【TAG】ラベルリソースの引数をカンマ区?で?しま?
099     *       errRemove          【TAG】エラー時?選択行を取り除?継続??行うかど?[true/false]を指定しま?初期値:false)
100     *       sqlType            【TAG】このチェ?を行う、SQLタイ?を指定しま?
101     *       execType           【TAG】このチェ?を行う、実行タイ?を指定しま?
102     *       conditionKey       【TAG】条件判定するカラ??を指定しま?
103     *       conditionList      【TAG】条件判定する?のリストを?|"で区?て登録しま?初期値:無条件)
104     *       uniqCheckClms      【TAG】指定されたキーに従って、メモリ上???ブルに対してユニ?クキーチェ?を行いま?
105     *       beforeErrorJsp     【TAG】エラーが発生した際に、エラーメ?ージの表示前にincludeするJSPを指定しま?
106     *       afterErrorJsp      【TAG】エラーが発生した際に、エラーメ?ージの表示後にincludeするJSPを指定しま?
107     *       selectedAll        【TAG】データを?件選択済みとして処?るかど?[true/false]を指定しま?初期値:false)
108     *       msg                【?】メ?ージIDを指定しま?lbl 属?を使用してください)
109     *       msgParamKeys       【?】メ?ージリソースの引数をカンマ区?で?しま?lblParamKeys 属?を使用してください)
110     *       from               【TAG】tableExist タグ?に伴??簡易機?追??チェ?する??タベ?ス?from 句)を指定します?
111     *       where              【TAG】tableExist タグ?に伴??簡易機?追??チェ?する検索条件(where句)を指定します?
112     *       debug              【TAG】デバッグ??を?力するかど?[true/false]を指定しま?初期値:false)
113     *   &gt;   ... Body ...
114     *   &lt;/og:dataCheck&gt;
115     *
116     * ●使用?
117     *       ・&lt;og:dataCheck
118     *                    command   = "ENTRY"
119     *                    exist     = "true"
120     *                    lbl       = "MSG0001"
121     *         &gt;
122     *             select count(*) from GEA03 where clm = [CLM]
123     *         &lt;/og:dataCheck&gt;
124     *
125     *          ・exist 属?の値に応じて、チェ?方法が異なります?
126     *            [ auto , true , false , one , notuse が指定できます?]
127     *
128     *       ・&lt;og:dataCheck
129     *                    command   = "ENTRY"
130     *                    lbl       = "MSG0001"
131     *         &gt;
132     *           &lt;![CDATA[
133     *             [DYSTART] &lt; [DY] &amp;&amp; [DY] &lt; [DYEND]
134     *           ]]&gt;
135     *         &lt;/og:dataCheck&gt;
136     *
137     *         ・&lt;og:dataCheck
138     *                    command   = "ENTRY"
139     *                    lbl       = "MSG0001"
140     *         &gt;
141     *           &lt;![CDATA[
142     *             [GOKEI] &lt; [TANKA] * [RITU]
143     *           ]]&gt;
144     *         &lt;/og:dataCheck&gt;
145     *
146     *    ※ og:tableExist タグが?されました。og:dataCheckタグで置き換えてください?
147     *       ・&lt;og:tableExist
148     *                    command = "{&#064;command}"
149     *                    names   = "USERID,SYSTEM_ID"
150     *                    from    = "GE10"
151     *                    where   = "USERID=? AND SYSTEM_ID=?"
152     *                    exist   = "true"
153     *         /&gt;
154     * 
155     *        ?
156     *       ・&lt;og:dataCheck
157     *                    command = "{&#064;command}"
158     *                    exist   = "true"
159     *                    from    = "GE10"
160     *                    where   = "USERID=[USERID] AND SYSTEM_ID=[SYSTEM_ID]"
161     *         /&gt;
162     * 
163     *       ・&lt;og:tableExist
164     *                    command = "{&#064;command}"
165     *                    from    = "GE10"
166     *                    where   = "USERID=[USERID] AND SYSTEM_ID=[SYSTEM_ID]"  /&gt;
167     *        ?
168     *       ・&lt;og:dataCheck
169     *                    command = "{&#064;command}"
170     *                    from    = "GE10"
171     *                    where   = "USERID=[USERID] AND SYSTEM_ID=[SYSTEM_ID]"  /&gt;
172     *         /&gt;
173     *
174     * </pre>
175     *
176     * @og.rev 4.1.1.1 (2008/02/22) 新規作?
177     * @og.group ??登録
178     *
179     * @version  4.0
180     * @author       Hiroki Nakamura
181     * @since    JDK5.0,
182     */
183    public class DataCheckTag extends CommonTagSupport {
184            //* こ?プログラ??VERSION??を設定します?       {@value} */
185            private static final String VERSION = "5.7.6.2 (2014/05/16)";
186    
187            private static final long       serialVersionUID        = 576220140516L ;
188    
189            /** command 引数に渡す事?出来?コマン?{@value} */
190            public static final String              CMD_NEW                         = "NEW";
191    
192            /** command 引数に渡す事?出来?コマン?{@value} */
193            public static final String              CMD_ENTRY                       = "ENTRY";
194    
195            /** command 引数に渡す事?出来?コマン?リス? */
196            private static final String[]   COMMAND_LIST            = { CMD_ENTRY, CMD_NEW };
197    
198            /** ?変数 */
199            private transient DBTableModel  table           = null;
200            private transient boolean               isSql           = false;
201            private transient boolean               isUniqCheck     = false; // 4.3.4.0 (2008/12/01) 追?
202            private transient ScriptEngine  jsEngine        = null;
203            private transient String                bodyStr         = null; // 4.3.4.0 (2008/12/01) 追?
204    
205            /** タグで設定する属? */
206            private String          command                 = CMD_ENTRY;
207            private String          exist                   = "auto";
208            private String          tableId                 = HybsSystem.TBL_MDL_KEY;
209            private String          dbid                    = null;
210            private String          lbl                             = null;
211            private String[]        lblParamKeys    = null;         // 4.2.0.1 (2008/03/27)
212            private boolean         errRemove               = false;
213            private String          sqlType                 = null;         // INSERT,COPY,UPDATE,MODIFY,DELETE
214            private String          execType                = null;         // INSERT,COPY,UPDATE,MODIFY,DELETE
215            private boolean         isExec                  = true;         // 4.1.2.0 (2008/03/12)
216    
217            private String          conditionKey    = null;         // 4.2.0.1 (2008/03/27)
218            private String          conditionList   = null;         // 4.2.0.1 (2008/03/27)
219            private String          from                    = null;         // 4.2.0.1 (2008/03/27)
220            private String          where                   = null;         // 5.7.6.2 (2014/05/16) tableExist タグに伴?利機?追?
221            private String[]        uniqCheckClms   = null;         // 4.3.4.0 (2008/12/01)
222    
223            private String          beforeErrorJsp  = null;         // 5.1.9.0 (2010/08/01)
224            private String          afterErrorJsp   = null;         // 5.1.9.0 (2010/08/01)
225            private boolean         selectedAll             = false;        // 5.1.9.0 (2010/08/01)
226    
227            /**
228             * Taglibの開始タグが見つかったときに処??doStartTag() ?オーバ?ライドします?
229             *
230             * @og.rev 4.1.1.0 (2008/02/22) 新規作?
231             * @og.rev 4.1.2.0 (2008/03/12) sqlType,execType 判?
232             *
233             * @return      後続????
234             */
235            @Override
236            public int doStartTag() {
237                    isExec = sqlType == null || execType == null || execType.indexOf( sqlType ) >= 0 ;
238    
239                    if( isExec ) {
240                            return EVAL_BODY_BUFFERED ;             // Body を評価する
241                    }
242                    else {
243                            return SKIP_BODY ;                              // Body を評価しな?
244                    }
245            }
246    
247            /**
248             * Taglibのタグ本体を処??doAfterBody() ?オーバ?ライドします?
249             *
250             * @og.rev 4.3.4.0 (2008/12/01) 新規追?
251             *
252             * @return      後続????(SKIP_BODY)
253             */
254            @Override
255            public int doAfterBody() {
256                    bodyStr = getBodyString().trim();
257                    return SKIP_BODY ;
258            }
259    
260            /**
261             * Taglibの終?グが見つかったときに処??doEndTag() ?オーバ?ライドします?
262             *
263             * @og.rev 4.1.1.0 (2008/02/22) 新規作?
264             * @og.rev 4.1.2.0 (2008/03/12) sqlType,execType 判?
265             * @og.rev 4.2.0.1 (2008/03/27) from を取?
266             * @og.rev 4.2.1.0 (2008/04/11) ErrMessageManager対?
267             * @og.rev 4.3.4.0 (2008/12/01) ユニ?クキーチェ?対応?bodyContentの取得を#doAfterBody()で行う?
268             * @og.rev 5.1.9.0 (2010/08/01) エラーメ?ージの表示前後にincludeするJSPを指定できるようにする?
269             * @og.rev 5.1.9.0 (2010/08/01) Transaction 対応します?
270             * @og.rev 5.3.7.0 (2011/07/01) TransactionReal の引数変更 、Transaction対応で、close処?入れる?
271             *
272             * @return      後続????
273             */
274            @Override
275            public int doEndTag() {
276                    debugPrint();
277                    int rtnCode = EVAL_PAGE;
278    
279                    // 4.1.2.0 (2008/03/12) 実行条件 isExec を評価
280                    if( isExec && check( command, COMMAND_LIST ) ) {
281                            // exist="notuse"の場合?チェ?しな?
282                            if( "notuse".equalsIgnoreCase( exist ) ) { return rtnCode; }
283    
284                            // パラメーターから処??タイプを判別
285                            checkParam();
286    
287                            // エラーメ?ージを管?るクラスを作?します?
288                            ErrMessageManager manager = new ErrMessageManager();
289                            manager.setTitle( "Data Check Error!" );
290                            manager.setParamKeys( lblParamKeys );
291                            manager.setResourceManager( getResource() );
292                            manager.setFrom( from );
293    
294                            // 5.1.9.0 (2010/08/01) TransactionTag 対?
295                            Transaction tran = null ;
296                            // 5.3.7.0 (2011/07/01) Transaction対応で、close処?入れる?
297                            try {
298                                    if( isSql ) {
299                                            TransactionTag tranTag = (TransactionTag)findAncestorWithClass( this,TransactionTag.class );
300                                            if( tranTag == null ) {
301                                                    tran = new TransactionReal( getApplicationInfo() );             // 5.3.7.0 (2011/07/01) 引数変更
302                                            }
303                                            else {
304                                                    tran = tranTag.getTransaction();
305                                            }
306                                    }
307    
308                                    // command="NEW"の場?
309                                    if( CMD_NEW.equals( command ) ) {
310                                            if( isSql ) {
311                                                    checkSql( bodyStr, manager, null, 0, DBTableModel.UPDATE_TYPE, tran );          // 5.1.9.0 (2010/08/01)
312                                            }
313                                            else {
314                                                    checkJs( bodyStr, manager, null, 0, jsEngine );
315                                            }
316                                    }
317                                    // command="ENTRY"の場???ブルモ?が存在しな??合?処?な?
318                                    else if( CMD_ENTRY.equals( command ) ) {
319                                            table = (DBTableModel) getObject( tableId );
320                                            if( table != null && table.getRowCount() > 0 ) {
321                                                    manager.setDBTableModel( table );
322                                                    if( isUniqCheck ) {
323                                                            checkUnique( manager );
324                                                    }
325                                                    else {
326                                                            checkRows( bodyStr, manager, tran );            // 5.1.9.0 (2010/08/01)
327                                                    }
328                                            }
329                                            else {
330                                                    System.out.println( "DBTableModel doesn't exist!! need this when command=\"ENTRY\"" );
331                                            }
332                                    }
333                            }
334                            finally {
335                                    if( tran != null ) { tran.close(); }
336                            }
337    
338                            // エラーが発生した?合?、エラーメ?ージを表示して以降?処?行わな??
339                            ErrorMessage errMessage = manager.getErrMessage() ;
340                            if( errMessage != null && !errMessage.isOK() && !errRemove ) {
341                                    rtnCode = SKIP_PAGE;
342    
343                                    // 5.1.9.0 (2010/08/01) エラーメ?ージの表示前にincludeするJSPを指?
344                                    if( beforeErrorJsp != null && beforeErrorJsp.length() > 0 ) {
345                                            includeJsp( beforeErrorJsp );
346                                    }
347    
348                                    jspPrint( TaglibUtil.makeHTMLErrorTable( errMessage, getResource() ) );
349    
350                                    // 5.1.9.0 (2010/08/01) エラーメ?ージの表示後にincludeするJSPを指?
351                                    if( afterErrorJsp != null && afterErrorJsp.length() > 0 ) {
352                                            includeJsp( afterErrorJsp );
353                                    }
354                            }
355                    }
356    
357                    return rtnCode ;
358            }
359    
360            /**
361             * タグリブオブジェクトをリリースします?
362             * キャ?ュされて再利用される?で、フィールド?初期設定を行います?
363             *
364             * @og.rev 4.1.1.0 (2008/02/22) 新規作?
365             * @og.rev 4.1.2.0 (2008/03/12) sqlType , execType , isExec 追?
366             * @og.rev 4.2.0.1 (2008/03/27) conditionKey , conditionList , msgParamKeys 追?
367             * @og.rev 5.1.9.0 (2010/08/01) beforeErrorJsp , afterErrorJsp, selectedAll 追?
368             * @og.rev 5.7.6.2 (2014/05/16) where 追??tableExist タグに伴?利機?追?
369             */
370            @Override
371            protected void release2() {
372                    super.release2();
373                    tableId                 = HybsSystem.TBL_MDL_KEY;
374                    dbid                    = null;
375                    command                 = CMD_ENTRY;
376                    table                   = null;
377                    exist                   = "auto";
378                    errRemove               = false;
379                    lbl                     = null;
380                    lblParamKeys    = null;         // 4.2.0.1 (2008/03/27)
381                    isSql                   = false;
382                    isUniqCheck             = false;        // 4.3.4.0 (2008/12/01)
383                    jsEngine                = null;
384                    sqlType                 = null;         // INSERT,COPY,UPDATE,MODIFY,DELETE
385                    execType                = null;         // INSERT,COPY,UPDATE,MODIFY,DELETE
386                    isExec                  = true;         // 4.1.2.0 (2008/03/12)
387                    conditionKey    = null;         // 4.2.0.1 (2008/03/27)
388                    conditionList   = null;         // 4.2.0.1 (2008/03/27)
389                    from                    = null;         // 4.2.0.1 (2008/03/27)
390                    where                   = null;         // 5.7.6.2 (2014/05/16) tableExist タグに伴?利機?追?
391                    bodyStr                 = null;         // 4.3.4.0 (2008/12/01))
392                    uniqCheckClms   = null;         // 4.3.4.0 (2008/12/01)
393                    beforeErrorJsp  = null;         // 5.1.9.0 (2010/08/01)
394                    afterErrorJsp   = null;         // 5.1.9.0 (2010/08/01)
395                    selectedAll             = false;        // 5.1.9.0 (2010/08/01)
396            }
397    
398            /**
399             * 引数及?ボディー部??チェ?を行い、???タイプを判別します?
400             *
401             * @og.rev 5.5.8.0 (2012/11/01) タイプ判別変更
402             * @og.rev 5.6.1.1 (2013/02/08) FROM 部の?出し位置修正
403             * @og.rev 5.7.6.2 (2014/05/16) tableExist タグに伴?利機?追??from属?とwhere属?追?
404             */
405            private void checkParam() {
406                    isUniqCheck = uniqCheckClms != null && uniqCheckClms.length > 0 ;
407                    if( isUniqCheck ) {
408                            if( !CMD_ENTRY.equals( command ) ) {
409                                    String errMsg = "ユニ?クキーチェ?は、command=\"ENTRY\"の場合?み使用可能です?"
410                                                            + " command=" + command ;               // 5.1.8.0 (2010/07/01) errMsg 修正
411                                    throw new HybsSystemException( errMsg );
412                            }
413                    }
414                    // 5.7.6.2 (2014/05/16) tableExist タグに伴?利機?追??from属?とwhere属?追?
415                    else if( from != null ) {
416                            StringBuilder buf = new StringBuilder();
417                            buf.append( "SELECT count(*) FROM " ).append( from );
418                            if( where != null ) { buf.append( " WHERE " ).append( where ); }
419                            bodyStr = buf.toString();
420                            isSql = true;
421                    }
422                    else {
423                            if( bodyStr == null || bodyStr.length() == 0 ) {
424                                    String errMsg = "Body部?チェ?定義を記述して下さ??";
425                                    throw new HybsSystemException( errMsg );
426                            }
427                            else {
428                                    // SQLチェ?かJavaScriptによるチェ?か?判?
429                                    String query = bodyStr.toUpperCase( Locale.JAPAN );             // 4.2.0.1 (2008/03/27)
430                                    if( query.indexOf( "SELECT" ) == 0 ) { // 5.5.8.0 (2012/11/01) 先?に限定する?(trim済?ため)
431                                            isSql = true;
432                                            int st = query.indexOf( "FROM" ) ;
433                                            int ed = query.indexOf( "WHERE" ) ;
434                                            if( st > 0 && st < ed ) {
435                                                    from = query.substring( st+"FROM".length(),ed ).trim();         // 5.6.1.1 (2013/02/08)
436                                            }
437                                    }
438                                    else {
439                                            jsEngine = new ScriptEngineManager().getEngineByName( "JavaScript" );
440                                    }
441                            }
442                    }
443            }
444    
445            /**
446             * SQLによる??タチェ?を行います?
447             * チェ?方法?、exist属?の?に依存します?
448             * autoの場合?、テーブルモ?の改廃Cから自動でチェ?方法が決定されます?
449             *
450             * @param       str     実行するSQL?
451             * @param       manager ErrMessageManager オブジェク?
452             * @param       values  SQL??パラメータ
453             * @param       row     行番号
454             * @param       modifyType      改廃C
455             * @param       tran    トランザクションオブジェク?
456             *
457             * @return      処??成否
458             *
459             * @og.rev 4.1.1.0 (2008/02/22) 新規作?
460             * @og.rev 4.2.1.0 (2008/04/11) ErrMessageManager対?
461             * @og.rev 5.1.9.0 (2010/08/01) Transaction 対応します?
462             */
463            private boolean checkSql( final String str, final ErrMessageManager manager, final String[] values
464                                                            , final int row, final String modifyType, final Transaction tran ) {
465    
466                    int cnt = DBUtil.dbExist( str, values, tran, dbid );                    // 5.1.9.0 (2010/08/01)
467    
468                    boolean okFlag = true;
469                    String id = null;
470                    if( ( "true".equalsIgnoreCase( exist ) || ( "auto".equalsIgnoreCase( exist )
471                                    && ( DBTableModel.UPDATE_TYPE.equals( modifyType ) || DBTableModel.DELETE_TYPE.equals( modifyType ) ) ) ) && cnt <= 0 ) {
472                            // ERR0025=??タ未登録エラー。キー={0}、?={1} の??タは、存在して?せん?
473                            id = ( lbl == null ? "ERR0025" : lbl );
474                            okFlag = false;
475                    }
476                    else if( ( "false".equalsIgnoreCase( exist ) || ( "auto".equalsIgnoreCase( exist )
477                                    && DBTableModel.INSERT_TYPE.equals( modifyType ) ) ) && cnt > 0 ) {
478                            // ERR0026=??タ登録済みエラー。キー={0}、?={1} の??タは、すでに存在して?す?
479                            id = ( lbl == null ? "ERR0026" : lbl );
480                            okFlag = false;
481                    }
482                    else if( "one".equalsIgnoreCase( exist ) && cnt > 1 ) {
483                            // ERR0027=??タ?重登録エラー。キー={0}、?={1} の??タは??て存在して?す?
484                            id = ( lbl == null ? "ERR0027" : lbl );
485                            okFlag = false;
486                    }
487    
488                    if( !okFlag ) {
489                            manager.addMessage( row, id, values );
490    
491                    }
492                    return okFlag;
493            }
494    
495            /**
496             * JavaScriptの式を実行します?
497             * 実行した結果がboolean型でな??合?エラーとなります?
498             *
499             * @param str  実行するSQL?
500             * @param       manager オブジェク?
501             * @param values 値配?
502             * @param row 行番号
503             * @param engine JavaScriptエンジン
504             *
505             * @return 処??成否
506             *
507             * @og.rev 4.1.1.0 (2008/02/22) 新規作?
508             * @og.rev 4.2.0.1 (2008/03/27) getClass().getName() から、instanceof に変更
509             * @og.rev 4.2.1.0 (2008/04/11) ErrMessageManager対?
510             */
511            private boolean checkJs(  final String str, final ErrMessageManager manager, final String[] values
512                                                            , final int row, final ScriptEngine engine ) {
513                    // JavaScriptエンジンによる評価
514                    Object obj = null;
515                    try {
516                            obj = engine.eval( str );
517                    }
518                    catch( ScriptException ex ) {
519                            String errMsg = "JavaScript式?パ?スに失敗しました?" + str + "]";
520                            throw new HybsSystemException( errMsg , ex );
521                    }
522    
523                    // 返り値がBoolean型かチェ?
524                    boolean okFlag = false;
525                    // 4.2.0.1 (2008/03/27) instanceof に変更
526                    if( obj instanceof Boolean ) {  // 4.3.1.1 (2008/08/23) instanceof チェ?は、nullチェ?不?
527                            okFlag = ((Boolean)obj).booleanValue();
528                    }
529                    else {
530                            String errMsg = "JavaScript式には true 若しくは false が返るように設定して下さ?
531                                                    + " Object=" + obj ;                    // 5.1.8.0 (2010/07/01) errMsg 修正
532                            throw new HybsSystemException( errMsg );
533                    }
534    
535                    if( !okFlag ) {
536                            // ERR0030=入力したデータが不正です?key={0} value={1} 形?{2}
537                            String id = ( lbl == null ? "ERR0030" : lbl );
538    
539                            manager.addMessage( row, id, values );
540                    }
541    
542                    return okFlag;
543            }
544    
545            /**
546             * DB??ブルモ?の?に対して??タチェ?を行います?
547             *
548             * @param str チェ?対象の??
549             * @param manager ErrMessageManagerオブジェク?
550             * @param tran Transactionトランザクションオブジェク?
551             *
552             * @og.rev 4.1.1.0 (2008/02/22) 新規作?
553             * @og.rev 4.2.0.1 (2008/03/27) conditionKey,conditionList 対?
554             * @og.rev 4.2.1.0 (2008/04/11) ErrMessageManager対?
555             * @og.rev 5.1.9.0 (2010/08/01) Transaction 対応します?
556             */
557            private void checkRows( final String str, final ErrMessageManager manager, final Transaction tran ) {
558    
559                    int[] rowNo = getParameterRows(); // 4.0.0 (2005/01/31)
560                    if( rowNo.length == 0 ) { return; }
561    
562                    Formatter format = new Formatter( table );
563                    format.setFormat( str );
564                    int[] clmNo = format.getClmNos();
565                    // 4.2.0.1 (2008/03/27) カラ?のメ?ージリソース??を作?します?
566                    manager.setClmNos( clmNo );
567    
568                    // SQL??場合?み[xxx]?に変換したSQL?取?JavaScriptの場合?ループ?で?毎に取?
569                    String query = null;
570                    if( isSql ) {
571                            query = format.getQueryFormatString();
572                    }
573    
574                    // 4.2.0.1 (2008/03/27) conditionKey,conditionList 対?
575                    int cndKeyNo = -1;
576                    if( conditionKey != null && conditionList != null ) {
577                            cndKeyNo = table.getColumnNo( conditionKey );           // 不正??エラー
578                    }
579    
580                    List<Integer> list = new ArrayList<Integer>();
581                    boolean okFlag = false;
582                    for( int i = 0; i < rowNo.length; i++ ) {
583                            int row = rowNo[i] ;
584                            String[] values = getTableModelData( row, clmNo );
585                            // 4.2.0.1 (2008/03/27) 条件?がされて?場合に?
586                            // Listに含まれな??合?、実行されな??
587                            // 4.2.1.0 (2008/04/11) 厳?処?ます?
588                            if( cndKeyNo >= 0 && conditionList.indexOf( table.getValue( row,cndKeyNo ) ) < 0 ) {
589                                    String conVal = "|" + table.getValue( row,cndKeyNo ) + "|" ;
590                                    if( conditionList.indexOf( conVal ) < 0 ) { continue; }
591                            }
592    
593                            if( isSql ) {
594                                    okFlag = checkSql( query, manager, values, row, table.getModifyType( row ), tran );
595                            }
596                            else {
597                                    String jsStr = format.getFormatString( row, "\"" );
598                                    okFlag = checkJs( jsStr, manager, values, row, jsEngine );
599                            }
600    
601                            if( errRemove && okFlag ) {
602                                    list.add( row );
603                            }
604                    }
605    
606                    if( errRemove ) {
607                            Integer[] in = list.toArray( new Integer[list.size()] );
608                            int[] newRowNo = new int[in.length];
609                            for( int i = 0; i < in.length; i++ ) {
610                                    newRowNo[i] = in[i].intValue();
611                            }
612                            setParameterRows( newRowNo );
613                    }
614            }
615    
616            /**
617             * DB??ブルモ?の?にユニ?クキーのチェ?を行います?
618             *
619             * @og.rev 4.3.4.0 (2008/12/01) 新規作?
620             *
621             * @param manager ErrMessageManagerオブジェク?
622             */
623            private void checkUnique( final ErrMessageManager manager ) {
624                    int[] rowNo = getParameterRows();
625                    if( rowNo.length == 0 ) { return; }
626    
627                    int[] clmNo = new int[uniqCheckClms.length];
628                    for( int i=0; i<clmNo.length; i++ ) {
629                            clmNo[i] = table.getColumnNo( uniqCheckClms[i] );
630                    }
631    
632                    manager.setClmNos( clmNo );
633    
634                    List<Integer> list = new ArrayList<Integer>();
635                    Map<String,Integer> map = new HashMap<String,Integer>();
636                    for( int i = 0; i < rowNo.length; i++ ) {
637                            int row = rowNo[i] ;
638                            String[] values = getTableModelData( row, clmNo );
639                            String key = StringUtil.array2line( values, " + " );
640    
641                            if( map.get( key ) == null ) {
642                                    map.put( key, 1 );
643                                    if( errRemove ) {
644                                            list.add( row );
645                                    }
646                            }
647                            else {
648                                    // ERR0027=??タ?重登録エラー。キー={0}、?={1} の??タは??て存在して?す?
649                                    id = ( lbl == null ? "ERR0027" : lbl );
650                                    manager.addMessage( row, id, values );
651                            }
652                    }
653    
654                    if( errRemove ) {
655                            Integer[] in = list.toArray( new Integer[list.size()] );
656                            int[] newRowNo = new int[in.length];
657                            for( int i = 0; i < in.length; i++ ) {
658                                    newRowNo[i] = in[i].intValue();
659                            }
660                            setParameterRows( newRowNo );
661                    }
662            }
663    
664            /**
665             * 【TAG?通常は使?せん)結果のDBTableModelを?sessionに登録するとき?キーを指定しま?
666             *              (初期値:HybsSystem#TBL_MDL_KEY[={@og.value org.opengion.hayabusa.common.HybsSystem#TBL_MDL_KEY}])?
667             *
668             * @og.tag
669             * 検索結果より、DBTableModelオブジェクトを作?します?これを?下流?viewタグ等に
670             * 渡す?合に??常は、session を利用します?そ?場合?登録キーです?
671             * query タグを同時に実行して、結果を求める?合?同?モリに配置される為?
672             * こ? tableId 属?を利用して、メモリ空間を?ます?
673             *              (初期値:HybsSystem#TBL_MDL_KEY[={@og.value org.opengion.hayabusa.common.HybsSystem#TBL_MDL_KEY}])?
674             *
675             * @param       id sessionに登録する時? ID
676             */
677            public void setTableId( final String id ) {
678                    tableId = nval( getRequestParameter( id ), tableId );
679            }
680    
681            /**
682             * 【TAG?通常は使?せん)Queryオブジェクトを作?する時?DB接続IDを指定します?
683             *
684             * @og.tag Queryオブジェクトを作?する時?DB接続IDを指定します?
685             *
686             * @param       id ??タベ?ス接続ID
687             */
688            public void setDbid( final String id ) {
689                    dbid = nval( getRequestParameter( id ), dbid );
690            }
691    
692            /**
693             * 【TAG】コマン?NEW or ENTRY)をセ?します?
694             *
695             * @og.tag
696             * コマンド?,HTMLから(get/post)?されます?で,CMD_xxx で設定される
697             * フィールド定数値の?れかを??できます?
698             *
699             * @param       cmd コマン?public static final 宣?れて???)
700             * @see         <a href="../../../../constant-values.html#org.opengion.hayabusa.taglib.DataCheckTag.CMD_NEW">コマンド定数</a>
701             */
702            public void setCommand( final String cmd ) {
703                    String cmd2 = getRequestParameter( cmd );
704                    if( cmd2 != null && cmd2.length() > 0 ) {
705                            command = cmd2.toUpperCase( Locale.JAPAN );
706                    }
707            }
708    
709            /**
710             * 【TAG】データベ?スのチェ?方法[auto/true/false/one/notuse]を指定しま?初期値:auto[自動])?
711             *
712             * @og.tag
713             * exist 属?に?された ?true:存在する??false:存在しな??one:ひとつ以下」?
714             * の値は、いずれの場合も、?立時は、正常とみなします?
715             * ?auto:自動」は、DBTableModeleのmodifyType(A,C,D)に応じて、チェ?します?
716             * A,C,D は、entryタグにコマンドを渡して??タを作?したときに、?部で作?されます?
717             * (command="NEW"の場合?、trueと同じ動きになります?)
718             * notuse は、チェ?を行いません。これ?、このタグを?有使用する場合に、外部で
719             * チェ?を行うかど?を指定できるようにするために使用します?
720             * (?true:存在する? には、データが存在した場合に??で、なければエラーです?)
721             * 初期値は?auto:自動」です?
722             *
723             * @param       ext チェ?方??auto:自動」?true:存在する??false:存在しな??one:ひとつ以下」?notuse:チェ?しな?)
724             */
725            public void setExist( final String ext ) {
726                    exist = nval( getRequestParameter( ext ), exist );
727                    if( !"auto".equalsIgnoreCase( exist )
728                                    && !"true".equalsIgnoreCase( exist )
729                                    && !"false".equalsIgnoreCase( exist )
730                                    && !"one".equalsIgnoreCase( exist )
731                                    && !"notuse".equalsIgnoreCase( exist ) ) {
732                            String errMsg = "exist 属?は?auto,true,false,one,notuse)を指定してください?[" + exist + "]" + HybsSystem.CR;
733                            throw new HybsSystemException( errMsg );
734                    }
735            }
736    
737            /**
738             * 【TAG】エラー時?選択行を取り除?継続??行うかど?[true/false]を指定しま?初期値:false)?
739             *
740             * @og.tag
741             * exist 属?に?された ?true:存在する??false:存在しな??one:ひとつ以下」?
742             * に対して、エラーが発生した選択行番号を?取り除?以下?処?継続するかど??
743             * ?します?
744             * true に設定した?合?、エラー??タを削除し?継続??行うことができます?
745             * flase の場合?、エラー??タを表示して、継続??停止します?
746             * 初期値は?false:エラー時停止?です?
747             *
748             * @param       flag エラー時?継続??[true:エラー行番号を取り除き継続??false:エラー時停止]
749             */
750            public void setErrRemove( final String flag ) {
751                    errRemove = nval( getRequestParameter( flag ), errRemove );
752            }
753    
754            /**
755             * 【?】メ?ージIDを指定しま?lbl 属?を使用してください)?
756             *
757             * @og.tag メ?ージIDを指定します?
758             * ???応じた?期設定?メ?ージIDは、以下?通りです?
759             *   exist="true"   ERR0025=??タ未登録エラー。キー={0}、?={1} の??タは、存在して?せん?
760             *   exist="false"  ERR0026=??タ登録済みエラー。キー={0}、?={1} の??タは、すでに存在して?す?
761             *   exist="one"    ERR0027=??タ?重登録エラー。キー={0}、?={1} の??タは??て存在して?す?
762             *   JavaScript     ERR0030=入力したデータが不正です?key={0} value={1} 形?{2}
763             * 引数のパラメータには??常、チェ?に使用した実データが?DBTableModel から取得されます?
764             * 引数を変更する場合?、lblParamKeys を使用してください?
765             *
766             * @og.rev 5.2.2.0 (2010/11/01) ?します?lbl 属?を使用してください?
767             *
768             * @param id メ?ージID
769             * @see    #setMsgParamKeys( String )
770             * @deprecated  lbl 属?を使用してください?
771             */
772            @Deprecated public void setMsg( final String id ) {
773                    setLbl( id );
774    //              msg = nval( getRequestParameter( id ), msg );
775            }
776    
777            /**
778             * 【TAG】ラベルリソースIDを指定します?
779             *
780             * @og.tag ラベルリソースIDを指定します?
781             * ???応じた?期設定?ラベルリソースIDは、以下?通りです?
782             *   exist="true"   ERR0025=??タ未登録エラー。キー={0}、?={1} の??タは、存在して?せん?
783             *   exist="false"  ERR0026=??タ登録済みエラー。キー={0}、?={1} の??タは、すでに存在して?す?
784             *   exist="one"    ERR0027=??タ?重登録エラー。キー={0}、?={1} の??タは??て存在して?す?
785             *   JavaScript     ERR0030=入力したデータが不正です?key={0} value={1} 形?{2}
786             * 引数のパラメータには??常、チェ?に使用した実データが?DBTableModel から取得されます?
787             * 引数を変更する場合?、lblParamKeys を使用してください?
788             *
789             * @param id メ?ージID
790             * @see    #setLblParamKeys( String )
791             */
792            @Override
793            public void setLbl( final String id ) {
794                    // 継承親のメソ?を使わな??
795                    lbl = nval( getRequestParameter( id ), lbl );
796            }
797    
798            /**
799             * 【?】メ?ージリソースの引数をカンマ区?で?しま?lblParamKeys 属?を使用してください)?
800             *
801             * @og.tag
802             * メ?ージリソースのキーをカンマ区?で?することで、設定します?
803             * メ?ージに引数( {0},{1} など ) がある?合?ここで?した??
804             * ?に、{0},{1},{2}・・・ に当てはめて?ます?
805             * キーワード?、カンマ区?で?し、それを?後?ラベルリソースで
806             * リソース変換を行います?(つまり?記述された?そ?も?では在りません)
807             * PL/SQL では?{#PN}" などと?して???、同様に "PN" と?しです?
808             * ??、where 条件に?されたキーと値は、@KEY と @VAL に?
809             * from と where の間???は?#064;TBL に対応付けられます?
810             * {&#064;XXXX} 変数も使用できます?実データの値を取出した??合?、[PN]と
811             * すれば、DBTableModel の PN の値を取出します?
812             * なにも指定しな??合?、キー={0} 、?={1}、from={2} です?
813             *
814             * @og.rev 4.2.0.1 (2008/03/27) 新規追?
815             * @og.rev 5.2.2.0 (2010/11/01) ?します?lbl 属?を使用してください?
816             *
817             * @param keys メ?ージリソースのキー(CSV)
818             * @see    #setLbl( String )
819             * @deprecated  lblParamKeys 属?を使用してください?
820             */
821            @Deprecated public void setMsgParamKeys( final String keys ) {
822                    setLblParamKeys( keys );
823    //              lblParamKeys = getCSVParameter( keys );
824            }
825    
826            /**
827             * 【TAG】ラベルリソースの引数をカンマ区?で?します?
828             *
829             * @og.tag
830             * ラベルリソースのキーをカンマ区?で?することで、設定します?
831             * ラベルに引数( {0},{1} など ) がある?合?ここで?した??
832             * ?に、{0},{1},{2}・・・ に当てはめて?ます?
833             * キーワード?、カンマ区?で?し、それを?後?ラベルリソースで
834             * リソース変換を行います?(つまり?記述された?そ?も?では在りません)
835             * PL/SQL では?{#PN}" などと?して???、同様に "PN" と?しです?
836             * ??、where 条件に?されたキーと値は?#064;KEY と &#064;VAL に?
837             * from と where の間???は?#064;TBL に対応付けられます?
838             * {&#064;XXXX} 変数も使用できます?実データの値を取出した??合?、[PN]と
839             * すれば、DBTableModel の PN の値を取出します?
840             * なにも指定しな??合?、キー={0} 、?={1}、from={2} です?
841             *
842             * @og.rev 4.2.0.1 (2008/03/27) 新規追?
843             *
844             * @param keys メ?ージリソースのキー(CSV)
845             * @see    #setLbl( String )
846             */
847            public void setLblParamKeys( final String keys ) {
848                    lblParamKeys = getCSVParameter( keys );
849            }
850    
851            /**
852             * 【TAG】このチェ?を行う、SQLタイ?を指定します?
853             *
854             * @og.tag
855             * SQLタイプ?、INSERT,COPY,UPDATE,MODIFY,DELETE などの記号を指定します?
856             * ?には、result 画面から update 画面へ遷移するとき?、command と
857             * 同じにしておけばよいでしょ??
858             * これは、execType とマッチした?合?み、このチェ?が??れます?
859             * 簡?equals タグの代役に使用できます?
860             * なにも指定しな??合?、チェ?は実行されます?
861             *
862             * @og.rev 4.1.2.0 (2008/03/12) 新規追?
863             *
864             * @param       type こ?チェ?を行う、SQLタイ?
865             */
866            public void setSqlType( final String type ) {
867                    sqlType = nval( getRequestParameter( type ),sqlType );
868            }
869    
870            /**
871             * 【TAG】このチェ?を行う、実行タイ?を指定します?
872             *
873             * @og.tag
874             * 実行タイプ?、sqlType とマッチした?合?み、このチェ?が??れます?
875             * 簡?equals タグの代役に使用できます?
876             * execType は、??が可能です?単純な??マッチで、sqlType ?
877             * 含め?、実行されます?
878             * 例えば、sqlType={&#064;sqlType} execType="INSERT|COPY" とすれば?
879             * sqlType に、INSERT また?、COPY が登録された?合にチェ?が掛かります?
880             * なにも指定しな??合?、チェ?は実行されます?
881             *
882             * @og.rev 4.1.2.0 (2008/03/12) 新規追?
883             *
884             * @param       type こ?チェ?を行う、実行タイ?
885             */
886            public void setExecType( final String type ) {
887                    execType = nval( getRequestParameter( type ),execType );
888            }
889    
890            /**
891             * 【TAG】条件判定するカラ??を指定します?
892             *
893             * @og.tag
894             * ??カラ??の値と、conditionList の値を比?て?
895             * 存在する場合?、check処?実行します?
896             * こ?処?有効なのは、command="ENTRY" の場合?みです?
897             *
898             * @og.rev 4.2.0.1 (2008/03/27) 新規追?
899             *
900             * @param       key カラ??
901             * @see         #setConditionList( String )
902             */
903            public void setConditionKey( final String key ) {
904                    conditionKey = nval( getRequestParameter( key ),null ) ;
905            }
906    
907            /**
908             * 【TAG】条件判定する?のリストを?|"で区?て登録しま?初期値:無条件)?
909             *
910             * @og.tag
911             * conditionKey とペアで?します?ここには、カラ??設定?のリストを
912             * ?することで、?条件(??結合)での比?行い、リストにカラ???
913             * 存在する場合?み、check処?実行します?
914             * こ?処?有効なのは、command="ENTRY" の場合?みです?
915             * 設定しな??合?、無条件に実行します?
916             *
917             * @og.rev 4.2.0.1 (2008/03/27) 新規追?
918             *
919             * @param       list 条件判定する?("|"で区?
920             * @see         #setConditionKey( String )
921             */
922            public void setConditionList( final String list ) {
923                    conditionList = nval( getRequestParameter( list ),null ) ;
924                    if( conditionList != null ) {
925                            conditionList = "|" + conditionList + "|" ;
926                    }
927            }
928    
929            /**
930             * 【TAG】指定されたキーに従って、メモリ上???ブルに対してユニ?クキーチェ?を行います?
931             *
932             * @og.tag
933             * ユニ?クキーチェ?を行うキーを指定します?ここで、指定されたキーに対して?
934             * DBTableModelの値をチェ?し?全てのキーに同じ値となって?行が存在すればエラーとなります?
935             * こ?チェ?は、command="ENTRY"の場合?み有効です?
936             * また?こ?チェ?は他?チェ?(DB存在チェ?など)と同時に処?ることはできません?
937             * キーが指定され手?場合?、??部?記述されて?定義は無視されます?
938             * errRemoveの属?がtrueに?されて?場合?重??、DBTableModelの並び?ら見て?
939             * ??の行?み処?れ?2つめ以降?重??無視されます?
940             * なお?キーはカンマ区?(CSV形?で??が可能です?
941             *
942             * @og.rev 4.3.4.0 (2008/12/01) 新規追?
943             *
944             * @param       clm チェ?キー(CSV形?
945             */
946            public void setUniqCheckClms( final String clm ) {
947                    String tmp = nval( getRequestParameter( clm ),null );
948                    uniqCheckClms = StringUtil.csv2Array( tmp );
949            }
950    
951            /**
952             * 【TAG】エラーが発生した際に、エラーメ?ージの表示前にincludeするJSPを指定します?
953             *
954             * @og.tag
955             * エラーが発生した際に、エラーメ?ージの表示前にincludeするJSPを指定します?
956             * エラーが発生して???合?、ここで?されたJSPが??れることはありません?
957             * 通常は、戻るリンクなどを指定します?
958             *
959             * ??方法?、相対パス、絶対パスの両方で?することができます?
960             * ?、絶対パスで?した?合?そ?基点は、コン?スト?ルートディレクトリになります?
961             * ? beforeErrorJsp = "/jsp/common/history_back.jsp"
962             *
963             * @og.rev 5.1.9.0 (2010/08/01) 新規追?
964             *
965             * @param jsp 表示前にincludeするJSPファイル?
966             */
967            public void setBeforeErrorJsp( final String jsp ) {
968                    beforeErrorJsp = nval( getRequestParameter( jsp ),beforeErrorJsp );
969            }
970    
971            /**
972             * 【TAG】エラーが発生した際に、エラーメ?ージの表示後にincludeするJSPを指定します?
973             *
974             * @og.tag
975             * エラーが発生した際に、エラーメ?ージの表示前にincludeするJSPを指定します?
976             * エラーが発生して???合?、ここで?されたJSPが??れることはありません?
977             *
978             * ??方法?、相対パス、絶対パスの両方で?することができます?
979             * ?、絶対パスで?した?合?そ?基点は、コン?スト?ルートディレクトリになります?
980             * ? afterErrorJsp = "/jsp/common/history_back.jsp"
981             *
982             * @og.rev 5.1.9.0 (2010/08/01) 新規追?
983             *
984             * @param jsp 表示後にincludeするJSPファイル?
985             */
986            public void setAfterErrorJsp( final String jsp ) {
987                    afterErrorJsp = nval( getRequestParameter( jsp ),afterErrorJsp );
988            }
989    
990            /**
991             * 【TAG】データを?件選択済みとして処?るかど?[true/false]を指定しま?初期値:false)?
992             *
993             * @og.tag
994             * 全ての??タを選択済み??タとして扱って処?ます?
995             * 全件処?る?合に?true/false)を指定します?
996             * 初期値は false です?
997             *
998             * @og.rev 5.1.9.0 (2010/08/01) 新規追?
999             *
1000             * @param  all 選択済みとして処?るかど?[true:全件選択済み/false:通常]
1001             */
1002            public void setSelectedAll( final String all ) {
1003                    selectedAll = nval( getRequestParameter( all ),selectedAll );
1004            }
1005    
1006            /**
1007             * 【TAG】チェ?する??タベ?ス?from 句)を指定します?
1008             *
1009             * @og.tag
1010             * これは、tableExist タグ?に伴?利機?で??常、BODYに記述され?
1011             * SELECT count(*) from XXXX where XXXXX で、チェ?しますが?
1012             * from 属? と、where 属?を指定する事で、?部で、チェ?用のSQL?
1013             * 作?します?
1014             * from が指定された場合?、BODY は無視されます?で、ご注意く???
1015             *
1016             * @og.rev 5.7.6.2 (2014/05/16) 新規追?
1017             *
1018             * @param  frm チェ?する??ブルID
1019             */
1020            public void setFrom( final String frm ) {
1021                    from = nval( getRequestParameter( frm ),from );
1022            }
1023    
1024            /**
1025             * 【TAG】チェ?する検索条件(where句)を指定します?
1026             *
1027             * @og.tag
1028             * これは、tableExist タグ?に伴?利機?で??常、BODYに記述され?
1029             * SELECT count(*) from XXXX where XXXXX で、チェ?しますが?
1030             * from 属? と、where 属?を指定する事で、?部で、チェ?用のSQL?
1031             * 作?します?
1032             * where は、from が指定された場合?み、有効ですし、where を指定しなければ?
1033             * 全件検索になります?
1034             * tableExist タグと異なる?は、where の??仕方で、tableExist タグでは?
1035             * names 属?と、対応す?where には? で記述して?したが?
1036             * dataCheck タグでは??常の [] でDBTableModelの値を指定します?
1037             *
1038             * @og.rev 5.7.6.2 (2014/05/16) 新規追?
1039             *
1040             * @param  whr チェ?するWHERE 条件
1041             */
1042            public void setWhere( final String whr ) {
1043                    where = nval( getRequestParameter( whr ),where );
1044            }
1045    
1046            /**
1047             * ??行番号の、カラ?o配?(int[])に対応した?の配?を返します?
1048             *
1049             * 表示??タの HybsSystem.ROW_SEL_KEY を?に?ばれた 行を
1050             * 処??対象とします?
1051             *
1052             * @og.rev 4.2.0.1 (2008/03/27) row と clm を?れ替えます?(他とあわせま?
1053             *
1054             * @param       row   行番号
1055             * @param       clmNo カラ?o配?
1056             *
1057             * @return      行番号とカラ?o配?に対応した?値の配?
1058             */
1059            private String[] getTableModelData( final int row, final int[] clmNo ) {
1060                    String[] values = new String[clmNo.length];
1061                    for( int i = 0; i < values.length; i++ ) {
1062                            values[i] = table.getValue( row, clmNo[i] );
1063                    }
1064                    return values;
1065            }
1066    
1067            /**
1068             * エラーメ?ージの前後に処?るJSPをインクルードします?
1069             *
1070             * @og.rev 5.1.9.0 (2010/08/01) 新規作?
1071             *
1072             * @param jsp JSP?
1073             */
1074            private void includeJsp( final String jsp ) {
1075                    try {
1076                            pageContext.include( jsp, false );
1077                    } catch ( IOException ex ) {
1078                            String errMsg = jsp + " の include に失敗しました?";
1079                            throw new HybsSystemException( errMsg,ex );
1080                    } catch ( ServletException ex ) {
1081                            String errMsg = jsp + " の include に失敗しました?";
1082                            throw new HybsSystemException( errMsg,ex );
1083                    }
1084            }
1085    
1086            /**
1087             * 表示??タの HybsSystem.ROW_SEL_KEY を?に?ばれた 行を処??対象とします?
1088             *
1089             * @og.rev 5.1.9.0 (2010/08/01) 新規追?
1090             *
1091             * @return      選択行?配?
1092             */
1093            @Override
1094            protected int[] getParameterRows() {
1095                    final int[] rowNo ;
1096                    if( selectedAll ) {
1097                            int rowCnt = table.getRowCount();
1098                            rowNo = new int[ rowCnt ];
1099                            for( int i=0; i<rowCnt; i++ ) {
1100                                    rowNo[i] = i;
1101                            }
1102                    } else {
1103                            rowNo = super.getParameterRows();
1104                    }
1105                    return rowNo ;
1106            }
1107    
1108            /**
1109             * ErrMessage を管?て? メソ????クラス
1110             *
1111             * 繰返し処?と、固定部が混在したエラーメ?ージで、固定部を?に処??
1112             * 繰返し部は、?時に処?るよ?しました?
1113             * また?実際にエラーが発生して?になるまで、実行遅延させます?
1114             *
1115             * @og.rev 4.2.1.0 (2008/04/11) 新規追?
1116             * @og.rev 4.3.0.0 (2008/07/24) クラス宣?static?
1117             */
1118            private static final class ErrMessageManager {
1119                    // 引数として初期設定される変数
1120                    private String title     = null;
1121                    private String from      = null;
1122                    private String[] lblKeys = null;
1123                    private ResourceManager resource = null;
1124                    private DBTableModel    table    = null;
1125                    private int[]  clmNo    = null;
1126    
1127                    // ?引数として処?れたキャ?ュ値
1128                    private ErrorMessage errMessage  = null;
1129                    private String names     = null;
1130                    private String fromLbl   = null;
1131                    private String[] lblVals = null;
1132    
1133                    private boolean isFirst  = true;                // 初期化されて??true
1134    
1135                    /**
1136                     * ErrMessage のタイトルを設定します?
1137                     *
1138                     * @param       title   タイトル
1139                     */
1140                    public void setTitle( final String title ) { this.title = title; }
1141    
1142                    /**
1143                     * 処?象の??ブル名を設定します?
1144                     *
1145                     * @param       from    ??ブル?
1146                     */
1147                    public void setFrom( final String from ) { this.from = from; }
1148    
1149                    /**
1150                     * 処?象の??ブルオブジェクトを設定します?
1151                     *
1152                     * @param table DBTableModelオブジェク?
1153                     */
1154                    public void setDBTableModel( final DBTableModel table ) { this.table = table; }
1155    
1156                    /**
1157                     * ResourceManagerオブジェクトを設定します?
1158                     *
1159                     * @param resource ResourceManagerオブジェク?
1160                     */
1161                    public void setResourceManager( final ResourceManager resource ) { this.resource = resource; }
1162    
1163                    /**
1164                     * lblParamKeys 属?の配?を設定します?
1165                     *
1166                     * @param       lblKeys 属?の配?
1167                     */
1168                    public void setParamKeys( final String[] lblKeys ) { this.lblKeys = lblKeys; }
1169    
1170                    /**
1171                     * カラ?列を設定します?
1172                     *
1173                     * @param       clmNo   カラ?
1174                     */
1175                    public void setClmNos( final int[] clmNo ) { this.clmNo = clmNo ; }
1176    
1177                    /**
1178                     * 初期処?行います?
1179                     * エラー処??、エラー時?み実行する為、??な??合?、??不要です?
1180                     * ??のエラー出力までは、?部オブジェクト?構築??行いません?
1181                     * ?回目以降?、?部変数にキャ?ュされた変換値を利用して??化します?
1182                     *
1183                     * @og.rev 4.2.3.2 (2008/06/20) from が?null なら?なにもしな??
1184                     */
1185                    private void firstExecute() {
1186                            errMessage = new ErrorMessage( title );
1187    
1188                            // ??ブル(from) をキーにラベルリソースから値を取得します?
1189                            // 4.2.3.2 (2008/06/20) from が?null なら?なにもしな??
1190                            if( from != null ) {
1191                                    fromLbl  = resource.getLabel( from );
1192                            }
1193    
1194                            // カラ?号配?から、カラ?のラベルリソース??のCSV??を作?します?
1195                            names = getKeysLabel( clmNo );
1196    
1197                            if( lblKeys != null && lblKeys.length > 0 ) {
1198                                    int size = lblKeys.length;
1199                                    lblVals = new String[size] ;
1200    
1201                                    for( int i=0; i<size; i++ ) {
1202                                            String key = lblKeys[i] ;
1203                                            if( key != null ) {
1204                                                    if(              "@KEY".equals( key ) ) { lblVals[i] = names;   }
1205                                                    else if( "@TBL".equals( key ) ) { lblVals[i] = fromLbl;}
1206                                                    else if( key.startsWith( "{#" ) && key.endsWith( "}" )  ) {
1207                                                            lblVals[i] = resource.getLabel( key.substring( 2,key.length()-1 ));
1208                                                    }
1209                                                    else {
1210                                                            lblVals[i] = key;
1211                                                    }
1212                                            }
1213                                    }
1214                            }
1215                    }
1216    
1217                    /**
1218                     * カラ?o配?(int[])に対応したカラ?のメ?ージリソース??を返します?
1219                     *
1220                     * @param       clmNo カラ?o配?
1221                     * @return      カラ?o配?に対応した?カラ?のメ?ージリソース
1222                     */
1223                    private String getKeysLabel( final int[] clmNo ) {
1224                            StringBuilder buf = new StringBuilder();
1225                            if( table != null && clmNo.length > 0 ) {
1226                                    String key = table.getColumnName( clmNo[0] );
1227                                    buf.append( resource.getLabel( key ) );
1228                                    for( int i=1; i<clmNo.length; i++ ) {
1229                                            key = table.getColumnName( clmNo[i] );
1230                                            buf.append( "," ).append( resource.getLabel( key ) );
1231                                    }
1232                            }
1233    
1234                            return buf.toString();
1235                    }
1236    
1237                    /**
1238                     * カラ?列を設定します?
1239                     *
1240                     * @og.rev 4.3.5.7 (2008/03/22) エラーメ?ージの行番号を実際の行番号と??させる?
1241                     *
1242                     * @param       row     カラ?
1243                     * @param       id      カラ?
1244                     * @param       values  ??行に対する値
1245                     */
1246                    public void addMessage( final int row, final String id, final String[] values ) {
1247                            if( isFirst ) { firstExecute(); isFirst = false; }
1248    
1249                            String vals = StringUtil.array2csv( values );
1250                            if( lblVals == null ) {
1251                                    errMessage.addMessage( row + 1, ErrorMessage.NG, id, names, vals, fromLbl );
1252                            }
1253                            else {
1254                                    int size = lblKeys.length;
1255                                    String[] args = new String[size] ;
1256    
1257                                    for( int i=0; i<size; i++ ) {
1258                                            String key = lblVals[i] ;
1259                                            if( key != null ) {
1260                                                    if(              "@VAL".equals( key ) ) { args[i] = vals; }
1261                                                    else if( key.startsWith( "[" ) && key.endsWith( "]" )  ) {
1262                                                            if( table != null ) {
1263                                                                    args[i] = table.getValue( row,key.substring( 1,key.length()-1 ) );
1264                                                            }
1265                                                    }
1266                                                    else {
1267                                                            args[i] = key;
1268                                                    }
1269                                            }
1270                                    }
1271                                    errMessage.addMessage( row + 1, ErrorMessage.NG, id, args );
1272                            }
1273                    }
1274    
1275                    /**
1276                     * ErrorMessageオブジェクトを返します?
1277                     *
1278                     * @return ErrorMessage オブジェク?
1279                     */
1280                    public ErrorMessage getErrMessage() { return errMessage; }
1281            }
1282    
1283            /**
1284             * シリアライズ用のカスタ?リアライズ書き込みメソ?
1285             *
1286             * @og.rev 4.0.0.0 (2006/09/31) 新規追?
1287             * @serialData ?のオブジェクト?、シリアライズされません?
1288             *
1289             * @param       strm    ObjectOutputStreamオブジェク?
1290             * @throws IOException  シリアライズに関する入出力エラーが発生した??
1291             */
1292            private void writeObject( final ObjectOutputStream strm ) throws IOException {
1293                    strm.defaultWriteObject();
1294            }
1295    
1296            /**
1297             * シリアライズ用のカスタ?リアライズ読み込みメソ?
1298             *
1299             * ここでは、transient 宣?れた?変数の??初期化が?なフィールド?み設定します?
1300             *
1301             * @og.rev 4.0.0.0 (2006/09/31) 新規追?
1302             * @serialData ?のオブジェクト?、シリアライズされません?
1303             *
1304             * @param       strm    ObjectInputStreamオブジェク?
1305             * @see #release2()
1306             * @throws IOException  シリアライズに関する入出力エラーが発生した??
1307             * @throws ClassNotFoundException       クラスを見つけることができなかった??
1308             */
1309            private void readObject( final ObjectInputStream strm ) throws IOException, ClassNotFoundException {
1310                    strm.defaultReadObject();
1311            }
1312    
1313            /**
1314             * こ?オブジェクト???表現を返します?
1315             * 基本???目?使用します?
1316             *
1317             * @return こ?クラスの??表現
1318             */
1319            @Override
1320            public String toString() {
1321                    return org.opengion.fukurou.util.ToString.title(this.getClass().getName() )
1322                    .println( "VERSION", VERSION )
1323                    .println( "tableId", tableId )
1324                    .println( "dbid", dbid )
1325                    .println( "command", command )
1326                    .println( "exist", exist )
1327                    .println( "lbl", lbl )
1328                    .println( "Other...", getAttributes().getAttribute() ).fixForm().toString();
1329            }
1330    }