java 整合Ucenter (authcode)函数的算法 博客分类: java 算法JavaJ#SecurityC++
程序员文章站
2024-02-20 20:44:58
...
自己用java整合ucenter,发现网上的都不能用。看看下php的authcode,照着写了下,发现怎么写都会有个bug,请高手搞一下。 ---接口 package com.hq.encryptor; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.net.URLDecoder; import java.net.URLEncoder; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; import sun.misc.BASE64Decoder; import sun.misc.BASE64Encoder; import com.hq.encryptor.iface.PasswordEnDe; /** * Ucenter论坛可逆加密算法 * bug:解密后的字符串可能多一个或者2个字符。谁解决了请发我信箱supttkl@163.com * @author GAO * */ public class UcenterPasswordEncryptor implements PasswordEnDe { // 密钥字符串 private String ENCRYPTOR_KEY = "1234567890"; private BASE64Decoder decoder = new BASE64Decoder(); private BASE64Encoder encoder = new BASE64Encoder(); public UcenterPasswordEncryptor() { } /** * @param key 密钥 */ public UcenterPasswordEncryptor(String key) { this.ENCRYPTOR_KEY = key; } // 加密 public String encrypt(String password) { try { password=URLEncoder.encode(password, "UTF-8");//支持中文 String key = ENCRYPTOR_KEY; int ckey_length = 4; key = getMd5String(key); String keya = getMd5String(key.substring(0, 16)); String keyb = getMd5String(key.substring(16, 32)); String min = String.valueOf(System.currentTimeMillis()); min = "0.00000000 " + min.substring(0, min.length() - 3); String keyc = ckey_length > 0 ? getMd5String(String.valueOf(min)) : ""; keyc = keyc.substring(keyc.length() - 4, keyc.length()); String cryptkey = keya + getMd5String(keya + keyc); int key_length = cryptkey.length(); byte[] temp = null; String str_temp = "0000000000" + getMd5String(password + keyb).substring(0, 16) + password; temp = str_temp.getBytes("UTF-8"); int[] box = new int[256]; for (int i = 0; i < box.length; i++) { box[i] = i; } char[] rndkey = new char[256]; for (int i = 0; i <= 255; i++) { rndkey[i] = cryptkey.charAt(i % key_length); } for (int j = 0, i = 0; i < 256; i++) { j = (j + box[i] + (int) rndkey[i]) % 256; int tmp = box[i]; box[i] = box[j]; box[j] = tmp; } for (int a = 0, j = 0, i = 0; i < temp.length; i++) { a = (a + 1) % 256; j = (j + box[a]) % 256; int tmp = box[a]; box[a] = box[j]; box[j] = tmp; int gao = (int) temp[i]; byte c = (byte) (gao ^ (box[(box[a] + box[j]) % 256])); temp[i] = c; } ByteArrayOutputStream bytearrayoutputstream = new ByteArrayOutputStream(); ByteArrayInputStream bytearrayinputstream = new ByteArrayInputStream( temp); encoder.encode(((InputStream) (bytearrayinputstream)), ((OutputStream) (bytearrayoutputstream))); String s = bytearrayoutputstream.toString(); return keyc + s.replace("=", ""); } catch (NoSuchAlgorithmException e) { throw new RuntimeException(e); } catch (IOException e) { throw new RuntimeException(e); } } private String getMd5String(String password) throws NoSuchAlgorithmException { MessageDigest md = MessageDigest.getInstance("MD5"); byte[] input = md.digest(password.getBytes()); String hex = byteToHexString(input); return hex; } private String byteToHexString(byte[] res) { StringBuffer sb = new StringBuffer(res.length << 1); for (int i = 0; i < res.length; i++) { String digit = Integer.toHexString(0xFF & res[i]); if (digit.length() == 1) { digit = '0' + digit; } sb.append(digit); } return sb.toString(); } // public boolean matches(String passwordToCheck, String storedPassword) { if(storedPassword == null) { throw new NullPointerException("storedPassword can not be null"); } if(passwordToCheck == null) { throw new NullPointerException("passwordToCheck can not be null"); } return encrypt(passwordToCheck).equals(storedPassword); } // 解密 public String decrypt(String password) { try { int ckey_length = 4; String key = getMd5String(ENCRYPTOR_KEY); String keya = getMd5String(key.substring(0, 16)); String min = String.valueOf(System.currentTimeMillis()); min = "0.00000000 " + min.substring(0, min.length() - 3); String keyc = ckey_length > 0 ? password.substring(0, ckey_length) : ""; String cryptkey = keya + getMd5String(keya + keyc); int key_length = cryptkey.length(); byte[] temp = null; if(true){//这步为出bug的地方 String t1 = password.substring(ckey_length, password.length()); ByteArrayInputStream bytearrayinputstream = new ByteArrayInputStream(t1.getBytes("UTF-8")); ByteArrayOutputStream bytearrayoutputstream = new ByteArrayOutputStream(); decoder.decodeBuffer(((InputStream) (bytearrayinputstream)), ((OutputStream) (bytearrayoutputstream))); temp=bytearrayoutputstream.toByteArray(); } int[] box=new int[256]; for (int i = 0; i <box.length; i++) { box[i] = i; } char[] rndkey = new char[256]; for (int i = 0; i <= 255; i++) { rndkey[i] = cryptkey.charAt(i % key_length); } for (int j = 0, i = 0; i < 256; i++) { j = (j + box[i] + (int) rndkey[i]) % 256; int tmp = box[i]; box[i] = box[j]; box[j] = tmp; } StringBuffer sb = new StringBuffer(); for(int a =0, j=0, i = 0; i < temp.length; i++) { a = (a + 1) % 256; j = (j + box[a]) % 256; int tmp = box[a]; box[a] = box[j]; box[j] = tmp; int gao=(int)temp[i]<0? (int)temp[i]+256:(int)temp[i]; char c =(char)(gao ^ (box[(box[a] + box[j]) % 256])); sb.append(c); } String lastStr= sb.substring(26, sb.length()); return URLDecoder.decode(lastStr, "UTF-8"); } catch (IOException e) { throw new RuntimeException(e); } catch (NoSuchAlgorithmException e) { throw new RuntimeException(e); } } }
推荐阅读
-
java 整合Ucenter (authcode)函数的算法 博客分类: java 算法JavaJ#SecurityC++
-
几种简单的负载均衡算法及其Java代码实现 博客分类: Java Notes
-
几种简单的负载均衡算法及其Java代码实现 博客分类: Java Notes
-
停个车真的不是一般的难ReentrantLock.lock之LockSupport.park 博客分类: Java JavaIBM编程算法JDK
-
冒泡排序的算法分析与改进 博客分类: Java基础笔记 算法ExchangeJ#CC++
-
关于物流的5种模型10种算法的实现 博客分类: Java基础笔记 物流算法游戏JBuilderF#
-
追MM与java的32种模式 博客分类: java Java设计模式算法数据结构QQ
-
关于有效的性能调优的一些建议 博客分类: java 算法性能