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.resource;
017    
018    import java.text.MessageFormat;
019    import java.util.List;
020    
021    import org.opengion.hayabusa.common.HybsSystem;
022    import org.opengion.hayabusa.common.HybsSystemException;
023    import org.opengion.hayabusa.common.SystemManager;
024    import org.opengion.fukurou.util.LogWriter;
025    import org.opengion.fukurou.util.Cleanable;
026    import org.opengion.fukurou.util.StringUtil;
027    import org.opengion.fukurou.util.ApplicationInfo;
028    import org.opengion.fukurou.db.DBUtil;
029    
030    /**
031     * systemId に対応したユーザー??を作?するファクトリクラスです?
032     *
033     * UserInfoオブジェクト??キャ?ュせずに、要求?度、データベ?スを検索します?
034     * これは、ユーザー登録が?他シス?より行われる可能性を?慮して?為です?
035     * ユーザーオブジェクト?要求?、基本?ログイン時?みで、その後セ?ョンに
036     * キープされます?
037     *
038     * 検索するカラ?は、?、USERID,LANG,NAME,ROLES,DROLES がこの?で含まれており?
039     * 絞込み条件(?パラメータ)として、SYSTEM_ID,USERID がこの?で?される?があります?
040     * (カラ?は関係ありません。並び?意味が重要です?)
041     * また?検索?ORDER BY)は、優先?位?低い?検索してください。使用するのは、??に
042     * 検索された行を使用します?
043     * ユーザーリソースは、RESOURCE_USER_DBID で????タベ?スから取得します?
044     * 未定義の場合?、RESOURCE_DBID から、それも未定義の場合? ?ォルト?接続??
045     * 使用します?
046     *
047     * SYSTEM_ID='**' は、?通リソースで?ROLESも?通に設定する?があります?)?
048     * これは、シス?間で共通に使用されるリソース??を登録しておきます?
049     * SYSTEM_ID は、指定?シス?IDと**を検索対象にします?**は、?シス?共通?
050     * ??シス?IDと**と両方存在する場合?、指定?シス?IDが優先されます?
051     *
052     * ver4 では、デフォルトロールと??方がなくなりましたので、画面のロールに?
053     * (*)を?示?追?、RWMODE を指定する?があります?
054     *
055     * @og.rev 4.0.0.0 (2004/12/31) 新規作?
056     * @og.group リソース管?
057     *
058     * @version  4.0
059     * @author   Kazuhiko Hasegawa
060     * @since    JDK5.0,
061     */
062    public final class UserInfoFactory {
063    
064            private static final String SYSTEM_ID = HybsSystem.sys( "SYSTEM_ID" );
065    
066            // ユーザーリソースの接続?を?取得します?
067            private static String dbid = StringUtil.nval(
068                                                                    HybsSystem.sys( "RESOURCE_USER_DBID" ) ,
069                                                                    HybsSystem.sys( "RESOURCE_DBID" )
070                                                            ) ;
071    
072            // ユーザーリソースのキー?読み込みのクエリー
073            private static String query                     = HybsSystem.sys( "RESOURCE_USER_SQL" );
074            private static String queryRole         = HybsSystem.sys( "RESOURCE_USER_ROLE_SQL" );
075    
076            // 5.2.0.0 (2010/09/01) LDAP対?
077            private static String srcType           = HybsSystem.sys( "RESOURCE_USER_SRC_TYPE" );
078            private static String[] ldapClm         = StringUtil.csv2Array( HybsSystem.sys( "RESOURCE_USER_LDAP_CLM" ) );
079            private static String ldapFilter        = HybsSystem.sys( "RESOURCE_USER_LDAP_FILTER" );
080            private static String ldapRoleFilter= HybsSystem.sys( "RESOURCE_USER_ROLE_LDAP_FILTER" );
081    
082            private static String searchScope       = HybsSystem.sys( "LDAP_SEARCH_SCOPE" );
083            private static String initctx           = HybsSystem.sys( "LDAP_INITIAL_CONTEXT_FACTORY" );
084            private static String providerURL       = HybsSystem.sys( "LDAP_PROVIDER_URL" );
085            private static String entrydn           = HybsSystem.sys( "LDAP_ENTRYDN" );
086            private static String password          = HybsSystem.sys( "LDAP_PASSWORD" );
087            private static String searchbase        = HybsSystem.sys( "LDAP_SEARCH_BASE" );
088    
089            /** コネクションにアプリケーション??を追記するかど???*/
090            public static final boolean USE_DB_APPLICATION_INFO  = HybsSystem.sysBool( "USE_DB_APPLICATION_INFO" ) ;
091    
092            // 4.0.0 (2005/01/31) Cleanable インターフェースによる初期化??
093            static {
094                    Cleanable clr = new Cleanable() {
095                            public void clear() {
096                                    UserInfoFactory.clear();
097                            }
098                    };
099    
100                    SystemManager.addCleanable( clr );
101            }
102    
103            private static final Object lock = new Object();
104    
105            /**
106             *  ?ォルトコンストラクターをprivateにして?
107             *  オブジェクト?生?をさせな??する?
108             *
109             */
110            private UserInfoFactory() {
111            }
112    
113            /**
114             * UserInfo オブジェクトを取得します?
115             *
116             * UserInfoオブジェクト??キャ?ュせずに、要求?度、データベ?スを検索します?
117             * これは、ユーザー登録が?他シス?より行われる可能性を?慮して?為です?
118             * ユーザーオブジェクト?要求?、基本?ログイン時?みで、その後セ?ョンに
119             * キープされます?
120             *
121             * @og.rev 3.7.0.4 (2005/03/18) ゲストログイン機?追?
122             * @og.rev 4.0.0.0 (2007/10/31) ロール?でのログイン機?追?
123             * @og.rev 4.3.4.0 (2008/12/01) GE20(ユーザー定数)へ登録するか?フラグへの対?
124             * @og.rev 4.4.0.0 (2009/08/02) ??タロール対?
125             * @og.rev 5.2.0.0 (2010/09/01) LDAP対?
126             * @og.rev 5.3.6.0 (2011/06/01) GE20の読み込みをUserInfo?移?
127             *
128             * @param       userID          ユーザーID
129             * @param       ipAddress       ログイン端末のIPアドレス
130             * @param       roles           ??タロール
131             *
132             * @return      UserInfoオブジェク?
133             */
134            public static UserInfo newInstance( final String userID,final String ipAddress,final String roles ) {
135                    // 3.8.7.0 (2006/12/15) アクセスログ取得?為,ApplicationInfoオブジェクトを設?
136                    ApplicationInfo appInfo = null ;
137                    if( USE_DB_APPLICATION_INFO ) {
138                            appInfo = new ApplicationInfo();
139                            // ユーザーID,IPアドレス,ホスト名
140                            appInfo.setClientInfo( userID,ipAddress,null );
141                            // 画面ID,操?プログラ?D
142                            appInfo.setModuleInfo( "UserInfoFactory",null,"newInstance" );
143                    }
144    
145    //              String[] args;
146    //              String[][] vals;
147    
148    //              if( roles == null || roles.length() == 0 ) {
149    //                      args = new String[] { SYSTEM_ID,userID };
150    //                      synchronized( lock ) {
151    //                              vals = DBUtil.dbExecute( query,args,appInfo,dbid );
152    //                      }
153    //              }
154    //              // 4.0.0.0 (2007/10/31)
155    //              else {
156    //                      args = new String[] { SYSTEM_ID,userID,roles };
157    //                      synchronized( lock ) {
158    //                              vals = DBUtil.dbExecute( queryRole,args,appInfo,dbid );
159    //                      }
160    //              }
161    
162                    String[][] vals;
163                    if( "LDAP".equalsIgnoreCase( srcType ) ) {
164                            vals = getValsByLdap( userID, roles );
165                    }
166                    else {
167                            vals = getVals( userID, roles, appInfo );
168                    }
169    
170                    final UserInfo info ;
171                    int len = vals.length ; // シス?ID ** を含??
172                    if( len >= 1 && vals[0].length >= 5 ) {
173                            // シス?IDでソートされる。SYSTEM_ID="**"は??に現れるので、最後を取?
174                            info = new UserInfo(
175                                                                    userID          ,                       // userID
176                                                                    vals[len-1][1]  ,               // lang
177                                                                    vals[len-1][2]  ,               // jname
178                                                                    vals[len-1][3]  ,               // roles
179                                                                    vals[len-1][4]  ,               // droles // 4.4.0.0 (2009/08/02)
180                                                                    SYSTEM_ID               ,               // systemId
181                                                                    ipAddress               ,               // ipAddress
182                                                                    appInfo                 ) ;             // ApplicationInfo
183                    }
184                    else {
185                            String errMsg = "UserInfo の??タ(USERID,LANG,NAME,ROLES,DROLES)が取得できません?
186                                                    + " Key [" + userID + "]"
187                                                    + " SQL [" + query + "]" ;
188                            LogWriter.log( errMsg );
189                            throw new HybsSystemException( errMsg );
190                    }
191    
192                    return info ;
193            }
194    
195            /**
196             * UserInfoFactoryをクリアします?
197             *
198             * @og.rev 5.2.0.0 (2010/09/01) LDAP対?
199             *
200             */
201            public static void clear() {
202                    synchronized( lock ) {
203                            dbid = StringUtil.nval(
204                                                                            HybsSystem.sys( "RESOURCE_USER_DBID" ) ,
205                                                                            HybsSystem.sys( "RESOURCE_DBID" )
206                                                                    ) ;
207                            query = HybsSystem.sys( "RESOURCE_USER_SQL" );
208                            queryRole = HybsSystem.sys( "RESOURCE_USER_ROLE_SQL" );
209    
210                            // 5.2.0.0 (2010/09/01) LDAP対?
211                            srcType                 = HybsSystem.sys( "RESOURCE_USER_SRC_TYPE" );
212                            ldapClm                 = StringUtil.csv2Array( HybsSystem.sys( "RESOURCE_USER_LDAP_CLM" ) );
213                            ldapFilter              = HybsSystem.sys( "RESOURCE_USER_LDAP_FILTER" );
214                            ldapRoleFilter  = HybsSystem.sys( "RESOURCE_USER_ROLE_LDAP_FILTER" );
215    
216                            searchScope             = HybsSystem.sys( "LDAP_SEARCH_SCOPE" );
217                            initctx                 = HybsSystem.sys( "LDAP_INITIAL_CONTEXT_FACTORY" );
218                            providerURL     = HybsSystem.sys( "LDAP_PROVIDER_URL" );
219                            entrydn                 = HybsSystem.sys( "LDAP_ENTRYDN" );
220                            password                = HybsSystem.sys( "LDAP_PASSWORD" );
221                            searchbase              = HybsSystem.sys( "LDAP_SEARCH_BASE" );
222                    }
223            }
224    
225            /**
226             * DBからユーザーリソースの??を取得します?
227             *
228             * @og.rev 5.2.0.0 (2010/09/01) 新規作?
229             *
230             * @param       userId  ユーザーID
231             * @param       roles   ロール
232             * @param       appInfo DB接続情報
233             *
234             * @return ユーザーリソース??
235             */
236            private static String[][] getVals( final String userId, final String roles, final ApplicationInfo appInfo ) {
237                    String[] args;
238                    String[][] rtn = null;
239    
240                    if( roles == null || roles.length() == 0 ) {
241                            args = new String[] { SYSTEM_ID,userId };
242                            synchronized( lock ) {
243                                    rtn = DBUtil.dbExecute( query,args,appInfo,dbid );
244                            }
245                    }
246                    // 4.0.0.0 (2007/10/31)
247                    else {
248                            args = new String[] { SYSTEM_ID,userId,roles };
249                            synchronized( lock ) {
250                                    rtn = DBUtil.dbExecute( queryRole,args,appInfo,dbid );
251                            }
252                    }
253    
254                    return rtn;
255            }
256    
257            /**
258             * LDAPからユーザーリソースの??を取得します?
259             *
260             * @og.rev 5.2.0.0 (2010/09/01) 新規作?
261             *
262             * @param       userId  ユーザーID
263             * @param       roles   ロール
264             *
265             * @return ユーザーリソース??
266             */
267            private static String[][] getValsByLdap( final String userId, final String roles ) {
268                    LDAPSearch serch = new LDAPSearch();
269                    serch.setSearchScope( searchScope ) ;
270                    serch.setInitctx( initctx ) ;
271                    serch.setProviderURL( providerURL ) ;
272                    serch.setSearchbase( searchbase ) ;
273                    if( entrydn != null  ) { serch.setEntrydn( entrydn ) ; }
274                    if( password != null ) { serch.setPassword( password ) ; }
275                    serch.setAttributes( ldapClm ) ;
276                    serch.init();
277    
278                    String filter = ( roles == null || roles.length() == 0 ) ? ldapFilter : ldapRoleFilter;
279                    String[] args = ( roles == null || roles.length() == 0 ) ? new String[] { SYSTEM_ID,userId } : new String[] { SYSTEM_ID,userId,roles };
280                    filter = MessageFormat.format( filter,(Object[])args );
281    
282                    List<String[]> list = serch.search( filter );
283    
284                    String[][] rtn = null;
285                    if( list.size() > 0 ) {
286                            rtn = new String[1][];
287                            rtn[0] = list.get( 0 );
288                            rtn[0][1] = StringUtil.nval( rtn[0][1], "ja" );                 // ???ォルト?は?ja'
289                            rtn[0][2] = StringUtil.nval( rtn[0][2], rtn[0][0] );    // 名称の?ォルト?は、ユーザーID
290                            rtn[0][3] = StringUtil.nval( rtn[0][3], ldapClm[3] );   // ロールズの初期値は、ロールに設定された??
291                            rtn[0][4] = StringUtil.nval( rtn[0][4], "" );
292                    }
293    
294                    return rtn;
295            }
296    }