Estoy escribiendo un generador de contraseñas para un script en PHP y quiero que sea compatible con una clase que escribí en Java, para que puedan compartir recursos.
código PHP:
public function PasswordGen($password, $rounds) { for($i = 0; $i < $rounds; $i++) { $password = substr(base64_encode(md5($password)), 0, 16); echo $i . " " . $password . PHP_EOL; // debugging // } return $password; }Código Java:
public static String PasswordGen(String password, int rounds) { try { for(int i = 0; i < rounds; i++) { byte[] md5 = MessageDigest.getInstance("MD5").digest(password.getBytes("UTF-8")); String md5h = (new BigInteger(1, md5)).toString(16); password = Base64.getEncoder().encodeToString(md5h.getBytes()).substring(0, 16); System.out.println(Integer.toString(i) + " " + password); // debugging // } } catch(Exception ex) { ex.printStackTrace(); return null; } return password; }Salida de depuración de PHP:
0 MWExZGM5MWM5MDcz 1 NDVkZmMxNWVjNWZi 2 ODY5YzVkODBhNTRh 3 ZGE2OTNiOWMxOWM1 4 OTcxMTY3MzgxMmRk 5 NWNjNDI2N2IzMDlj 6 NGVkYzY0YjVkMWUy 7 MjdhMGU4NjhhNmU3 8 OWY5OGE3ZGZiODZl 9 Y2I1ZjBkNjRmMjkx 10 YTk5NDA1MGI1OWY1 11 YzRmYWE5ZTk0ZDdl 12 NDBiZWZkNmQ5Yjhj 13 MzQyNzcwNGRjMTYw 14 N2U4ZmUxOGMyNWYx 15 MjBjOTZhNGE4ZDQ1 16 MjdmMzkwMzI0NDdj 17 YjM4NDI0YWU0YzUw 18 NDRiNjA1MWUwOGZi 19 MGI1YmIyMDViMGYzSalida de depuración de Java:
0 MWExZGM5MWM5MDcz 1 NDVkZmMxNWVjNWZi 2 ODY5YzVkODBhNTRh 3 ZGE2OTNiOWMxOWM1 4 OTcxMTY3MzgxMmRk 5 NWNjNDI2N2IzMDlj 6 NGVkYzY0YjVkMWUy 7 MjdhMGU4NjhhNmU3 8 OWY5OGE3ZGZiODZl 9 Y2I1ZjBkNjRmMjkx 10 YTk5NDA1MGI1OWY1 11 YzRmYWE5ZTk0ZDdl 12 NDBiZWZkNmQ5Yjhj 13 MzQyNzcwNGRjMTYw 14 N2U4ZmUxOGMyNWYx 15 MjBjOTZhNGE4ZDQ1 16 MjdmMzkwMzI0NDdj 17 YjM4NDI0YWU0YzUw 18 NDRiNjA1MWUwOGZi 19 YjViYjIwNWIwZjMyFunciona como se esperaba hasta el bucle 19. ¿Por qué produce una salida diferente después de eso?
En Java, convertir un BigDecimal en una cadena hexadecimal con el método toString(int base) no genera ceros a la izquierda.
Puede descubrir esto imprimiendo el resultado del paso intermedio (convirtiendo el código hash md5 en una cadena hexadecimal): en Java da b5bb205b0f32a7bf2a80fc870cbd2b7 mientras que en PHP da 0b5bb205b0f32a7bf2a80fc870cbd2b7 . Es solo una diferencia de un cero inicial, pero después de aplicar la codificación base64, se ven muy diferentes.
Una forma más fácil de obtener ceros a la izquierda es usar el método String.format .
Reemplace esta línea:
String md5h = ( new BigInteger(1, md5) ).toString(16);con esta línea:
String md5h = String.format("%032x", new BigInteger(1, md5));y obtendrá el mismo resultado que con su código php.