1. 程式人生 > >專案中關於配置檔案中密碼的加密處理

專案中關於配置檔案中密碼的加密處理

專案中關於配置檔案中密碼的加密處理

轉載地址:http://supanccy2013.iteye.com/blog/2101964


    在專案中,為了專案的配置靈活,長把一些常量寫在配置檔案中,這時涉及一個問題,就是如果配置欄位是密碼,就不夠安全。這個時候需要在配置檔案中把密碼加密處理。下面是處理方案: 
    實際遇到的有兩種情況,一種是自己寫程式來都去配置檔案,這個時候處理比較簡單,把自己的加密工具,把密碼加個密放進配置檔案中,讀取的時候再解密即可。 第二種情況是遇到框架東西,例如spring這種框架,密碼加密之後解除安裝配置檔案中,我們該怎麼處理:下面是處理方法: 


    1,用自己的加密工具把密碼加密之後的密文解除安裝spring配置檔案中。 
    2,自己寫一個讀取配置檔案的類,這個類必須實現spring的一個介面,並實現當中的相關方法,把這個類配置到spring的配置檔案中,並且配置的時候這個類的id必須是固定的,這樣spring才能用你寫的整合類讀取配置檔案。 
    下面是例項: 


1,手寫新建一個properties的配置檔案,放在src的根目錄下,內容如下: 
Java程式碼  收藏程式碼
driverClass=oracle.jdbc.driver.OracleDriver  
jdbcUrl=jdbc:oracle:thin:@127.0.0.1:1521:ORCL  
user=supan  
password=root  
maxPoolSize=100  
maxIdleTime=100  
maxStatementsPerConnection=100  
numHelperThreads=1000  
idleConnectionTestPeriod=30  




2,自己寫一個讀取配置檔案的類,該類必須繼承spring的介面。內容如下: 
Java程式碼  收藏程式碼
package com.supan.frame;  
import java.util.Enumeration;  
import java.util.Properties;  
import org.springframework.beans.factory.config.PropertyPlaceholderConfigurer;  
import org.springframework.util.ObjectUtils;  
public class MyPropertyPlaceConfigurer extends PropertyPlaceholderConfigurer  
{  
    @Override  
    protected void convertProperties(Properties props)  
    {  
        super.convertProperties(props);  
        //讀取properties檔案中鍵的名字  
        Enumeration<?> propertyNames = props.propertyNames();  
        //遍歷鍵名字  
        while(propertyNames.hasMoreElements())  
        {  
            String propertyName = (String)propertyNames.nextElement();  
            //配置的值  
            String propertyValue = props.getProperty(propertyName);  
            //轉換後的值  
            String convertedValue = convertPropertyValue(propertyValue);  
              
            //對名為password的值進行解密  
            if("password".equals(propertyName))  
            {  
                //在這裡可以用自己的加密工具對配置的密文進行解密  
                //因為此時沒有加密工具只是演示一下。  
//              convertedValue = EmfCipher.decrpypt(convertedValue);  
                convertedValue = "root";  
            }  
              
            if(ObjectUtils.nullSafeEquals(propertyValue, convertedValue))  
            {  
                //注意:這裡並不是去修改配置檔案,而是改變讀取到配置檔案中的鍵值對  
                props.setProperty(propertyName, convertedValue);  
            }  
        }  
    }  
}  






3,把自己寫的讀取配置檔案的java類配置到配置檔案中。注意配置讀取bean的id一定要是propertyConfigurer 


Java程式碼  收藏程式碼
<beans xmlns="http://www.springframework.org/schema/beans"      
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"      
    xmlns:tx="http://www.springframework.org/schema/tx"      
    xmlns:aop="http://www.springframework.org/schema/aop"      
    xmlns:context="http://www.springframework.org/schema/context"      
    xsi:schemaLocation="http://www.springframework.org/schema/aop         
      http://www.springframework.org/schema/aop/spring-aop-3.0.xsd       
      http://www.springframework.org/schema/beans         
      http://www.springframework.org/schema/beans/spring-beans-3.0.xsd       
      http://www.springframework.org/schema/context       
      http://www.springframework.org/schema/context/spring-context-3.0.xsd       
      http://www.springframework.org/schema/tx         
      http://www.springframework.org/schema/tx/spring-tx-3.0.xsd">     
      
    <!--注入配置檔案讀取bean -->  
    <bean id="propertyConfigurer" class="com.supan.frame.MyPropertyPlaceConfigurer">  
            <property name="locations">  
              <list>  
                <value>jdbc.properties</value>  
              </list>  
            </property>  
    </bean>  
      
    <!-- 定義資料來源Bean,使用C3P0資料來源實現 -->   
    <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource" destroy-method="close">  
      <property name="driverClass">  
       <value>${driverClass}</value>  
      </property>  
      <property name="jdbcUrl">  
       <value>${jdbcUrl}</value>  
      </property>  
      <property name="user">  
       <value>${user}</value>  
      </property>  
      <property name="password">  
       <value>${password}</value>  
      </property>  
      <property name="maxPoolSize">  
       <value>${maxPoolSize}</value>  
      </property>  
      <property name="maxIdleTime">  
       <value>${maxIdleTime}</value>  
      </property>  
      <property name="maxStatementsPerConnection">  
       <value>${maxStatementsPerConnection}</value>  
      </property>  
      <property name="numHelperThreads">  
       <value>${numHelperThreads}</value>  
      </property>  
      <property name="idleConnectionTestPeriod">  
       <value>${idleConnectionTestPeriod}</value>  
      </property>  
     </bean>  
    <!-- 定義HIbernate的SessionFactory,讓Spring管理HIbernate,實現Spring和hibernate的整合 -->      
    <bean id="sessionFactory" class="org.springframework.orm.hibernate3.LocalSessionFactoryBean">    
        <property name="dataSource" ref="dataSource"></property>    
        <property name="hibernateProperties">    
            <props>    
                <prop key="hibernate.dialect">org.hibernate.dialect.Oracle9Dialect</prop>     
                <prop key="hibernate.show_sql">true</prop>    
                <prop key="hibernate.hbm2ddl.auto">update</prop>  
                <prop key="hibernate.format_sql">true</prop>  
            </props>    
        </property>    
        <property name="mappingResources">    
            <list>    
               <value>com/supan/bean/User.hbm.xml</value>  
            </list>    
        </property>    
    </bean>   
      
    <bean id="userDao" class="com.supan.dao.imp.UserDaoImp">  
       <property name="sessionFactory" ref="sessionFactory"></property>  
    </bean>   
</beans>  




4,userDao實現類 
Java程式碼  收藏程式碼
public void getUserNameAndInfo()  
    {  
        //定義存放結果的結果map  
        final Map<String,String> result = new HashMap<String, String>();  
        getHibernateTemplate().execute(new HibernateCallback<Object>()  
        {  
            @Override  
            public Object doInHibernate(Session session)  
                    throws HibernateException, SQLException  
            {  
                session.doWork(new Work()  
                {  
                    @Override  
                    public void execute(Connection conn) throws SQLException  
                    {  
                        CallableStatement proc = null;  
                        try  
                        {  
                            proc = conn.prepareCall("{call PROC_GETUSER_NAME_AGE(?,?,?)}");  
                              
                            //注意:這裡是註冊輸出引數  
                            proc.registerOutParameter(1, java.sql.Types.VARCHAR);  
                            proc.registerOutParameter(2, java.sql.Types.VARCHAR);  
                            //注意:這裡是傳遞輸入引數  
                            proc.setLong(3, 21L);  
                              
                            //執行儲存過程  
                            proc.execute();  
                              
                            //獲取執行完的儲存過程的返回值  
                            result.put("name", proc.getString(1));  
                            result.put("age", proc.getString(2));  
                        }  
                        catch(Exception e)  
                        {  
                            //logger.error("訪問資料庫失敗");  
                            e.printStackTrace();  
                            result.put("name", null);  
                            result.put("age", null);  
                        }  
                        finally  
                        {  
                            if(null != proc)  
                            {  
                                proc.close();  
                            }  
                        }  
                    }  
                });  
                  
                return null;  
            }  
        });  
          
        System.out.println(result.get("name"));  
        System.out.println(result.get("age"));  
    }  




5,測試類 
Java程式碼  收藏程式碼
package com.supan.test;  
import org.springframework.context.ApplicationContext;  
import org.springframework.context.support.ClassPathXmlApplicationContext;  
import com.supan.dao.UserDao;  
import junit.framework.TestCase;  
public class JunitMainTest extends TestCase  
{  
     public void testApringAndHibernate()  
     {  
         ApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");  
         UserDao ud = (UserDao)ctx.getBean("userDao");  
         ud.getUserNameAndInfo();  
     }  
}  




6,建立資料庫表,並插入一條資料 
-- Create table 
create table TBL_USER 

  ID     NUMBER(10) not null, 
  NAME   VARCHAR2(20 CHAR), 
  INFO   VARCHAR2(30 CHAR), 
  REMARK VARCHAR2(30 CHAR), 
  AGE    VARCHAR2(3 CHAR) 
); 
insert into tbl_user values(hibernate_sequence.nextval,'chenchaoyang','is a good man','hahha','26'); 


7,儲存過程 
Java程式碼  收藏程式碼
/*建立儲存過程,該儲存過程三個引數,前兩個是輸出引數 
最後一個是輸入引數*/  
create or replace procedure PROC_GETUSER_NAME_AGE(userName out varchar2,  
                                                  userAge  out varchar2,  
                                                  userId   in long)   
AS  
  --宣告該儲存過程為“自治事物單元”  
  PRAGMA AUTONOMOUS_TRANSACTION;  
    
  --定義兩個變數  
  v_userName varchar2(255);  
  v_userAge  varchar2(255);  
  
begin  
  select name, info into v_userName, v_userAge from TBL_User t where t.id = userId;  
  userName := v_userName;  
  userAge  := v_userAge;  
end;  






8,輸出結果: 
chenchaoyang 
is a good man