我在将 SQLite 数据库中存储为 BLOB 的哈希电子邮件值与 Android 应用程序中的电子邮件地址生成的哈希值进行比较时遇到了问题。这是我的代码的简化版本:
@SuppressLint("Range")
public UserCredentials findUserCredentials(String email) throws DBFindException {
SQLiteDatabase db = null;
Cursor cursor = null;
UserCredentials userCredentials = null;
try {
db = open();
byte[] emailHash = SecurityService.hash(SerializationUtils.serialize(email));
String selection = EMAIL_HASH + "=?";
String[] selectionArgs = {new String(emailHash, StandardCharsets.UTF_8)};
cursor = db.query(TABLE_NAME, null, selection, selectionArgs, null, null, null);
if (cursor != null && cursor.moveToFirst()) {
byte[] passwordBytes = cursor.getBlob(cursor.getColumnIndex(PASSWORD));
byte[] salt = cursor.getBlob(cursor.getColumnIndex(PASSWORD_SALT));
if (passwordBytes != null && salt != null) {
HashData hashData = new HashData(passwordBytes, salt);
userCredentials = new UserCredentials(cursor.getLong(cursor.getColumnIndex(ID)), hashData);
}
}
} catch (SQLiteException | SerializationException | HashException exception) {
throw new DBFindException("Failed to findUserCredentials from user with email (" + email + ")", exception);
} finally {
if (cursor != null)
cursor.close();
close(db);
}
return userCredentials;
}
尽管确保从电子邮件地址生成的哈希与数据库中存储的值匹配,但查询不会返回任何结果。我怀疑这个问题可能与我如何将哈希值作为 selectArgs 中的参数传递有关。然而,即使将哈希值转换为十六进制格式进行比较,问题仍然存在。
有人可以建议可能导致此问题的原因或建议任何潜在的解决方案吗?
PS:这是我在插入操作期间用于“getContentValues”的代码片段,其中 EMAIL_HASH 是数据库中的列,user.getEmail() 返回一个字符串:
contentValues.put(EMAIL_HASH, SecurityService.hash(SerializationUtils.serialize(user.getEmail())));
确保在生成和比较哈希值时使用相同的哈希算法和编码/解码机制。哈希过程中的任何差异都可能导致值不匹配。
这是代码片段的修改版本,演示了如何将哈希值编码为十六进制字符串:
String emailHashHex = bytesToHex(emailHash); // Convert byte array to hexadecimal string
String selection = EMAIL_HASH + "=?";
String[] selectionArgs = { emailHashHex };
// Helper method to convert byte array to hexadecimal string
private String bytesToHex(byte[] bytes) {
StringBuilder sb = new StringBuilder();
for (byte b : bytes) {
sb.append(String.format("%02x", b));
}
return sb.toString();
}
通过确保一致的编码和解码机制并使用十六进制编码进行比较,您应该能够在 SQLite 查询中成功比较哈希值。