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.SystemManager;
020import org.opengion.hayabusa.db.DBColumn;
021import org.opengion.hayabusa.db.DBTableModel;
022import org.opengion.hayabusa.db.DBTableModelUtil;
023import org.opengion.hayabusa.html.ViewForm;
024import org.opengion.hayabusa.html.ViewFormFactory;
025import org.opengion.hayabusa.resource.ResourceManager;
026import org.opengion.fukurou.util.HybsTimerTask;
027import org.opengion.fukurou.util.HybsTimerTaskManager;
028import org.opengion.fukurou.util.ToString;                                              // 6.1.1.0 (2015/01/17)
029import org.opengion.fukurou.util.ArraySet;                                              // 6.4.3.4 (2016/03/11)
030
031import static org.opengion.fukurou.util.StringUtil.nval ;
032
033import java.util.Timer;
034import java.util.Set;                                                                                   // 6.4.3.4 (2016/03/11)
035import java.util.Map;
036import java.util.HashMap;
037import java.util.Iterator;
038
039/**
040 * アプリケーション共有のタイマー機能を用いて、繰り返しスケジュールを設定するタグです。
041 *
042 * タイマースケジュールは、帳票デーモンや、再編成処理、定期的バッチ処理など、エンジン上の
043 * スレッドで動作するスケジュールを登録します。
044 * スケジュールすべきクラスは、HybsTimerTask を拡張(extends)しておく必要があります。
045 *
046 * @og.formSample
047 * ●形式:<og:schedule timerTask="・・・" name="・・・" command="[SET|VIEW|REMOVE|CANCEL]" ・・・ />
048 * ●body:あり(EVAL_BODY_BUFFERED:BODYを評価し、{@XXXX} を解析します)
049 *
050 * ●Tag定義:
051 *   <og:schedule
052 *       command            【TAG】コマンド (SET,VIEW,REMOVE,CANCEL)をセットします(初期値:SET)
053 *       timerTask        ○【TAG】処理を実行するクラス名(HybsTimerTask のサブクラス)を指定します(必須)。
054 *       name             ○【TAG】名称(ユニークキー)を設定します(必須)。
055 *       comment            【TAG】タイマータスクの説明を設定します
056 *       singleton          【TAG】Name属性が同一のタスクを2重登録出来ないよう[true/false]にします(初期値:true[出来ない])
057 *       delay              【TAG】ミリ秒単位の遅延時間を設定します(初期値:0)
058 *       period             【TAG】ミリ秒単位の繰り返し間隔を設定します(初期値:60000)
059 *       fixedDelay         【TAG】固定遅延実行を指定するかどうか[true:固定遅延実行/false:固定頻度実行]を設定します(初期値:true)
060 *       keys               【TAG】HybsTimerTask に渡す為のキー情報、CSV形式で複数指定します
061 *       vals               【TAG】HybsTimerTask に渡す為の値を、CSV形式で複数指定します
062 *       prmKeys            【TAG】HybsTimerTask に渡すパラメータのキー情報を、CSV形式で指定します(分解しない)。
063 *       prmVals            【TAG】HybsTimerTask に渡すパラメータの値を、CSV形式で指定します(分解しない)。
064 *       startTime          【TAG】24時間制(YYMMDD)の開始時刻を設定します(初期値:000000)
065 *       stopTime           【TAG】24時間制(YYMMDD)の終了時刻を設定します(初期値:000000)
066 *       scope              【TAG】キャッシュする場合のスコープ(local,request,page,session,application)を指定します(初期値:local)
067 *       tableId            【TAG】(通常は使いません)結果をDBTableModelに書き込んで、sessionに登録するときのキーを指定します
068 *       debug              【TAG】デバッグ情報を出力するかどうか[true/false]を指定します(初期値:false)
069 *   >   ... Body ...
070 *   </og:schedule>
071 *
072 * ●使用例
073 *      帳票デーモンスケジュール登録
074 *      period は、ms単位で指定する必要があるため、1000倍しています。
075 *      <og:schedule
076 *          command     = "{@CMD}"
077 *          scope       = "request"
078 *          timerTask   = "org.opengion.hayabusa.report.ReportDaemon"
079 *          name        = "{@NAME}"
080 *          comment     = "Start-up By {@USER.INFO}"
081 *          singleton   = "true"
082 *          delay       = "0"
083 *          period      = "{@PERIOD}000"
084 *          fixedDelay  = "true"
085 *          keys        = "SYSTEM_ID,DMN_GRP"
086 *          vals        = "{@SYSTEM_ID},{@DMN_GRP}"
087 *      />
088 *
089 * @og.group その他部品
090 *
091 * @version  4.0
092 * @author   Kazuhiko Hasegawa
093 * @since    JDK5.0,
094 */
095public class ScheduleTag extends CommonTagSupport {
096        /** このプログラムのVERSION文字列を設定します。   {@value} */
097        private static final String VERSION = "6.4.3.4 (2016/03/11)" ;
098        private static final long serialVersionUID = 643420160311L ;
099
100        /** command 引数に渡す事の出来る コマンド  セット {@value} */
101        public static final String CMD_SET   = "SET";
102        /** command 引数に渡す事の出来る コマンド  ビュー {@value} */
103        public static final String CMD_VIEW   = "VIEW";
104        /** command 引数に渡す事の出来る コマンド  リムーブ {@value} */
105        public static final String CMD_REMOVE   = "REMOVE";
106        /** command 引数に渡す事の出来る コマンド  キャンセル {@value} */
107        public static final String CMD_CANCEL   = "CANCEL";
108
109        // 6.4.3.4 (2016/03/11) String配列 から、Setに置き換えます。
110        private static final Set<String> COMMAND_SET = new ArraySet<>( CMD_SET , CMD_VIEW , CMD_REMOVE , CMD_CANCEL );
111
112        // 3.5.2.0 (2003/10/20) 結果を DBTableModel として、scope 属性に登録する。
113        private String            tableId          = HybsSystem.TBL_MDL_KEY;
114
115        private String  command         = CMD_SET;
116        private String  timerTask       ;                       // 処理を実行する HybsTimerTask のクラス名を指定します。
117        private String  name            ;                       // タイマータスクの名称(ユニークキー)
118        private String  comment         ;                       // タイマータスクの説明
119        private long    delay           ;                       // タスクが実行される前のミリ秒単位の遅延(初期値:0)
120        private long    period          = 60000l;       // 連続するタスク実行のミリ秒単位の時間(初期値:60000 mS)
121        private boolean fixedDelay      = true;         // 固定遅延実行(true)/固定頻度実行(false) (初期値:true)
122        private int             uniqKey         = -1;           // ありえない値を初期設定しておく。
123        private boolean singleton       = true;         // Name属性が同一のタスクを2重登録出来ないようにする(初期値:true)
124
125        private static final long FIXED_RATE_MIN_TIME = 1000;   // 固定頻度実行時の最小繰り返し時間
126
127        private static final String TIMER_KEY           = HybsSystem.SCEDULE_KEY;
128        private static final String TIMERTASK_KEY       = HybsSystem.SCEDULE_TASK_KEY;
129
130        // 6.2.5.1 (2015/06/12) CSV形式のkeys,vals引数(CSV引数)対応。
131        private String          keys            ;                       // タイマータスクへ渡すキー配列
132        private String          vals            ;                       // タイマータスクへ渡すバリュー配列
133
134        private String          body            ;                       // タイマータスクへ渡すボディー要素
135        private String          startTime       = "000000";     // 24時間制の開始時刻
136        private String          stopTime        = "000000";     // 24時間制の終了時刻
137
138        // 3.5.2.0 (2003/10/20) 結果を DBTableModel として、scope 属性に登録する。
139        private String          scope           = "local";      // local は互換性のため。"request","page","session","application"
140
141        // 3.7.0.4 (2005/03/14) 帳票デーモンに、エラー時にスリープして待機する機能を追加
142        private final int ERROR_SLEEP_TIME = HybsSystem.sysInt( "REPORT_DAEMON_ERROR_SLEEP_TIME" );
143
144        // 4.0.0 (2006/11/17) HybsTimerTaskManager を static クラスから通常オブジェクトとして管理。
145        private static final HybsTimerTaskManager TASK_MANAGER ;                        // 6.4.1.1 (2016/01/16) taskManager  → TASK_MANAGER  refactoring
146
147        // 4.0.0 (2005/01/31) Cleanable インターフェースによる初期化処理
148        // 4.3.6.2 (2009/04/15) コンテキスト終了時のみclear()されるように対応
149        static {
150                TASK_MANAGER = new HybsTimerTaskManager();
151                // 4.3.6.2 (2009/04/15)
152                SystemManager.addCleanable( TASK_MANAGER, true );       // コンテキスト終了時のみ呼び出す
153        }
154
155        /**
156         * デフォルトコンストラクター
157         *
158         * @og.rev 6.4.2.0 (2016/01/29) PMD refactoring. Each class should declare at least one constructor.
159         */
160        public ScheduleTag() { super(); }               // これも、自動的に呼ばれるが、空のメソッドを作成すると警告されるので、明示的にしておきます。
161
162        /**
163         * Taglibの開始タグが見つかったときに処理する doStartTag() を オーバーライドします。
164         *
165         * @og.rev 3.2.2.0 (2003/05/31) HybsTimerTask に対して、設定値を渡せるように変更。
166         *
167         * @return      後続処理の指示( EVAL_BODY_BUFFERED )
168         */
169        @Override
170        public int doStartTag() {
171                return EVAL_BODY_BUFFERED ;     // Body を評価する。( extends BodyTagSupport 時)
172        }
173
174        /**
175         * Taglibのタグ本体を処理する doAfterBody() を オーバーライドします。
176         *
177         * @og.rev 3.2.2.0 (2003/05/31) HybsTimerTask に対して、設定値を渡せるように変更。
178         *
179         * @return      後続処理の指示(SKIP_BODY)
180         */
181        @Override
182        public int doAfterBody() {
183                body = getBodyString();
184
185                return SKIP_BODY ;
186        }
187
188        /**
189         * Taglibの終了タグが見つかったときに処理する doEndTag() を オーバーライドします。
190         *
191         * @og.rev 3.1.1.2 (2003/04/04) Tomcat4.1 対応。release2() を doEndTag()で呼ぶ。
192         * @og.rev 3.6.0.8 (2004/11/19) DBTableModel をセーブする時に、トランザクションチェックを行います。
193         * @og.rev 6.4.3.4 (2016/03/11) String配列 から、Setに置き換えます。
194         *
195         * @return      後続処理の指示
196         */
197        @Override
198        public int doEndTag() {
199                debugPrint();           // 4.0.0 (2005/02/28)
200                if( !check( command, COMMAND_SET ) ) { return EVAL_PAGE ; }
201
202                if( "session".equals( scope ) ) {
203                        startQueryTransaction( tableId );               // 3.6.0.8 (2004/11/19)
204                }
205
206                // 3.6.0.8 (2004/11/19) トランザクションチェックを行います。
207                if( commandExec( command ) ) {
208                        return EVAL_PAGE ;              // ページの残りを評価する。
209                }
210                else {
211                        jspPrint( "ScheduleTag Query処理が割り込まれました。DBTableModel は登録しません。" );
212                        return SKIP_PAGE;
213                }
214        }
215
216        /**
217         * タグリブオブジェクトをリリースします。
218         * キャッシュされて再利用されるので、フィールドの初期設定を行います。
219         *
220         * @og.rev 3.1.1.2 (2003/04/04) Tomcat4.1 対応。release2() を doEndTag()で呼ぶ。
221         * @og.rev 3.2.2.0 (2003/05/31) HybsTimerTask に対して、設定値を渡せるように変更。
222         * @og.rev 3.5.2.0 (2003/10/20) 結果を DBTableModel として、scope 属性に登録する。
223         */
224        @Override
225        protected void release2() {
226                super.release2();
227                command         = CMD_SET;
228                timerTask       = null;         // 処理を実行する HybsTimerTask のクラス名を指定します。
229                name            = null;         // タイマータスクの名称(ユニークキー)
230                comment         = null;         // タイマータスクの説明
231                delay           = 0;            // タスクが実行される前のミリ秒単位の遅延(初期値:0)
232                period          = 60000;        // 連続するタスク実行のミリ秒単位の時間(初期値:60000 mS)
233                fixedDelay      = true;         // 固定遅延実行(true)/固定頻度実行(false) (初期値:true)
234                uniqKey         = -1;           // ありえない値を初期設定しておく。
235                singleton       = true;         // Name属性が同一のタスクを2重登録出来ないようにする(初期値:true)
236                keys            = null;         // タイマータスクへ渡すキー配列
237                vals            = null;         // タイマータスクへ渡すバリュー配列
238                startTime       = "000000";     // 24時間制の開始時刻
239                stopTime        = "000000";     // 24時間制の終了時刻
240                tableId         = HybsSystem.TBL_MDL_KEY;               //
241                scope           = "local";      // local は互換性のため。"request","page","session","application"
242        }
243
244        /**
245         * コマンドを実行します。
246         *
247         * コマンドは、HTMLから(SET/VIEW/REMOVE/CANCEL)指定されますので、setCommand()メソッドで
248         * 登録します。
249         * コマンドを登録すると同時に、実行も行ないます。
250         *
251         * @og.rev 3.5.2.0 (2003/10/20) viewAttribute()メソッドを、全てで実行します。
252         * @og.rev 3.6.0.8 (2004/11/19) 正常に登録できたかどうかを、返します。
253         * @og.rev 4.0.0.0 (2007/10/18) メッセージリソース統合( setMsg() ⇒ setLbl )
254         *
255         * @param   command コマンド (public static final 宣言されている文字列)
256         * @see         <a href="../../../../constant-values.html#org.opengion.hayabusa.taglib.ScheduleTag.CMD_SET">コマンド定数</a>
257         *
258         * @return 正常かどうか(true:正常/false:異常)
259         */
260        protected boolean commandExec( final String command ) {
261                if( CMD_SET.equals( command ) ) {
262                        setAttribute();
263                        setLbl( "MSG0059" );    // 登録しました。
264                        jspPrint( getMsglbl() );
265                }
266                else if( CMD_VIEW.equals( command ) ) {
267                        jspPrint( String.valueOf( TASK_MANAGER.size() ) );
268                        setLbl( "MSG0033" );    //  件検索しました。
269                        jspPrint( getMsglbl() );
270                }
271                else if( CMD_REMOVE.equals( command ) ) {
272                        removeAttribute();
273                        setLbl( "MSG0061" );    // 削除しました。
274                        jspPrint( getMsglbl() );
275                }
276                else if( CMD_CANCEL.equals( command ) ) {
277                        cancelAttribute();
278                        setLbl( "MSG0063" );    // 完了しました。
279                        jspPrint( getMsglbl() );
280                }
281                return viewAttribute();
282        }
283
284        /**
285         * HybsTimerTask を登録します。
286         *
287         * @og.rev 3.2.2.0 (2003/05/31) HybsTimerTask に対して、設定値を渡せるように変更。
288         * @og.rev 3.6.0.7 (2004/11/06) パラメータをMapで渡すように変更。
289         * @og.rev 3.7.0.4 (2005/03/14) HybsTimerTask に setErrorSleepSec メソッドの追加
290         * @og.rev 6.2.5.1 (2015/06/12) CSV形式のkeys,vals引数(CSV引数)対応。
291         */
292//      @SuppressWarnings(value={"unchecked"})
293        private void setAttribute() {
294                // シングルトンで、かつ、すでに、同一名称のタスクが
295                // 含まれている場合は、セットしない。
296                if( singleton && TASK_MANAGER.contains( name ) ) { return ; }
297
298                // 6.2.5.1 (2015/06/12) CSV形式のkeys,vals引数(CSV引数)対応。
299                final Map<String,String> param = getCSVParameter( keys,vals );
300
301                final HybsTimerTask task = HybsSystem.newInstance( timerTask );
302                TASK_MANAGER.addTask( task );
303
304                task.setName( name );
305                task.setComment( comment );
306                task.setParameter( param );             // 3.6.0.7 (2004/11/06)
307                task.setBody( body );
308                task.setStartTime( startTime );
309                task.setStopTime( stopTime );
310                task.setErrorSleepSec( ERROR_SLEEP_TIME );      // 3.7.0.4 (2005/03/14)
311                task.initDaemon();
312
313                // 3.6.1.0 (2005/01/05) Timer 同一スレッドのため、個別に作成する。
314                @SuppressWarnings(value={"unchecked"})          // 8.2.1.0 (2022/07/15) メソッド全体から局所化
315                Map<String,Timer> timerMap = (Map<String,Timer>)getContextAttribute( TIMER_KEY );
316                if( timerMap == null ) { timerMap = new HashMap<>(); }
317
318                Timer timer = timerMap.get( name );
319                if( timer == null ) { timer = new Timer( true ); }
320
321                if( fixedDelay ) {
322                        if( period > 0 ) { timer.schedule( task,delay,period ); }
323                        else             { timer.schedule( task,delay ); }
324                }
325                else {
326                        if( period < FIXED_RATE_MIN_TIME ) { period = FIXED_RATE_MIN_TIME; }
327                        timer.scheduleAtFixedRate( task,delay,period );
328                }
329
330                // 3.6.1.0 (2005/01/05) Timer 同一スレッドのため、個別に作成する。
331                timerMap.put( name,timer );
332                setContextAttribute( TIMER_KEY,timerMap );
333        }
334
335        /**
336         * HybsTimerTask を一覧表示します。
337         *
338         * @og.rev 3.5.2.0 (2003/10/20) 結果を DBTableModel として、scope 属性に登録する。
339         * @og.rev 3.5.6.1 (2004/06/25) lang 言語コード 属性を削除します。
340         * @og.rev 3.6.0.8 (2004/11/19) DBTableModel をセーブする時に、トランザクションチェックを行います。
341         * @og.rev 3.6.0.8 (2004/11/19) 正常に登録できたかどうかを、返します。
342         *
343         * @return 正常かどうか(true:正常/false:異常)
344         */
345        private boolean viewAttribute() {
346                final HybsTimerTask[] tasks = TASK_MANAGER.toArray();
347                final DBTableModel table = makeDBTable( tasks );
348
349                if( "local".equals( scope ) ) {
350                        if( table != null ) {
351                                final ViewForm form = ViewFormFactory.newInstance( "HTMLTable" );
352                                form.clear();
353                                form.init( table );
354                                jspPrint( form.create() );
355                        }
356                }
357                else {
358                        super.setScope( scope );                // 3.6.0.9 (2004/12/03)
359                        // 3.6.0.8 (2004/11/19) トランザクションチェックを行います。
360                        return commitTableObject( tableId, table );
361                }
362                return true;
363        }
364
365        /**
366         * HybsTimerTask を削除します。
367         *
368         * @og.rev 3.2.2.0 (2003/05/31) キャンセルを名前でもできる様にロジック追加。
369         *
370         */
371        private void removeAttribute() {
372                if( uniqKey >= 0 ) {
373                        TASK_MANAGER.cancelTask( uniqKey );
374                }
375                else {
376                        TASK_MANAGER.cancelTask( name );
377                }
378        }
379
380        /**
381         * Timer そのものをキャンセルします。
382         *
383         * すべての、HybsTimerTask は、削除されます。
384         *
385         * @og.rev 3.6.1.0 (2005/01/05) Timer 同一スレッドのため、個別に作成する。
386         */
387//      @SuppressWarnings(value={"unchecked"})
388        private void cancelAttribute() {
389                TASK_MANAGER.clear();
390
391                // 3.6.1.0 (2005/01/05)
392                @SuppressWarnings(value={"unchecked"})          // 8.2.1.0 (2022/07/15) メソッド全体から局所化
393                final Map<String,Timer> timerMap = (Map<String,Timer>)getContextAttribute( TIMER_KEY );
394                if( timerMap != null ) {
395                        final Iterator<Timer> iterator = timerMap.values().iterator();  // 4.3.3.6 (2008/11/15) Generics警告対応
396                        while( iterator.hasNext() ) {
397                                (iterator.next()).cancel();     // 4.3.3.6 (2008/11/15) Generics警告対応
398                        }
399                        timerMap.clear();
400                }
401                removeContextAttribute( TIMER_KEY );
402        }
403
404        /**
405         * 【TAG】コマンド (SET,VIEW,REMOVE,CANCEL)をセットします(初期値:SET)。
406         *
407         * @og.tag
408         * コマンドは、HTMLから(get/post)指定されますので、CMD_xxx で設定される
409         * フィールド定数値のいづれかを、指定できます。
410         * 何も設定されない、または、null の場合は、"SET" が初期値にセットされます。
411         *
412         * @param       cmd コマンド (public static final 宣言されている文字列)
413         * @see         <a href="../../../../constant-values.html#org.opengion.hayabusa.taglib.ScheduleTag.CMD_SET">コマンド定数</a>
414         */
415        public void setCommand( final String cmd ) {
416                command = nval( getRequestParameter( cmd ),command );
417        }
418
419        /**
420         * 【TAG】処理を実行するクラス名(HybsTimerTask のサブクラス)を指定します。
421         *
422         * @og.tag 処理を実行する HybsTimerTask のクラス名を指定します。
423         *
424         * @param   val クラス名
425         */
426        public void setTimerTask( final String val ) {
427                timerTask = getRequestParameter( val );
428        }
429
430        /**
431         * 【TAG】名称(ユニークキー)を設定します。
432         *
433         * @og.tag タイマータスクの名称(ユニークキー)を設定します。
434         *
435         * @param   nm タイマータスクの名称
436         */
437        public void setName( final String nm ) {
438                name = getRequestParameter( nm );
439        }
440
441        /**
442         * 【TAG】タイマータスクの説明を設定します。
443         *
444         * @og.tag タイマータスクの説明を設定します。
445         *
446         * @param   cmt タイマータスクの説明
447         */
448        public void setComment( final String cmt ) {
449                comment = getRequestParameter( cmt );
450        }
451
452        /**
453         * 【TAG】ミリ秒単位の遅延時間を設定します(初期値:0)。
454         *
455         * @og.tag タスクが実行される前のミリ秒単位の遅延を設定します(初期値:0)
456         *
457         * @param   val 遅延時間(ms)
458         */
459        public void setDelay( final String val ) {
460                delay = nval( getRequestParameter( val ),delay );
461        }
462
463        /**
464         * 【TAG】ミリ秒単位の繰り返し間隔を設定します(初期値:60000)。
465         *
466         * @og.tag 連続するタスク実行のミリ秒単位の時間を設定します(初期値:60000 mS)
467         *
468         * @param   val 繰り返し間隔(ms)
469         */
470        public void setPeriod( final String val ) {
471                period = nval( getRequestParameter( val ),period );
472        }
473
474        /**
475         * 【TAG】固定遅延実行を指定するかどうか[true:固定遅延実行/false:固定頻度実行]を設定します(初期値:true)。
476         *
477         * @og.tag
478         * 固定遅延実行では、前の実行の実際の実行時間を基準にしてそれぞれの実行がスケジュールされます。
479         * 何らかの理由で実行が遅延した場合 そのあとの実行も遅延されます。
480         * 最終的に、実行の頻度は通常、指定した期間の対応する頻度よりも若干遅くなります
481         *
482         * 固定頻度実行では、最初の実行のスケジュールされた実行時間を基準にしてそれぞれの実行が
483         * スケジュールされます。何らかの理由で実行が遅延した場合、「遅れを取り戻す」ために
484         * 2 つ以上の実行が連続して行われます。最終的に実行の頻度は、指定した期間の対応する頻度と
485         * 同じになります
486         * 初期値は、true:固定遅延実行 です。
487         *
488         * @param   flag 遅延方式指定 [true:固定遅延実行/false:固定頻度実行]
489         */
490        public void setFixedDelay( final String flag ) {
491                fixedDelay = nval( getRequestParameter( flag ),fixedDelay );
492        }
493
494        /**
495         * 【TAG】スケジュールを一意に決めるためのユニーク番号を指定します(初期値:-1)。
496         *
497         * @og.tag
498         * スケジュールを削除したりする場合に、必要なユニーク番号を指定します。
499         * 初期値は、-1:あり得ない値 です。
500         *
501         * @param   no ユニーク番号
502         */
503        public void setUniqKey( final String no ) {
504                uniqKey = nval( getRequestParameter( no ),uniqKey );
505        }
506
507        /**
508         * 【TAG】Name属性が同一のタスクを2重登録出来ないよう[true:禁止/false:なにもない]にします(初期値:true:禁止)。
509         *
510         * @og.tag
511         * 同一種類のタスクを複数同時立上げしたくない場合に、利用します。
512         * 一般に、タイマータスクそのものが、繰り返し実行されますので、
513         * 初期値は、2重登録禁止にしています。
514         *
515         * @param   flag 2重登録不可 [true:禁止/false:なにもない]
516         */
517        public void setSingleton( final String flag ) {
518                singleton = nval( getRequestParameter( flag ),singleton );
519        }
520
521        /**
522         * 【TAG】HybsTimerTask に渡す為のキー情報、CSV形式で複数指定します。
523         *
524         * @og.tag
525         * HybsTimerTask に渡す為の、キー情報をCSV形式で複数指定できます。
526         * vals 属性には、キーに対応する値を、設定してください。
527         * 分解方法は、CSV変数を先に分解してから、getRequestParameter で値を取得します。
528         * こうしないとデータ自身にカンマを持っている場合に分解をミスる為です。
529         *
530         * @og.rev 3.2.2.0 (2003/05/31) 新規追加
531         * @og.rev 3.5.6.2 (2004/07/05) CommonTagSupport#getCSVParameter を使用
532         * @og.rev 6.2.5.1 (2015/06/12) CSV形式のkeys,vals引数(CSV引数)対応。
533         *
534         * @param       key キー情報(CSV形式)
535         */
536        public void setKeys( final String key ) {
537                keys = key;
538        }
539
540        /**
541         * 【TAG】HybsTimerTask に渡す為の値を、CSV形式で複数指定します。
542         *
543         * @og.tag
544         * キーに設定した値を、CSV形式で複数して出来ます。
545         * 指定順序は、キーと同じにしておいて下さい。
546         * 分解方法は、CSV変数を先に分解してから、getRequestParameter で値を取得します。
547         * こうしないとデータ自身にカンマを持っている場合に分解をミスる為です。
548         *
549         * @og.rev 3.2.2.0 (2003/05/31) 新規追加
550         * @og.rev 3.5.6.2 (2004/07/05) CommonTagSupport#getCSVParameter を使用
551         * @og.rev 6.2.5.1 (2015/06/12) CSV形式のkeys,vals引数(CSV引数)対応。
552         *
553         * @param       val 値(CSV形式)
554         */
555        public void setVals( final String val ) {
556                vals = val;
557        }
558
559        /**
560         * 【TAG】24時間制(YYMMDD)の開始時刻を設定します(初期値:000000)。
561         *
562         * @og.tag
563         * 指定時刻範囲内での実行のみ許可するように開始時刻を設定します。
564         * これは、タイマーで指定した間隔ごとにチェックを入れるので、チェック時間が
565         * 長い場合は、正確に開始時刻から始まるというものではありません。
566         * 初期値は、"000000" です。
567         *
568         * @og.rev 3.2.2.0 (2003/05/31) 新規追加
569         *
570         * @param       st 開始時刻
571         */
572        public void setStartTime( final String st ) {
573                startTime = nval( getRequestParameter( st ),startTime ) ;
574        }
575
576        /**
577         * 【TAG】24時間制(YYMMDD)の終了時刻を設定します(初期値:000000)。
578         *
579         * @og.tag
580         * 指定時刻範囲内での実行のみ許可するように終了時刻を設定します。
581         * これは、タイマーで指定した間隔ごとにチェックを入れるので、チェック時間が
582         * 長い場合は、正確に終了時刻で終了するというものではありません。
583         * (終了時刻を越えてからの新規実行はありません。)
584         * 初期値は、"000000" です。
585         *
586         * @og.rev 3.2.2.0 (2003/05/31) 新規追加
587         *
588         * @param       st 終了時刻
589         */
590        public void setStopTime( final String st ) {
591                stopTime = nval( getRequestParameter( st ),stopTime ) ;
592        }
593
594        /**
595         * HybsTimerTask オブジェクト配列より、DBTableModel を作成して返します。
596         * カラム名は、"TaskName","UniqKey","Comment","CreateTime","scheduledTime" です。
597         *
598         * @param   tasks       タイマータスクオブジェクト配列(可変長引数)
599         *
600         * @return      タイマータスクオブジェクトのテーブルモデル。 無ければ null
601         */
602        private DBTableModel makeDBTable( final HybsTimerTask... tasks ) {
603                if( tasks == null || tasks.length == 0 ) { return null; }               // 6.1.1.0 (2015/01/17) 可変長引数でもnullは来る。
604
605                final ResourceManager  resource  = getResource();
606
607                final String[] names = new String[] {
608                                                        "TaskName","UniqKey","Comment","CreateTime","scheduledTime"
609                                                };
610
611                final DBTableModel table = DBTableModelUtil.newDBTable();
612                table.init( names.length );
613                for( int i=0; i<names.length; i++ ) {
614                        final DBColumn dbColumn = resource.makeDBColumn( names[i] );
615                        table.setDBColumn( i,dbColumn );
616                }
617
618                for( int i=0; i<tasks.length; i++ ) {
619                        String[] clmVals = new String[names.length];
620                        clmVals[0] = tasks[i].getName() ;
621                        clmVals[1] = String.valueOf( tasks[i].getUniqKey() );
622                        clmVals[2] = tasks[i].getComment() ;
623                        clmVals[3] = HybsSystem.getDate( tasks[i].getCreateTime() );
624                        clmVals[4] = HybsSystem.getDate( tasks[i].scheduledExecutionTime() );
625                        table.addColumnValues( clmVals );
626                }
627
628                return table ;
629        }
630
631        /**
632         * 【TAG】(通常は使いません)結果のDBTableModelを、sessionに登録するときのキーを指定します
633         *              (初期値:HybsSystem#TBL_MDL_KEY[={@og.value HybsSystem#TBL_MDL_KEY}])。
634         *
635         * @og.tag
636         * 検索結果より、DBTableModelオブジェクトを作成します。これを、下流のviewタグ等に
637         * 渡す場合に、通常は、session を利用します。その場合の登録キーです。
638         * query タグを同時に実行して、結果を求める場合、同一メモリに配置される為、
639         * この tableId 属性を利用して、メモリ空間を分けます。
640         *              (初期値:HybsSystem#TBL_MDL_KEY[={@og.value HybsSystem#TBL_MDL_KEY}])。
641         *
642         * @param       id テーブルID (sessionに登録する時のID)
643         */
644        public void setTableId( final String id ) {
645                tableId = nval( getRequestParameter( id ),tableId );
646        }
647
648        /**
649         * 【TAG】キャッシュする場合のスコープ(local,request,page,session,application)を指定します(初期値:local)。
650         *
651         * @og.tag
652         * "local","request","page","session","application" が指定できます。
653         * "local" は、過去のバージョンとの互換性を保つ為の特殊な値です。
654         * 初期値は、"local" です。
655         *
656         * @og.rev 3.5.2.0 (2003/10/20) 新規作成
657         *
658         * @param       scp     スコープ
659         */
660        @Override
661        public void setScope( final String scp ) {
662                scope = nval( getRequestParameter( scp ),scope );
663        }
664
665        /**
666         * このオブジェクトの文字列表現を返します。
667         * 基本的にデバッグ目的に使用します。
668         *
669         * @return このクラスの文字列表現
670         * @og.rtnNotNull
671         */
672        @Override
673        public String toString() {
674                return ToString.title( this.getClass().getName() )
675                                .println( "VERSION"                             ,VERSION                )
676                                .println( "tableId"                             ,tableId                )
677                                .println( "command"                             ,command                )
678                                .println( "timerTask"                   ,timerTask              )
679                                .println( "name"                                ,name                   )
680                                .println( "comment"                             ,comment                )
681                                .println( "delay"                               ,delay                  )
682                                .println( "period"                              ,period                 )
683                                .println( "fixedDelay"                  ,fixedDelay             )
684                                .println( "uniqKey"                             ,uniqKey                )
685                                .println( "singleton"                   ,singleton              )
686                                .println( "FIXED_RATE_MIN_TIME" ,FIXED_RATE_MIN_TIME)
687                                .println( "TIMER_KEY"                   ,TIMER_KEY              )
688                                .println( "TIMERTASK_KEY"               ,TIMERTASK_KEY  )
689                                .println( "keys"                                ,keys                   )
690                                .println( "vals"                                ,vals                   )
691                                .println( "body"                                ,body                   )
692                                .println( "startTime"                   ,startTime              )
693                                .println( "stopTime"                    ,stopTime               )
694                                .println( "scope"                               ,scope                  )
695                                .println( "ERROR_SLEEP_TIME"    ,ERROR_SLEEP_TIME)
696                                .println( "Other..."    ,getAttributes().getAttribute() )
697                                .fixForm().toString() ;
698        }
699}