001
014
015 package com.liferay.util;
016
017 import com.liferay.portal.kernel.log.Log;
018 import com.liferay.portal.kernel.log.LogFactoryUtil;
019 import com.liferay.portal.kernel.util.Base64;
020 import com.liferay.portal.kernel.util.Digester;
021 import com.liferay.portal.kernel.util.DigesterUtil;
022 import com.liferay.portal.kernel.util.GetterUtil;
023 import com.liferay.portal.kernel.util.ServerDetector;
024 import com.liferay.portal.kernel.util.StringPool;
025
026 import java.security.Key;
027 import java.security.Provider;
028 import java.security.SecureRandom;
029 import java.security.Security;
030
031 import java.util.Map;
032 import java.util.concurrent.ConcurrentHashMap;
033
034 import javax.crypto.Cipher;
035 import javax.crypto.KeyGenerator;
036
037
041 public class Encryptor {
042
043 public static final String ENCODING = Digester.ENCODING;
044
045 public static final String KEY_ALGORITHM = "DES";
046
047 public static final String SUN_PROVIDER_CLASS =
048 "com.sun.crypto.provider.SunJCE";
049
050 public static final String IBM_PROVIDER_CLASS =
051 "com.ibm.crypto.provider.IBMJCE";
052
053 public static final String PROVIDER_CLASS = GetterUtil.getString(
054 SystemProperties.get(Encryptor.class.getName() + ".provider.class"),
055 SUN_PROVIDER_CLASS);
056
057 public static Key generateKey() throws EncryptorException {
058 return generateKey(KEY_ALGORITHM);
059 }
060
061 public static Key generateKey(String algorithm) throws EncryptorException {
062 try {
063 Security.addProvider(getProvider());
064
065 KeyGenerator generator = KeyGenerator.getInstance(algorithm);
066 generator.init(56, new SecureRandom());
067
068 Key key = generator.generateKey();
069
070 return key;
071 }
072 catch (Exception e) {
073 throw new EncryptorException(e);
074 }
075 }
076
077 public static Provider getProvider()
078 throws ClassNotFoundException, IllegalAccessException,
079 InstantiationException {
080
081 Class<?> providerClass = null;
082
083 try {
084 providerClass = Class.forName(PROVIDER_CLASS);
085 }
086 catch (ClassNotFoundException cnfe) {
087 if ((ServerDetector.isWebSphere()) &&
088 (PROVIDER_CLASS.equals(SUN_PROVIDER_CLASS))) {
089
090 if (_log.isWarnEnabled()) {
091 _log.warn(
092 "WebSphere does not have " + SUN_PROVIDER_CLASS +
093 ", using " + IBM_PROVIDER_CLASS + " instead");
094 }
095
096 providerClass = Class.forName(IBM_PROVIDER_CLASS);
097 }
098 else if (System.getProperty("java.vm.vendor").equals(
099 "IBM Corporation")) {
100
101 if (_log.isWarnEnabled()) {
102 _log.warn(
103 "IBM JVM does not have " + SUN_PROVIDER_CLASS +
104 ", using " + IBM_PROVIDER_CLASS + " instead");
105 }
106
107 providerClass = Class.forName(IBM_PROVIDER_CLASS);
108 }
109 else {
110 throw cnfe;
111 }
112 }
113
114 return (Provider)providerClass.newInstance();
115 }
116
117 public static String decrypt(Key key, String encryptedString)
118 throws EncryptorException {
119
120 byte[] encryptedBytes = Base64.decode(encryptedString);
121
122 return decryptUnencodedAsString(key, encryptedBytes);
123 }
124
125 public static byte[] decryptUnencodedAsBytes(Key key, byte[] encryptedBytes)
126 throws EncryptorException {
127
128 String algorithm = key.getAlgorithm();
129
130 String cacheKey = algorithm.concat(StringPool.POUND).concat(
131 key.toString());
132
133 Cipher cipher = _decryptCipherMap.get(cacheKey);
134
135 try {
136 if (cipher == null) {
137 Security.addProvider(getProvider());
138
139 cipher = Cipher.getInstance(algorithm);
140
141 cipher.init(Cipher.DECRYPT_MODE, key);
142
143 _decryptCipherMap.put(cacheKey, cipher);
144 }
145
146 synchronized (cipher) {
147 return cipher.doFinal(encryptedBytes);
148 }
149 }
150 catch (Exception e) {
151 throw new EncryptorException(e);
152 }
153 }
154
155 public static String decryptUnencodedAsString(
156 Key key, byte[] encryptedBytes)
157 throws EncryptorException {
158
159 try {
160 byte[] decryptedBytes = decryptUnencodedAsBytes(
161 key, encryptedBytes);
162
163 return new String(decryptedBytes, ENCODING);
164 }
165 catch (Exception e) {
166 throw new EncryptorException(e);
167 }
168 }
169
170 public static String digest(String text) {
171 return DigesterUtil.digest(text);
172 }
173
174 public static String digest(String algorithm, String text) {
175 return DigesterUtil.digest(algorithm, text);
176 }
177
178 public static String encrypt(Key key, String plainText)
179 throws EncryptorException {
180
181 byte[] encryptedBytes = encryptUnencoded(key, plainText);
182
183 return Base64.encode(encryptedBytes);
184 }
185
186 public static byte[] encryptUnencoded(Key key, byte[] plainBytes)
187 throws EncryptorException {
188
189 String algorithm = key.getAlgorithm();
190
191 String cacheKey = algorithm.concat(StringPool.POUND).concat(
192 key.toString());
193
194 Cipher cipher = _encryptCipherMap.get(cacheKey);
195
196 try {
197 if (cipher == null) {
198 Security.addProvider(getProvider());
199
200 cipher = Cipher.getInstance(algorithm);
201
202 cipher.init(Cipher.ENCRYPT_MODE, key);
203
204 _encryptCipherMap.put(cacheKey, cipher);
205 }
206
207 synchronized (cipher) {
208 return cipher.doFinal(plainBytes);
209 }
210 }
211 catch (Exception e) {
212 throw new EncryptorException(e);
213 }
214 }
215
216 public static byte[] encryptUnencoded(Key key, String plainText)
217 throws EncryptorException {
218
219 try {
220 byte[] decryptedBytes = plainText.getBytes(ENCODING);
221
222 return encryptUnencoded(key, decryptedBytes);
223 }
224 catch (Exception e) {
225 throw new EncryptorException(e);
226 }
227 }
228
229 private static Log _log = LogFactoryUtil.getLog(Encryptor.class);
230
231 private static Map<String, Cipher> _decryptCipherMap =
232 new ConcurrentHashMap<String, Cipher>(1, 1f, 1);
233 private static Map<String, Cipher> _encryptCipherMap =
234 new ConcurrentHashMap<String, Cipher>(1, 1f, 1);
235
236 }