嘿伙计我有问题,我必须将PHP转换为Java ...
Php函数以原始格式创建sha1哈希并对其进行编码。
strtolower(urlencode(sha1("asfasfasdf", true)));
OUT:%bep%c3%9cc%dc%e4%89%f6n%0cw%fb%a3%95%ba%d8%c9r%82
在java中我尝试过:
public static String buildIdentity(String identity) {
try {
return URLEncoder.encode(toSHA1(identity.getBytes())).toLowerCase();
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
return null;
}
public static String toSHA1(byte[] convertme) throws UnsupportedEncodingException{
MessageDigest md = null;
try {
md = MessageDigest.getInstance("SHA-1");
md.update(convertme);
byte[] res = md.digest();
return new String(res);
}
catch(NoSuchAlgorithmException e) {
e.printStackTrace();
}
return null;
}
System.out.println(Utils.buildIdentity("asfasfasdf"));
但输出结果为:%ef%bf%bdp%c3%9cc%ef%bf%bd%ef%bf%bd%ef%bf%bdn%0cw%ef%bf%bd%ef%bf%bd%ef%bf%bdr%ef%bf%bd
请帮助我:(
找到解决方案!
public static String buildIdentity(String identity) {
try {
return URLEncoder.encode( new String(toSHA1(identity.getBytes("ISO-8859-1")), "ISO-8859-1"), "ISO-8859-1").toLowerCase();
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
return null;
}
public static byte[] toSHA1(byte[] convertme){
try {
MessageDigest md = MessageDigest.getInstance("SHA-1");
md.update(convertme);
return md.digest();
}
catch(NoSuchAlgorithmException e) {
e.printStackTrace();
}
return null;
}
答案 0 :(得分:0)
new String(byte[])
使用平台默认编码将字节转换为字符。对我来说,如果你从new String(res, "iso-8859-1");
方法返回toSHA1
,它就可以了。这应该是好的,因为“前256个代码点与ISO-8859-1的内容相同,以便使转换现有的西方文本变得微不足道。” (来自Wikipedia)。
但这涉及到字符串的不必要转换。相反,如果您不想添加依赖项,我将使用apache commons中的URLCodec
类或复制粘贴this。
默认编码问题也适用于identity.getBytes()
调用:您应在此处指定编码。它现在可能有效,但如果部署到生产服务器,它可能无法正常工作。
使用URLCodec
固定代码:
public static String buildIdentity(String identity) {
try {
return new String(new URLCodec().encode(toSHA1(identity.getBytes("utf-8"))), "iso-8859-1");
} catch (UnsupportedEncodingException e) {
// should never happen, utf-8 and iso-8859-1 support is required by jvm specification. In any case, we rethrow.
throw new RuntimeException(e);
}
}
public static byte[] toSHA1(byte[] convertme) throws UnsupportedEncodingException {
try {
MessageDigest md = MessageDigest.getInstance("SHA-1");
md.update(convertme);
return md.digest();
} catch (NoSuchAlgorithmException e) {
throw new RuntimeException(e);
}
}
public static void main(String[] args) {
System.out.println(buildIdentity("asfasfasdf"));
}
答案 1 :(得分:0)
您的代码忽略了Java字符编码问题。在buildIdentity
方法中,您在没有参数的字符串上调用getBytes
,因此将使用您平台的默认字符编码。这可能会导致问题,具体取决于您的平台;要在指定编码的平台之间获得可重现的结果,例如identity.getBytes("UTF-8")
。
在toSHA1
方法中,您无需指定编码即可调用构造函数new String(res)
。这里的事情很可能出错。如果您的操作系统的字符编码与ISO-8859-1
不同,则某些字节将替换为具有与原始字节不同的数值的字符,然后当您使用{{1}对其进行编码时},你不会得到你期望的结果。因此,请使用URLEncoder.encode
。
似乎Java生成的哈希比PHP生成的哈希更长。但是,如果编码是正确的,那么它们应该以相同的字符串开始,并且您应该能够调用new String(res, "ISO-8859-1")
获取要编码的正确数量的字符。