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.common;
017    
018    import java.io.Serializable;
019    import java.sql.Connection;
020    import java.sql.PreparedStatement;
021    import java.sql.SQLException;
022    import java.util.ArrayList;
023    import java.util.Arrays;
024    import java.util.Comparator;
025    import java.util.HashMap;
026    import java.util.List;
027    import java.util.Map;
028    import java.util.Locale;
029    
030    import javax.servlet.http.HttpSession;
031    
032    import org.opengion.fukurou.db.ConnectionFactory;
033    import org.opengion.fukurou.util.Cleanable;
034    import org.opengion.fukurou.util.Closer;
035    import org.opengion.fukurou.util.LogWriter;
036    import org.opengion.fukurou.db.DBSimpleTable;
037    
038    /**
039     * Webアプリケーション全体で使用して?オブジェクト類?ト?タルの管?ラスです?
040     *
041     * SystemManager は?
042     *
043     *              session オブジェクト?管?アクセス?開放
044     *
045     * の作業を行います?
046     *
047     * 上記?クラス(staticメソ?)へのアクセスは、もちろん直接呼び出して
048     * 操作することも可能ですが、サーバ?のクリーンシャ??ン時やセ?ョンの
049     * 開放時?初期化??ど、ある種の統合的なトリガを受けて?係するクラスに
050     * イベントを伝えるよ?することで、Webアプリケーションサーバ?との?取り?
051     * ??管?る目?作?されて?す?
052     *
053     * @og.group 初期?
054     *
055     * @version  4.0
056     * @author   Kazuhiko Hasegawa
057     * @since    JDK5.0,
058     */
059    public final class SystemManager {
060            // 3.1.0.0 (2003/03/20) Hashtable を使用して??で?同期でも構わな??を?HashMap に置換え?
061            private static final Map<String,UserSummary> map = new HashMap<String,UserSummary>( HybsSystem.BUFFER_MIDDLE );
062    
063            /** 4.0.0 (2005/01/31) Cleanable インターフェースを実?たオブジェクトを管?ます?  */
064            private static final List<Cleanable> clearList = new ArrayList<Cleanable>() ;
065    
066            /** 4.3.6.2 (2009/04/15) Context終?のみclear()され?Cleanable ブジェクトを管?ます?  */
067            private static final List<Cleanable> contextClearList = new ArrayList<Cleanable>() ;
068    
069            // 4.1.0.0 (2008/01/11) GE12クリア用
070            // 4.3.6.6 (2009/05/15) ENGINE_INFOは削除しな?
071            /** エンジン個別(SYSTEM_ID='個別' KBSAKU='0' CONTXT_PATH='自身')パラメータの?削除のクエリー       {@value}        */
072            private static final String DEL_SYS = "DELETE FROM GE12 WHERE SYSTEM_ID=? AND KBSAKU='0' AND CONTXT_PATH=? AND PARAM_ID != 'ENGINE_INFO'";
073    
074            /**
075             *  ?ォルトコンストラクターをprivateにして?
076             *  オブジェクト?生?をさせな??する?
077             *
078             */
079            private SystemManager() {
080            }
081    
082            /**
083             * session を記録します?
084             *
085             * 管??権限で、強制ログアウトさせる場合などに、使用します?
086             * Servlet 2.1 では、HttpSessio#getSessionContext() より取り出した
087             * HttpSessionContextのgetSession(java.lang.String sessionId) で
088             * すべての session を取り?せました?Deprecated になりました?
089             * セキュリ?ー上?好ましくな???す?で,注意して使用してください?
090             * common\session_init.jsp より登録しま?
091             *
092             * @og.rev 5.5.9.1 (2012/12/07) セ?ョン作?時に、規定?キーでセ?ョンIDを保存しておく?
093             *
094             * @param   session Httpセ?ョン
095             */
096            public static void addSession( final HttpSession session ) {
097                    String sessionID = session.getId();
098    
099                    UserSummary userInfo = (UserSummary)session.getAttribute( HybsSystem.USERINFO_KEY );
100                    if( userInfo != null ) {
101                            synchronized( map ) {
102                                    map.put( sessionID,userInfo );
103                            }
104                            session.setAttribute( HybsSystem.SESSION_KEY, sessionID );              // 5.5.9.1 (2012/12/07) セ?ョンIDを保?
105                    }
106            }
107    
108            /**
109             * session を削除します?
110             *
111             * 管??権限で、強制ログアウトさせる場合などに、使用します?
112             * Servlet 2.1 では、HttpSessio#getSessionContext() より取り出した
113             * HttpSessionContextのgetSession(java.lang.String sessionId) で
114             * すべての session を取り?せました?Deprecated になりました?
115             * セキュリ?ー上?好ましくな???す?で,注意して使用してください?
116             *
117             * @og.rev 5.5.9.1 (2012/12/07) セ?ョン作?時に登録した規定?キーで userInfo を削除します?
118             * @og.rev 5.6.6.0 (2013/07/05) セ?ョンの Attribute に SESSION_KEY で登録して? sessionID も削除します?
119             *
120             * @param   session Httpセ?ョン
121             */
122    //      public static void removeSession( final String sessionID ) {
123            public static void removeSession( final HttpSession session ) {
124    
125                    String sessionID = (String)session.getAttribute( HybsSystem.SESSION_KEY );      // 5.5.9.1 (2012/12/07) セ?ョンIDを取り??
126    
127                    // 5.6.6.0 (2013/07/05) userInfo の map からの削除とuserInfo の clear を簡??
128                    synchronized( map ) {
129                            UserSummary userInfo = map.remove( sessionID );
130                            if( userInfo != null ) { userInfo.clear(); }
131                    }
132    
133    //              final UserSummary userInfo ;
134    //              synchronized( map ) {
135    //                      userInfo = map.remove( sessionID );
136    //              }
137    //              if( userInfo != null ) { userInfo.clear(); }
138    
139                    // 5.6.6.0 (2013/07/05) セ?ョンの Attribute に SESSION_KEY で登録して? sessionID も削除します?
140                    session.removeAttribute( HybsSystem.USERINFO_KEY );
141                    session.removeAttribute( HybsSystem.SESSION_KEY );
142            }
143    
144            /**
145             * すべてのシス?にログイン中のUserSummary オブジェクトを取得します?
146             *
147             * キーは、UserSummary の Attribute も含めた値が使用できます?
148             * 引数のキーは、?部で大?に変換された?ち、?部キーとして使用されます?
149             *
150             * @og.rev 4.0.0.0 (2005/01/31) ?ロジ?大?更
151             * @og.rev 5.6.6.0 (2013/07/05) Comparator の作り方を?簡?します?キーの??も増やします?
152             *
153             * @param   key ソートするキー?を指?
154             * @param   direction ソートする方向[true:??/false:降?]
155             *
156             * @return      ログイン中のオブジェク?
157             */
158            public static UserSummary[] getRunningUserSummary( final String key,final boolean direction ) {
159                    final UserSummary[] users ;
160                    synchronized( map ) {
161                            users = map.values().toArray( new UserSummary[map.size()] );
162                    }
163    
164                    if( key != null ) {
165    //                      Comparator<UserSummary> comp = getUserSummaryComparator( key,direction );
166                            Comparator<UserSummary> comp = new ATTRI_Comparator( key.toUpperCase( Locale.JAPAN ),direction );
167                            Arrays.sort( users,comp );
168                    }
169    
170                    return users ;
171            }
172    
173            /**
174             * シス?にログイン中の、すべてのセ?ョン数を?取得します?
175             *
176             * ちなみに、不正な??タが存在した場合?、ここでMapから削除しておきます?
177             *
178             * @og.rev 4.0.0.0 (2005/01/31) 新規作?
179             *
180             * @return ログイン中の有効なすべてのセ?ョン数
181             */
182            public static int getRunningCount() {
183                    final int rtnSize;
184                    synchronized( map ) {
185                            String[] keys = map.keySet().toArray( new String[map.size()] );
186                            for( int i=0; i<keys.length; i++ ) {
187                                    if( map.get( keys[i] ) == null ) {
188                                            map.remove( keys[i] );
189                                    }
190                            }
191                            rtnSize = map.size() ;
192                    }
193    
194                    return rtnSize;
195            }
196    
197            /**
198             * contextDestroyed 時に、すべてのセ?ョンを?invalidate()します?
199             * 注意:キャ?ュで?管?て?セ?ョンが?すべて無効化されてしま?す?
200             * よって、?部にセ?ョンを管?なくなったため?invalidate() もできません?
201             * 不?合が出るかもしれません?
202             *
203             * @og.rev 3.5.2.1 (2003/10/27) 新規作?
204             * @og.rev 4.0.0.0 (2005/01/31) セ?ョン ?UserSummary に変更
205             */
206            static void sessionDestroyed() {
207                    final UserSummary[] users ;
208                    synchronized( map ) {
209                            users = map.values().toArray( new UserSummary[map.size()] );
210                            map.clear();
211                    }
212    
213                    for( int i=0; i<users.length; i++ ) {
214                            users[i].clear();
215                    }
216                    System.out.println( "  [" + users.length + "] Session Destroyed " );
217            }
218    
219            /**
220             * 初期化したいオブジェクトを登録します?
221             * オブジェクト?、Cleanable インターフェースを実?ておく?があります?
222             * 実際に、clear() する場合?、ここで登録した全てのオブジェクト? clear()
223             * メソ?が呼び出されます?
224             *
225             * @og.rev 4.0.0.0 (2005/01/31) 新規作?
226             * @og.rev 4.3.6.2 (2009/04/15) コン?スト終?のみのclear()対?
227             *
228             * @param obj インターフェースの実?
229             */
230            public static void addCleanable( final Cleanable obj ) {
231    //              synchronized( clearList ) {
232    //                      clearList.add( obj );
233    //              }
234                    addCleanable( obj, false );
235            }
236    
237            /**
238             * 初期化したいオブジェクトを登録します?
239             * オブジェクト?、Cleanable インターフェースを実?ておく?があります?
240             * 実際に、clear() する場合?、ここで登録した全てのオブジェクト? clear()
241             * メソ?が呼び出されます?
242             *
243             * @og.rev 4.0.0.0 (2005/01/31) 新規作?
244             * @og.rev 4.3.6.2 (2009/04/15) コン?スト終?のみのclear()対?
245             *
246             * @param obj インターフェースの実?
247             * @param flag trueの場合?コン?スト停止時?みclear()を呼び出?
248             */
249            public static void addCleanable( final Cleanable obj, final boolean flag ) {
250                    if( flag ) {
251                            synchronized( contextClearList ) {
252                                    contextClearList.add( obj );
253                            }
254                    }
255                    else {
256                             synchronized( clearList ) {
257                                    clearList.add( obj );
258                             }
259                    }
260            }
261    
262            /**
263             * addCleanable( final Cleanable ) で登録したすべてのオブジェクトを初期化します?
264             * 処??、Cleanable インターフェースの clear()メソ?を?次呼び出します?
265             *
266             * @og.rev 4.0.0.0 (2005/01/31) 新規作?
267             * @og.rev 4.3.6.2 (2009/04/15) コン?スト終?のみのclear()対?
268             *
269             * @param       flag 完?終?に、true
270             */
271            public static void allClear( final boolean flag ) {
272                    final Cleanable[] clr ;
273                    synchronized( clearList ) {
274                            clr = clearList.toArray( new Cleanable[clearList.size()] );
275                            if( flag ) { clearList.clear() ; }              // contextDestroyed の場合?み実?
276                    }
277                    // 登録の??で処?て?ます?
278                    for( int i=clr.length-1; i>=0; i-- ) {
279                            clr[i].clear();
280                    }
281    
282                    // コン?スト停止時?みclear()
283                    if( flag ) {
284                            final Cleanable[] clr2 ;
285                            synchronized( contextClearList ) {
286                                    clr2 = contextClearList.toArray( new Cleanable[contextClearList.size()] );
287                                    contextClearList.clear();
288                            }
289                            // 登録の??で処?て?ます?
290                            for( int i=clr2.length-1; i>=0; i-- ) {
291                                    clr2[i].clear();
292                            }
293                    }
294            }
295    
296            /**
297             * GE12からCONTXT PATHをhost:port/context/で登録して?物を削除します?
298             * (web.xmlにTOMCAT_PORTを指定した?合に上記CONTEXT_PATHで登録されま?
299             *
300             * @og.rev 4.1.0.0 (2007/12/26) 新規作?
301             * @og.rev 5.5.4.5 (2012/07/27) 初期起動時のDB接続?は、RESOURCE_DBID とする?
302             */
303            protected static void clearGE12() {
304                    String HOST_URL                 = HybsSystem.sys( "HOST_URL" );
305                    String RESOURCE_DBID    = HybsSystem.sys( "RESOURCE_DBID" );    // 5.5.4.5 (2012/07/27) 初期起動時のDB接続?
306                    if( HOST_URL != null && !"**".equals( HOST_URL ) ) {
307                            Connection connection = null;
308                            PreparedStatement pstmt = null;
309                            try {
310    //                              connection = ConnectionFactory.connection( null, null );
311                                    connection = ConnectionFactory.connection( RESOURCE_DBID, null );       // 5.5.4.5 (2012/07/27) 初期起動時のDB接続?は、RESOURCE_DBID とする?
312                                    pstmt = connection.prepareStatement( DEL_SYS );
313                                    pstmt.setString( 1, HybsSystem.sys( "SYSTEM_ID" ) );
314                                    pstmt.setString( 2, HOST_URL );
315                                    int delCnt = pstmt.executeUpdate();
316                                    connection.commit();
317                                    System.out.println( HOST_URL + " DELETE FROM GE12[" + delCnt + "]" );
318                            } catch (HybsSystemException e) {
319                                    LogWriter.log( e );
320                            } catch (SQLException e) {
321                                    Closer.rollback( connection );
322                                    LogWriter.log( e );
323                            }
324                            finally {
325                                    Closer.stmtClose( pstmt );
326                                    ConnectionFactory.close( connection, null );
327                            }
328                    }
329            }
330    
331            /**
332             * soffice.binをkillする処?callします?
333             *
334             * @og.rev 4.3.0.0 (2008/07/18) 新規作?
335             * @og.rev 5.2.2.0 (2010/11/01) 循環参?解消?ため、SystemManager から ProcessFactory へ移?
336             */
337    //      protected static void sofficeKill() {
338    //              System.out.println("Kill all soffice.bin");
339    //              ProcessFactory.kill();
340    //      }
341    
342            // deleteGUIAccessInfo() メソ?でしか使用しな??定数宣?
343            private static final int C_DEL_SYSTEM_ID                = 0;
344            private static final int C_DEL_DYSET                    = 1;
345    
346            /**
347             * アクセス統計テーブル(GE15)の再編成を行います?
348             * ??タの保存期間につ?は、シス?リソースのACCESS_TOKEI_ALIVE_DAYSで?します?
349             * ??タの作?された日時を基準として、上記?期間よりも古?ータは、物?除されます?
350             * ACCESS_TOKEI_ALIVE_DAYSが指定されて???合???タの削除は行われません?
351             *
352             * @og.rev 5.0.2.0 (2009/11/01) 新規作?
353             * @og.rev 5.5.5.1 (2012/08/07) リソース系DBID 付け忘れ対?
354             */
355            protected static void deleteGUIAccessInfo() {
356                    String aliveDays = HybsSystem.sys( "ACCESS_TOKEI_ALIVE_DAYS" );
357                    if( aliveDays == null || aliveDays.length() == 0 ) {
358                            return;
359                    }
360                    String delBaseDate = HybsSystem.getDate( HybsSystem.getDate( "yyyyMMdd" ), -1 * Integer.valueOf( aliveDays ) );
361    
362                    String[] names = new String[] { "SYSTEM_ID","DYSET" };
363                    String[] values = new String[names.length];
364                    values[C_DEL_SYSTEM_ID          ] = HybsSystem.sys( "SYSTEM_ID" );
365                    values[C_DEL_DYSET                      ] = delBaseDate + "000000";
366    
367                    String RESOURCE_DBID    = HybsSystem.sys( "RESOURCE_DBID" );    // 5.5.5.1 (2012/08/07) リソース系DBID 付け忘れ対?
368                    DBSimpleTable dbTable = new DBSimpleTable( names );
369                    dbTable.setApplicationInfo( null );
370                    dbTable.setConnectionID( RESOURCE_DBID );       // 5.5.5.1 (2012/08/07)
371                    dbTable.setTable( "GE15" );
372                    dbTable.setWhere( "SYSTEM_ID = [SYSTEM_ID] and DYSET <= [DYSET]" );
373    
374                    boolean okFlag = false;
375                    try {
376                            dbTable.startDelete();
377                            dbTable.execute( values );
378                            okFlag = true;
379                    }
380                    catch (SQLException ex) {
381                            LogWriter.log( "  アクセス統計テーブル削除時にエラーが発生しました" );
382                            LogWriter.log( ex.getMessage() );
383                    }
384                    finally {
385                            int cnt = dbTable.close( okFlag );
386                            System.out.println();
387                            System.out.println( "  アクセス統計テーブルから、[" + cnt + "]件、削除しました? );
388                    }
389            }
390    
391            /**
392             * UserSummary の??キーに対応した?目をソートす?Comparator を返します?
393             *
394             * キーは、JNAME,ID,IPADDRESS,LOGINTIME の?のどれかです?
395             *
396             * @og.rev 3.8.5.3 (2006/08/07) 新規追?
397             * @og.rev 5.6.6.0 (2013/07/05) Comparator の作り方を?簡?します?そ?ため、??
398             *
399             * @param       key     ソートするキー?を指?
400             * @param       direction       ソートする方向[true:??/false:降?]
401             *
402             * @return  ??キーに対応した?目をソートす?Comparator
403             */
404    //      public static Comparator<UserSummary> getUserSummaryComparator( final String key,final boolean direction ) {
405    //              if( "JNAME,ID,ROLES,IPADDRESS,LOGINTIME".indexOf( key ) < 0 ) {
406    //                      String errMsg = "ソートキーには、JNAME,ID,ROLES,IPADDRESS,LOGINTIME 以外??できません?
407    //                                              + " Key=" + key ;
408    //                      throw new HybsSystemException( errMsg );
409    //              }
410    //
411    //              Comparator<UserSummary> comp = null;
412    //
413    //              if( "JNAME".equals( key ) ) {
414    //                      comp = new JNAME_Comparator( direction );
415    //              }
416    //              else if( "ID".equals( key ) ) {
417    //                      comp = new ID_Comparator( direction );
418    //              }
419    //              else if( "ROLES".equals( key ) ) {
420    //                      comp = new ROLES_Comparator( direction );
421    //              }
422    //              else if( "IPADDRESS".equals( key ) ) {
423    //                      comp = new IPADDRESS_Comparator( direction );
424    //              }
425    //              else if( "LOGINTIME".equals( key ) ) {
426    //                      comp = new LOGINTIME_Comparator( direction );
427    //              }
428    //
429    //              return comp ;
430    //      }
431    
432            /**
433             * UserSummary の Attribute で比??Comparator ?クラスの定義?
434             *
435             * key が?Attribute のキーになりますが、使用するのは、大?化してからです?
436             *
437             * @og.rev 5.6.6.0 (2013/07/05) 新規追?
438             */
439            private static final class ATTRI_Comparator implements Comparator<UserSummary>, Serializable {
440                    private static final long serialVersionUID = 5660 ;             // 5.6.6.0 (2013/07/05)
441                    private final String  key  ;
442                    private final boolean direct ;
443    
444                    /**
445                     * ソート?方向を引数にとるコンストラクタ?
446                     *
447                     * @og.rev 5.6.6.0 (2013/07/05) 新規追?
448                     *
449                     * @param       direction       ソート?方向[true:??/false:降?]
450                     */
451                    public ATTRI_Comparator( final String key,final boolean direction ) {
452                            this.key = key;
453                            direct   = direction;
454                    }
455    
456                    /**
457                     * getAttribute 比?ソ?
458                     * インタフェース Comparable の 実?す?
459                     *
460                     * キーとして、getAttribute( String ) の取得結果を使用する為、null もあり得ます?そ?場合?equals 整合?は取れませんが?
461                     * 処?しては、正常に動作するよ?しておきます?つまり?null はもっとも小さ??とし?比?象がともに null の
462                     * 場合?、同じと判断します?
463                     *
464                     * @og.rev 5.6.6.0 (2013/07/05) 新規追?
465                     *
466                     * @param o1 比?象の??のオブジェク?
467                     * @param o2 比?象の 2 番目のオブジェク?
468                     * @return      ??の引数?2 番目の引数より小さ??合???整数、両方が等し??合? 0、最初?引数?2 番目の引数より大きい場合?正の整数
469                     */
470                    public int compare( final UserSummary o1, final UserSummary o2 ) {
471                            String key1 = o1.getAttribute( key );
472                            String key2 = o2.getAttribute( key );
473    
474                            int rtn ;
475                            if( key1 == null && key2 == null )      { rtn =  0; }
476                            else if( key1 == null )                         { rtn = -1; }
477                            else if( key2 == null )                         { rtn =  1; }
478                            else                                                            { rtn = key1.compareTo( key2 ) ; }
479    
480                            return ( direct ) ? rtn : -rtn;                 // マイナス 0 が気になるが、まあ?良しとする?
481                    }
482            }
483    
484    //      /**
485    //       * JNAME で比??Comparator ?クラスの定義?
486    //       *
487    //       * @og.rev 4.0.0.0 (2006/09/31) 新規追?
488    //       * @og.rev 5.6.6.0 (2013/07/05) ATTRI_Comparator に統合?ため、?
489    //       */
490    //      private static final class JNAME_Comparator implements Comparator<UserSummary>, Serializable {
491    //              private static final long serialVersionUID = 4000 ;     // 4.0.0 (2006/09/31)
492    //              private final boolean direct ;
493    //
494    //              /**
495    //               * ソート?方向を引数にとるコンストラクタ?
496    //               *
497    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
498    //               *
499    //               * @param       direction       ソート?方向[true:??/false:降?]
500    //               */
501    //              public JNAME_Comparator( final boolean direction ) {
502    //                      direct = direction;
503    //              }
504    //
505    //              /**
506    //               * getJname 比?ソ?
507    //               * インタフェース Comparable の 実?す?
508    //               *
509    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
510    //               *
511    //               * @param o1 比?象の??のオブジェク?
512    //               * @param o2 比?象の 2 番目のオブジェク?
513    //               * @return      ??の引数?2 番目の引数より小さ??合???整数、両方が等し??合? 0、最初?引数?2 番目の引数より大きい場合?正の整数
514    //               */
515    //              public int compare( final UserSummary o1, final UserSummary o2 ) {
516    //                      String key1 = o1.getJname();
517    //                      String key2 = o2.getJname();
518    //                      return ( direct ) ? key1.compareTo( key2 ) : key2.compareTo( key1 );
519    //              }
520    //      }
521    //
522    //      /**
523    //       * ID で比??Comparator ?クラスの定義?
524    //       *
525    //       * @og.rev 4.0.0.0 (2006/09/31) 新規追?
526    //       * @og.rev 5.6.6.0 (2013/07/05) ATTRI_Comparator に統合?ため、?
527    //       */
528    //      private static final class ID_Comparator implements Comparator<UserSummary>, Serializable {
529    //              private static final long serialVersionUID = 4000 ;     // 4.0.0 (2006/09/31)
530    //              private final boolean direct ;
531    //
532    //              /**
533    //               * ソート?方向を引数にとるコンストラクタ?
534    //               *
535    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
536    //               *
537    //               * @param       direction       ソート?方向[true:??/false:降?]
538    //               */
539    //              public ID_Comparator( final boolean direction ) {
540    //                      direct = direction;
541    //              }
542    //
543    //              /**
544    //               * getUserID 比?ソ?
545    //               * インタフェース Comparable の 実?す?
546    //               *
547    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
548    //               *
549    //               * @param o1 比?象の??のオブジェク?
550    //               * @param o2 比?象の 2 番目のオブジェク?
551    //               * @return      ??の引数?2 番目の引数より小さ??合???整数、両方が等し??合? 0、最初?引数?2 番目の引数より大きい場合?正の整数
552    //               */
553    //              public int compare( final UserSummary o1, final UserSummary o2 ) {
554    //                      String key1 = o1.getUserID();
555    //                      String key2 = o2.getUserID();
556    //                      return ( direct ) ? key1.compareTo( key2 ) : key2.compareTo( key1 );
557    //              }
558    //      }
559    //
560    //      /**
561    //       * ROLES で比??Comparator ?クラスの定義?
562    //       *
563    //       * @og.rev 4.0.0.0 (2006/09/31) 新規追?
564    //       * @og.rev 5.6.6.0 (2013/07/05) ATTRI_Comparator に統合?ため、?
565    //       */
566    //      private static final class ROLES_Comparator implements Comparator<UserSummary>, Serializable {
567    //              private static final long serialVersionUID = 4000 ;     // 4.0.0 (2006/09/31)
568    //              private final boolean direct ;
569    //
570    //              /**
571    //               * ソート?方向を引数にとるコンストラクタ?
572    //               *
573    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
574    //               *
575    //               * @param       direction       ソート?方向[true:??/false:降?]
576    //               */
577    //              public ROLES_Comparator( final boolean direction ) {
578    //                      direct = direction;
579    //              }
580    //
581    //              /**
582    //               * getRoles 比?ソ?
583    //               * インタフェース Comparable の 実?す?
584    //               *
585    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
586    //               *
587    //               * @param o1 比?象の??のオブジェク?
588    //               * @param o2 比?象の 2 番目のオブジェク?
589    //               * @return      ??の引数?2 番目の引数より小さ??合???整数、両方が等し??合? 0、最初?引数?2 番目の引数より大きい場合?正の整数
590    //               */
591    //              public int compare( final UserSummary o1, final UserSummary o2 ) {
592    //                      String key1 = o1.getRoles();
593    //                      String key2 = o2.getRoles();
594    //                      return ( direct ) ? key1.compareTo( key2 ) : key2.compareTo( key1 );
595    //              }
596    //      }
597    //
598    //      /**
599    //       * IPADDRESS で比??Comparator ?クラスの定義?
600    //       *
601    //       * @og.rev 4.0.0.0 (2006/09/31) 新規追?
602    //       * @og.rev 5.6.6.0 (2013/07/05) ATTRI_Comparator に統合?ため、?
603    //       */
604    //      private static final class IPADDRESS_Comparator implements Comparator<UserSummary>, Serializable {
605    //              private static final long serialVersionUID = 4000 ;     // 4.0.0 (2006/09/31)
606    //              private final boolean direct ;
607    //
608    //              /**
609    //               * ソート?方向を引数にとるコンストラクタ?
610    //               *
611    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
612    //               *
613    //               * @param       direction       ソート?方向[true:??/false:降?]
614    //               */
615    //              public IPADDRESS_Comparator( final boolean direction ) {
616    //                      direct = direction;
617    //              }
618    //
619    //              /**
620    //               * getIPAddress 比?ソ?
621    //               * インタフェース Comparable の 実?す?
622    //               *
623    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
624    //               *
625    //               * @param o1 比?象の??のオブジェク?
626    //               * @param o2 比?象の 2 番目のオブジェク?
627    //               * @return      ??の引数?2 番目の引数より小さ??合???整数、両方が等し??合? 0、最初?引数?2 番目の引数より大きい場合?正の整数
628    //               */
629    //              public int compare( final UserSummary o1, final UserSummary o2 ) {
630    //                      String key1 = o1.getIPAddress();
631    //                      String key2 = o2.getIPAddress();
632    //                      return ( direct ) ? key1.compareTo( key2 ) : key2.compareTo( key1 );
633    //              }
634    //      }
635    //
636    //      /**
637    //       * LOGINTIME で比??Comparator ?クラスの定義?
638    //       *
639    //       * @og.rev 4.0.0.0 (2006/09/31) 新規追?
640    //       * @og.rev 5.6.6.0 (2013/07/05) ATTRI_Comparator に統合?ため、?
641    //       */
642    //      private static final class LOGINTIME_Comparator implements Comparator<UserSummary>, Serializable {
643    //              private static final long serialVersionUID = 4000 ;     // 4.0.0 (2006/09/31)
644    //              private final boolean direct ;
645    //
646    //              /**
647    //               * ソート?方向を引数にとるコンストラクタ?
648    //               *
649    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
650    //               *
651    //               * @param       direction       ソート?方向[true:??/false:降?]
652    //               */
653    //              public LOGINTIME_Comparator( final boolean direction ) {
654    //                      direct = direction;
655    //              }
656    //
657    //              /**
658    //               * getLoginTime 比?ソ?
659    //               * インタフェース Comparable の 実?す?
660    //               *
661    //               * @og.rev 4.0.0.0 (2006/09/31) 新規追?
662    //               *
663    //               * @param o1 比?象の??のオブジェク?
664    //               * @param o2 比?象の 2 番目のオブジェク?
665    //               * @return      ??の引数?2 番目の引数より小さ??合???整数、両方が等し??合? 0、最初?引数?2 番目の引数より大きい場合?正の整数
666    //               */
667    //              public int compare( final UserSummary o1, final UserSummary o2 ) {
668    //                      long key1 = o1.getLoginTime();
669    //                      long key2 = o2.getLoginTime();
670    //                      int rtn = (direct) ? 1:-1 ;
671    //                      return ( key1 == key2 ) ? 0 : (key1 < key2) ? rtn : -rtn ;
672    //              }
673    //      }
674    }