    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 java.util.concurrent.ConcurrentMap;
    019import java.util.concurrent.ConcurrentHashMap;
    020
    021import org.opengion.hayabusa.common.HybsSystemException;
    022import org.opengion.fukurou.util.ToString;
    023
    024/**
    025 * ValueMapTag にパラメーターを渡す為のタグクラスです。
    026 *
    027 * valueMap タグでは、特殊な 処理を行っており、そのMapで未使用のキーワードを
    028 * 出力するために、このタグを使用します。
    029 * valueMapParam の BODY部の文字列を、繰り返して、valueMap タグの未使用キーに適用します。
    030 * キーワードは、XXXX 部分を、valueMap の未使用キーに変換します。
    031 * キーワードは、YYYY 部分は、grpKeyClm を使用した場合に、置換される一連のｸﾞﾙｰﾌﾟｶﾗﾑ名を指定します。
    032 *
    033 * このタグは、ValueMapTag の内部からしか、使用できません。
    034 *
    035 * @og.formSample
    036 * ●形式：
    037 *     &lt;og:valueMapParam clsKey="CLASS_KEY" &gt;
    038 *          &lt;tr&gt;&lt;td class="LBL"&gt;{&#064;$XXXX 1}&lt;/td&gt;&lt;td&gt;{&#064;$XXXX 2}&lt;/td&gt;&lt;td&gt;{&#064;$XXXX 3}&lt;/td&gt;&lt;/tr&gt;
    039 *     &lt;/og:valueMapParam
    040 *
    041 * ●body：あり(EVAL_BODY_BUFFERED:BODYを評価し、{&#064;XXXX} を解析します)
    042 *
    043 * ●Tag定義：
    044 *   &lt;og:valueMapParam
    045 *       noneClassKey       【TAG】繰返し対象が無い場合に、display:none; を出力する class 属性名(初期値:null)
    046 *       restMarkClm        【TAG】繰返し対象が無い場合に、DBTableModelにマークするカラム名(初期値:null)
    047 *       restMarkVal        【TAG】繰返し対象が無い場合に、DBTableModelにマークする値(初期値:null)
    048 *       grpKeyClm          【TAG】繰返し対象が無い場合に、YYYYｷｰﾜｰﾄﾞに置換するｸﾞﾙｰﾌﾟｶﾗﾑ名を指定します(初期値:null) 6.9.9.0 (2018/08/20)
    049 *       caseKey            【TAG】このタグ自体を利用するかどうかの条件キーを指定します(初期値:null)
    050 *       caseVal            【TAG】このタグ自体を利用するかどうかの条件値を指定します(初期値:null)
    051 *       caseNN             【TAG】指定の値が、null/ゼロ文字列 でない場合(Not Null=NN)は、このタグは使用されます(初期値:判定しない)
    052 *       caseNull           【TAG】指定の値が、null/ゼロ文字列 の場合は、このタグは使用されます(初期値:判定しない)
    053 *       caseIf             【TAG】指定の値が、true/TRUE文字列の場合は、このタグは使用されます(初期値:判定しない)
    054 *       debug              【TAG】デバッグ情報を出力するかどうか[true/false]を指定します(初期値:false)
    055 *   &gt;   ... Body ...
    056 *   &lt;/og:valueMapParam&gt;
    057 *
    058 * ●使用例
    059 *     &lt;og:valueMap ･････ &gt;
    060 *          ･････
    061 *         &lt;table&gt;
    062 *         &lt;og:valueMapParam noneClassKey="AddTokens"  grpKeyClm="TKN_GRP"&gt;
    063 *               &lt;tr&gt;&lt;td class="LBL"&gt;{&#064;$XXXX 1}&lt;/td&gt;&lt;td&gt;{&#064;&#064;YYYY*}&lt;/td&gt;&lt;td&gt;{&#064;$XXXX 3}&lt;/td&gt;&lt;/tr&gt;
    064 *         &lt;/og:valueMapParam&gt;
    065 *         &lt;/table&gt;
    066 *     &lt;/og:valueMap
    067 *
    068 *     grpKeyClmにTKN_GRP を指定することで、同一共通ﾄｰｸﾝを横に並べる
    069 *     YYYYに、TKN_GRP が割りあたり、{&#064;&#064;YYYY*} に、共通ﾄｰｸﾝとﾏｯﾁする場合に、横に並ぶ。
    070 *
    071 * @og.rev 6.7.8.0 (2017/04/21) 新規作成
    072 * @og.group ファイル出力
    073 *
    074 * @version  6.7
    075 * @author   Kazuhiko Hasegawa
    076 * @since    JDK8.0,
    077 */
    078public class ValueMapParamTag extends CommonTagSupport {
    079        /** このプログラムのVERSION文字列を設定します。   {@value} */
    080        private static final String VERSION = "6.9.9.0 (2018/08/20)" ;
    081        private static final long serialVersionUID = 699020180820L ;
    082
    083        /** ValueMapParamTag クラスのキーワードの enum */
    084        public static enum VMP_KEYS {
    085                NONE_CLS_KEY    ,                               // noneClassKey のキーワード
    086                REST_MARK_CLM   ,                               // restMarkClm のキーワード
    087                REST_MARK_VAL   ,                               // restMarkVal のキーワード
    088                REST_CHANGE_KEY ,                               // ValueMapParamTag の文字列を置き換えるタグ名
    089                GRP_KEY_CLM             ,                               // 6.9.9.0 (2018/08/20) YYYYｷｰﾜｰﾄﾞに置換するｸﾞﾙｰﾌﾟｶﾗﾑ名
    090                BODY_VAL                ;                               // このタグのBODY部の文字列(未変換)
    091        };
    092
    093        // 各種設定情報を、管理するMapオブジェクト。これを、上位の ValueMapTag に渡す。
    094        private final ConcurrentMap<VMP_KEYS,String> paramMap = new ConcurrentHashMap<>();
    095
    096        private static final String REST_CHANGE_VAL = "h_REST_CHANGE_VAL" ;
    097
    098        /**
    099         * デフォルトコンストラクター
    100         *
    101         */
    102        public ValueMapParamTag() { super(); }          // これも、自動的に呼ばれるが、空のメソッドを作成すると警告されるので、明示的にしておきます。
    103
    104        /**
    105         * Taglibの開始タグが見つかったときに処理する doStartTag() を オーバーライドします。
    106         *
    107         * @return      後続処理の指示
    108         */
    109        @Override
    110        public int doStartTag() {
    111                return useTag()
    112                                        ? EVAL_BODY_BUFFERED            // Body を評価する。( extends BodyTagSupport 時)
    113                                        : SKIP_BODY;                            // Body を評価しない
    114        }
    115
    116        /**
    117         * Taglibのタグ本体を処理する doAfterBody() を オーバーライドします。
    118         *
    119         * @return      後続処理の指示(SKIP_BODY)
    120         */
    121        @Override
    122        public int doAfterBody() {
    123                putMap( VMP_KEYS.BODY_VAL , getBodyRawString() );               // {&#064;XXXX}を変換しない生のBODY文を設定します
    124
    125                return SKIP_BODY ;
    126        }
    127
    128        /**
    129         * Taglibの終了タグが見つかったときに処理する doEndTag() を オーバーライドします。
    130         *
    131         * @return      後続処理の指示
    132         */
    133        @Override
    134        public int doEndTag() {
    135                debugPrint();
    136
    137                if( useTag() ) {
    138                        final ValueMapTag vm_Tag = (ValueMapTag)findAncestorWithClass( this,ValueMapTag.class );
    139                        if( vm_Tag == null ) {
    140                                final String errMsg = "<b>" + getTagName() + "タグは、ValueMapTagの内側(要素)に記述してください。</b>";
    141                                throw new HybsSystemException( errMsg );
    142                        }
    143
    144                        jspPrint( "{@" + REST_CHANGE_VAL + "}" );                               // ValueMapParamTag を置き換えます。
    145                        putMap( VMP_KEYS.REST_CHANGE_KEY , REST_CHANGE_VAL );   // Map に入れて、ValueMapTag に渡します。
    146
    147                        vm_Tag.setParam( paramMap );
    148                }
    149                return EVAL_PAGE ;
    150        }
    151
    152        /**
    153         * タグリブオブジェクトをリリースします。
    154         * キャッシュされて再利用されるので、フィールドの初期設定を行います。
    155         *
    156         */
    157        @Override
    158        protected void release2() {
    159                super.release2();
    160                paramMap.clear() ;
    161        }
    162
    163        /**
    164         * 内部の paramMap に、登録します。
    165         *
    166         * ConcurrentMap は、nullのキーも値も設定できないので、val のnull判定処理が
    167         * 必要ですが、各Map登録時に行うのではなく、ここに集約します。
    168         * val がnull か、空文字列の場合は、Map にセットしません。
    169         *
    170         * @param   key paramMap に、登録するVMP_KEYS enum のキー
    171         * @param   val paramMap に、登録する値。
    172         */
    173        private void putMap( final VMP_KEYS key , final String val ) {
    174                if( val != null && !val.isEmpty() ) {
    175                        paramMap.put( key,val );
    176                }
    177        }
    178
    179        /**
    180         * 【TAG】繰返し対象が無い場合に、display:none; を出力する class 名を指定します(初期値:null)。
    181         *
    182         * @og.tag
    183         * valueMap タグで、繰返し処理が無い場合に、このclassキーに対して、display:none; を出力します。
    184         * null (未指定) の場合は、display:none; を出力しません。
    185         *
    186         * @param   clsKey display:none; を出力する class 名
    187         */
    188        public void setNoneClassKey( final String clsKey ) {
    189                putMap( VMP_KEYS.NONE_CLS_KEY , getRequestParameter( clsKey ) );
    190        }
    191
    192        /**
    193         * 【TAG】繰返し対象が無い場合に、DBTableModelにマークするカラム名(初期値:null)。
    194         *
    195         * @og.tag
    196         * valueMap タグで、繰返し処理が無い場合に、DBTableModel の指定のカラムに、
    197         * マーク(値の設定)を行うカラムIDを指定します。
    198         * 例えば、クラス属性に指定しているカラムの値を書き換えれば、対象無しとして
    199         * 追加されたデータに、色づけなどを行うことが出来ます。
    200         *
    201         * @param   clm DBTableModelにマークするカラム名
    202         */
    203        public void setRestMarkClm( final String clm ) {
    204                putMap( VMP_KEYS.REST_MARK_CLM , getRequestParameter( clm ) );
    205        }
    206
    207        /**
    208         * 【TAG】繰返し対象が無い場合に、DBTableModelにマークする値(初期値:null)。
    209         *
    210         * @og.tag
    211         * valueMap タグで、繰返し処理が無い場合に、DBTableModel の指定のカラムに、
    212         * マーク(値の設定)を行うカラムIDに指定する値を指定します。
    213         * 例えば、クラス属性に指定しているカラムの値を書き換えれば、対象無しとして
    214         * 追加されたデータに、色づけなどを行うことが出来ます。
    215         *
    216         * @param   val DBTableModelにマークする値
    217         */
    218        public void setRestMarkVal( final String val ) {
    219                putMap( VMP_KEYS.REST_MARK_VAL , getRequestParameter( val ) );
    220        }
    221
    222        /**
    223         * 【TAG】繰返し対象が無い場合に、YYYYｷｰﾜｰﾄﾞに置換するｸﾞﾙｰﾌﾟｶﾗﾑ名を指定します(初期値:null)。
    224         *
    225         * @og.tag
    226         * valueMap タグで、繰返し処理が無い場合に、DBTableModel の指定のカラムを
    227         * 利用して、YYYYｷｰﾜｰﾄﾞと置換します。
    228         * これは、ｸﾞﾙｰﾌﾟｷｰﾜｰﾄﾞが同一のｶﾗﾑを、横持ちに順番に表示させる場合に、有効です。
    229         * 初期値は、未設定なので、YYYYｷｰﾜｰﾄﾞは、置換されずに、そのまま残ります。
    230         *
    231         * @og.rev 6.9.9.0 (2018/08/20) YYYYｷｰﾜｰﾄﾞに置換するｸﾞﾙｰﾌﾟｶﾗﾑ名
    232         *
    233         * @param   clm YYYYｷｰﾜｰﾄﾞに置換するｸﾞﾙｰﾌﾟｶﾗﾑ名
    234         */
    235        public void setGrpKeyClm( final String clm ) {
    236                putMap( VMP_KEYS.GRP_KEY_CLM , getRequestParameter( clm ) );
    237        }
    238
    239        /**
    240         * このオブジェクトの文字列表現を返します。
    241         * 基本的にデバッグ目的に使用します。
    242         *
    243         * @return このクラスの文字列表現
    244         * @og.rtnNotNull
    245         */
    246        @Override
    247        public String toString() {
    248                final ToString toStr = ToString.title( this.getClass().getName() );
    249
    250                paramMap.forEach( (k,v) -> toStr.println( k.name() , v ) );
    251
    252                return toStr.fixForm().toString() ;
    253
    254        //      return ToString.title( this.getClass().getName() )
    255        //                      .println( "VERSION"             ,VERSION        )
    256        //                      .println( "clsKey"              ,clsKey         )
    257        //                      .println( "value"               ,value          )
    258        //                      .println( "Other..."    ,getAttributes().getAttribute() )
    259        //                      .fixForm().toString() ;
    260        }
    261}