如何在Android中SHA1哈希一个string?
在Objective C中,我一直在使用下面的代码来散列一个string:
-(NSString *) sha1:(NSString*)stringToHash { const char *cStr = [stringToHash UTF8String]; unsigned char result[20]; CC_SHA1( cStr, strlen(cStr), result ); return [NSString stringWithFormat:@"%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X", result[0], result[1], result[2], result[3], result[4], result[5], result[6], result[7], result[8], result[9], result[10], result[11], result[12], result[13], result[14], result[15], result[16], result[17], result[18], result[19] ]; }
现在我需要相同的Android,但不知道如何做到这一点。 我一直在寻找这样的例子: 在Android上进行SHA1encryption? 但是这并没有给我在iPhone上的结果。 任何人都可以指向正确的方向吗?
你不需要和这个。 你可以用简单的java来完成。
你有没有尝试过一个简单的Java例子,看看这是否返回正确的sha1。
import java.io.UnsupportedEncodingException; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; public class AeSimpleSHA1 { private static String convertToHex(byte[] data) { StringBuilder buf = new StringBuilder(); for (byte b : data) { int halfbyte = (b >>> 4) & 0x0F; int two_halfs = 0; do { buf.append((0 <= halfbyte) && (halfbyte <= 9) ? (char) ('0' + halfbyte) : (char) ('a' + (halfbyte - 10))); halfbyte = b & 0x0F; } while (two_halfs++ < 1); } return buf.toString(); } public static String SHA1(String text) throws NoSuchAlgorithmException, UnsupportedEncodingException { MessageDigest md = MessageDigest.getInstance("SHA-1"); byte[] textBytes = text.getBytes("iso-8859-1"); md.update(textBytes, 0, textBytes.length); byte[] sha1hash = md.digest(); return convertToHex(sha1hash); } }
还分享你的预期sha1应该是什么。 也许ObjectC做错了。
一个更简单的SHA-1方法:( 根据评论者的build议更新,也使用更高效的字节 – >stringalgorithm )
String sha1Hash( String toHash ) { String hash = null; try { MessageDigest digest = MessageDigest.getInstance( "SHA-1" ); byte[] bytes = toHash.getBytes("UTF-8"); digest.update(bytes, 0, bytes.length); bytes = digest.digest(); // This is ~55x faster than looping and String.formating() hash = bytesToHex( bytes ); } catch( NoSuchAlgorithmException e ) { e.printStackTrace(); } catch( UnsupportedEncodingException e ) { e.printStackTrace(); } return hash; } // http://stackoverflow.com/questions/9655181/convert-from-byte-array-to-hex-string-in-java final protected static char[] hexArray = "0123456789ABCDEF".toCharArray(); public static String bytesToHex( byte[] bytes ) { char[] hexChars = new char[ bytes.length * 2 ]; for( int j = 0; j < bytes.length; j++ ) { int v = bytes[ j ] & 0xFF; hexChars[ j * 2 ] = hexArray[ v >>> 4 ]; hexChars[ j * 2 + 1 ] = hexArray[ v & 0x0F ]; } return new String( hexChars ); }
如果你能脱离使用番石榴,这是迄今为止最简单的方法 ,你不必重新发明轮子:
final HashCode hashCode = Hashing.sha1().hashString(yourValue, Charset.defaultCharset());
然后你可以把哈希值作为一个byte[]
, int
,或者long
。
没有包装在一个尝试赶上,没有shenanigans。 如果你决定要使用SHA-1以外的东西,Guava也支持sha256,sha 512以及一些我从未听说过的adler32和murmur3。
final MessageDigest digest = MessageDigest.getInstance("SHA-1"); result = digest.digest(stringToHash.getBytes("UTF-8"); // Another way to make HEX, my previous post was only the method like your solution StringBuilder sb = new StringBuilder(); for (byte b : result) // This is your byte[] result.. { sb.append(String.format("%02X", b)); } String messageDigest = sb.toString();
完全基于@Howmarrh的答案,这是我的实现,testing和工作正常,没有依赖关系:
public static String getSha1Hex(String clearString) { try { MessageDigest messageDigest = MessageDigest.getInstance("SHA-1"); messageDigest.update(clearString.getBytes("UTF-8")); byte[] bytes = messageDigest.digest(); StringBuilder buffer = new StringBuilder(); for (byte b : bytes) { buffer.append(Integer.toString((b & 0xff) + 0x100, 16).substring(1)); } return buffer.toString(); } catch (Exception ignored) { ignored.printStackTrace(); return null; } }
Android自带了Apache的Commons Codec,或者将它作为依赖添加。 然后做:
String myHexHash = DigestUtils.shaHex(myFancyInput);
这是您默认使用Android 4的旧版弃用方法。 DigestUtils的新版本带来了所有ShaHex()方法的风格,如sha256Hex(),并且还用不同的参数types重载了方法。
你正在寻找的方法不是特定于Android,而是一般的Java。 你正在寻找MessageDigest ( import java.security.MessageDigest
)。
在这里可以看到sha512(String s)
方法的实现,并且对SHA-1哈希的更改将会将第71行更改为:
MessageDigest md = MessageDigest.getInstance("SHA-1");
String.format("%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X%02X", result[0], result[1], result[2], result[3], result[4], result[5], result[6], result[7], result[8], result[9], result[10], result[11], result[12], result[13], result[14], result[15], result[16], result[17], result[18], result[19]);