001package com.thed.util; 002 003import org.apache.commons.codec.binary.Base64; 004import org.apache.commons.lang.StringUtils; 005import org.apache.commons.logging.Log; 006import org.apache.commons.logging.impl.LogFactoryImpl; 007 008import javax.crypto.Cipher; 009import javax.crypto.SecretKeyFactory; 010import javax.crypto.spec.DESKeySpec; 011import javax.crypto.spec.SecretKeySpec; 012import java.security.Key; 013 014public class CodecUtils { 015 private static Log logger = LogFactoryImpl.getLog(CodecUtils.class); 016 private static final int KEY_LENGTH = 8; 017 private static String keyString = "ZBOT"; 018 019 /** 020 * encrypts the data using customerId as default key. Uses axis base64 utility (because its SOAP safe) 021 * @param data 022 * @return 023 */ 024 public static String encrypt(String data) { 025 try{ 026 return encrypt(data, generateKey(keyString, null)); 027 } catch (Exception e) { 028 logger.error("Crypto.encrypt() Exception: ", e); 029 return null; 030 } 031 } 032 033 private static String encrypt(String plain, Key key) throws Exception{ 034 Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding"); 035 cipher.init(Cipher.ENCRYPT_MODE, key); 036 037 byte[] inputBytes = plain.getBytes("UTF8"); 038 byte[] outputBytes = cipher.doFinal(inputBytes); 039 040 String base64 = new String(Base64.encodeBase64(outputBytes)); 041 042 return base64; 043 } 044 045 /** 046 * decrypts the data using customerId as default key 047 * @param plain 048 * @return 049 */ 050 public static String decrypt(String plain) { 051 try{ 052 return decrypt(plain, generateKey(keyString, null)); 053 } catch (Exception e) { 054 logger.error("Crypto.encrypt() Exception: ", e); 055 return null; 056 } 057 } 058 059 private static String decrypt(String raw, Key key) throws Exception { 060 Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding"); 061 cipher.init(Cipher.DECRYPT_MODE, key); 062 063 byte[] inputBytes = Base64.decodeBase64(raw.getBytes()); 064 byte[] outputBytes = cipher.doFinal(inputBytes); 065 066 String result = new String(outputBytes, "UTF8"); 067 068 return result; 069 } 070 071 /** 072 * Uses simple SecretKeySpec (KeyGenerator is not used as it adds randomness to the key and decrypt fails 073 * @param keyString Length should be equal to or less then 16 074 * @param algorithm Defaults to DES 075 * @return generated Key 076 * @throws Exception 077 * @see {@link SecretKeySpec} 078 */ 079 private static Key generateKey(String keyString, String algorithm) throws Exception{ 080 if(StringUtils.isBlank(algorithm)){ 081 algorithm = "DES"; 082 } 083 keyString = StringUtils.rightPad(keyString, KEY_LENGTH, '-'); 084 085 DESKeySpec spec = new DESKeySpec(keyString.getBytes()); 086 SecretKeyFactory factory = SecretKeyFactory.getInstance(algorithm); 087 Key key = factory.generateSecret(spec); 088 089 return key; 090 091 } 092}