當柳上原的風吹向天際的時候...

          真正的快樂來源于創造

            BlogJava :: 首頁 :: 聯系 :: 聚合  :: 管理
            368 Posts :: 1 Stories :: 201 Comments :: 0 Trackbacks
          將文字在網絡中進行傳輸的時候,如果存在非ASCII碼字符,很容易出現亂碼問題,要解決也不難,在傳輸的文字上用URLEncoder進行編碼,將它變成全部是ASCII碼的形式,這樣在網絡傳輸中就不會受到影響;在另一側,將收到的文字用URLDecoder加碼就能還原文字原本的摸樣。

          IMSample中涉及到文字的混合加密,情況稍復雜一點,但流程還是一樣的。


          相關涉及編碼和解碼的工具類:
          package com.heyang.common.code;

          import java.io.UnsupportedEncodingException;
          import java.net.URLDecoder;
          import java.net.URLEncoder;


          /**
           * UTF8轉碼器
           * 
          @author heyang
           *
           
          */
          public class UTF8Coder{
              
          private static final String UTF_8 = "utf-8";// 編碼形式

              
          /**
               * 對文字進行UTF8轉碼
               * 
          @param str
               * 
          @return
               
          */
              
          public static String encode(String str){
                  
          try {
                      
          return URLEncoder.encode(str, UTF_8);
                  } 
          catch (UnsupportedEncodingException e) {
                      
          return null;
                  }
              }
              
              
          /**
               * 將轉碼后的文字還原
               * 
          @param str
               * 
          @return
               
          */
              
          public static String decode(String str){
                  
          try {
                      
          return URLDecoder.decode(str, UTF_8);
                  } 
          catch (UnsupportedEncodingException e) {
                      
          return null;
                  }
              }
          }

          變化后的加密器代碼:
          package com.heyang.common.cipher;

          import org.apache.commons.codec.binary.Base64;

          import com.heyang.common.code.AESSecurityCoder;
          import com.heyang.common.code.Base64SecurityUtil;
          import com.heyang.common.code.RSASecurityCoder;
          import com.heyang.common.code.UTF8Coder;

          /**
           * 對消息進行加密的加密器
           * 說明:
           * 作者:何楊(heyang78@gmail.com)
           * 創建時間:2010-12-27 下午07:00:29
           * 修改時間:2010-12-27 下午07:00:29
           
          */
          public class IMMsgEncrypter{
              
          // 經加密的消息
              private String cipheredMsg;
              
              
          /**
               * 構造函數
               * 
          @param plainMsg 未加密的消息
               * 
          @param otherSideRSAPublicKey 對方RSA公鑰
               * 
          @param rsaCoder 己方RSA編碼器
               * 
          @param aesCoder 己方AES編碼器
               * 
          @throws IMMsgEncryptException
               
          */
              
          public IMMsgEncrypter(String plainMsg,String otherSideRSAPublicKey,RSASecurityCoder rsaCoder,AESSecurityCoder aesCoder) throws IMMsgEncryptException{
                  
          try{
                      
          // 防止亂碼
                      plainMsg=UTF8Coder.encode(plainMsg);
                      
                      
          // 對明文進行AES加密
                      byte[] aesArr=aesCoder.getEncryptByteArray(plainMsg); // 對明文進行AES加密
                      String cipherText=Base64.encodeBase64String(aesArr);// 得到AES加密后的密文
                      
                      
          // 使用RSA對AES密鑰進行加密
                      String key=aesCoder.getAesKey();// 取得AES的密鑰
                      String aesKey="";
                      
          try{
                          
          byte[] clientRsaKeyArr=null;
                          clientRsaKeyArr
          =Base64.decodeBase64(otherSideRSAPublicKey);
                          
          byte[] rsaArr=rsaCoder.getEncryptArray(key, clientRsaKeyArr);
                          aesKey
          =Base64.encodeBase64String(rsaArr);
                      }
                      
          catch(Exception ex){
                          
          throw new IMMsgEncryptException("使用對方RSA公鑰加密己方AES鑰匙時發生異常.");
                      }
                      
                      
          // 在發出的密文前附帶經服務器RSA公鑰加密的AES密鑰
                      StringBuilder sb=new StringBuilder();
                      sb.append(
          "<aeskey>"+aesKey+"</aeskey>");
                      sb.append(
          "<rsakey>"+rsaCoder.getPublicKeyString()+"</rsakey>");
                      sb.append(
          "<text>"+cipherText+"</text>");
                      
                      
          // 最后對整體進行Base64加密
                      cipheredMsg=Base64SecurityUtil.getEncryptString(sb.toString());
                  }
                  
          catch(Exception ex){
                      
          throw new IMMsgEncryptException("加密消息時發生異常,異常信息為"+ex.getMessage()+".");
                  }
              }

              
          public String getCipheredMsg() {
                  
          return cipheredMsg;
              }
          }

          修改后的解碼器代碼:
          package com.heyang.common.cipher;

          import java.util.HashMap;
          import java.util.Map;
          import java.util.regex.Matcher;
          import java.util.regex.Pattern;

          import org.apache.commons.codec.binary.Base64;

          import com.heyang.common.code.AESSecurityCoder;
          import com.heyang.common.code.Base64SecurityUtil;
          import com.heyang.common.code.RSASecurityCoder;
          import com.heyang.common.code.UTF8Coder;


          /**
           * 消息解密器
           * 說明:
           * 作者:何楊(heyang78@gmail.com)
           * 創建時間:2010-12-27 下午07:41:44
           * 修改時間:2010-12-27 下午07:41:44
           
          */
          public class IMMsgDecrypter{
              
          // 固定的三個節點名
              private static final String TEXT = "text";

              
          private static final String RSAKEY = "rsakey";

              
          private static final String AESKEY = "aeskey";

              
          // 對方的RSA公鑰
              private String otherSideRSAPublicKey;
              
              
          // 解密后的明文
              private String plainMsg;
              
              
          /**
               * 構造函數
               * 
          @param cipherMsg 要解密的消息
               * 
          @param rsaCoder 己方RSA編碼器
               * 
          @param aesCoder 己方AES編碼器
               * 
          @throws IMMsgDecryptException
               
          */
              
          public IMMsgDecrypter(String cipherMsg,RSASecurityCoder rsaCoder,AESSecurityCoder aesCoder) throws IMMsgDecryptException{
                  
          try{
                      
          // 先用Base64解密密文
                      cipherMsg=Base64SecurityUtil.getDecryptString(cipherMsg);
                      
                      
          // 用正則表達式得到密鑰文,客戶端的RSA公鑰和密文
                      String regex="<(\\w+)>((.|\\s)+)</\\1>";

                      Pattern pattern
          =Pattern.compile(regex);
                      Matcher matcher
          =pattern.matcher(cipherMsg);
                          
                      String cipheredAesKey
          ="";// 經服務器RSA公鑰加密的客戶端AES鑰匙密文
                      String cipherText="";// 經客戶端AES加密的密文
                      
                      Map
          <String,String> map=new HashMap<String,String>();
                      
          while(matcher.find()){
                          map.put(matcher.group(
          1), matcher.group(2));
                      }
                      
                      
          if(map.size()==3){
                          cipheredAesKey
          =map.get(AESKEY);
                          otherSideRSAPublicKey
          =map.get(RSAKEY);
                          cipherText
          =map.get(TEXT);
                      }
                      
          else{
                          
          throw new IMMsgDecryptException("解密消息時發生異常,原因是消息格式不正確.消息為:"+cipherMsg);
                      }

                      
          // 得到經過服務器RSA私鑰解密后的AES密鑰
                      String plainAesKey="";
                      
          try {
                          
          byte[] cipheredAesKeyArr=Base64.decodeBase64(cipheredAesKey);
                          plainAesKey
          =rsaCoder.getDecryptString(cipheredAesKeyArr);
                      } 
          catch (Exception e) {
                          
          throw new IMMsgDecryptException("無法解密對方AES密鑰,異常信息為"+e.getMessage()+",客戶端請求為:"+cipherMsg);
                      }
                      
                      
          // 使用AES密鑰解密出明文
                      byte[] cipherTextArr=Base64.decodeBase64(cipherText);
                      plainMsg
          =aesCoder.getDecryptString(cipherTextArr, plainAesKey);
                      
                      
          //  UTF08還原
                      plainMsg=UTF8Coder.decode(plainMsg);
                  }
                  
          catch(Exception ex){
                      
          throw new IMMsgDecryptException("解密消息發生異常,異常信息為"+ex.getMessage()+".");
                  }
              }

              
          public String getOtherSideRSAPublicKey() {
                  
          return otherSideRSAPublicKey;
              }

              
          public String getPlainMsg() {
                  
          return plainMsg;
              }
          }

          以上只是涉及亂碼問題的一個處理方法,各位還要具體情況具體分析。
          posted on 2011-01-21 22:41 何楊 閱讀(257) 評論(0)  編輯  收藏

          只有注冊用戶登錄后才能發表評論。


          網站導航:
           
          主站蜘蛛池模板: 塘沽区| 霍林郭勒市| 镶黄旗| 三穗县| 凉城县| 恩平市| 大连市| 家居| 来凤县| 平阴县| 榕江县| 滦南县| 兰考县| 江孜县| 安岳县| 连平县| 祥云县| 文登市| 绍兴市| 中超| 大渡口区| 武威市| 浦北县| 昆山市| 邢台县| 邛崃市| 闽侯县| 海晏县| 日照市| 日土县| 灌云县| 奇台县| 大安市| 丹巴县| 房产| 嵊州市| 灵璧县| 泸溪县| 深圳市| 水城县| 扶绥县|