我检查了这个问题的论坛,我发现了一些答案,但任何这种情况是不同的,不为我工作。
我遇到此错误的问题:
let test = PasswordHash::new(&hashed_password).clone().unwrap();
| ---------------- `hashed_password` is borrowed here
53 | // Ok(PasswordHash::new(&hashed_password).unwrap())
54 | Ok(test)
| ^^^^^^^^ returns a value referencing data owned by the current function
我完全知道这个错误是什么意思。我知道问题出在哪里,我甚至知道是什么造成的。但是我不知道如何修复它。
我的想法是不重复负责生成PasswordHash的部分代码。我决定创建单独的函数来完成这个任务。
我的代码如下:
use argon2::{
password_hash::{
rand_core::OsRng,
PasswordHash, PasswordHasher, PasswordVerifier, SaltString, Error
},
Argon2,
};
struct AlgorithmData {
version: u32,
params: String,
algorithm_type: String,
}
impl AlgorithmData {
fn new() -> Self {
let example_string = "example_string";
let password_hash = Hasher::get_passwordhash_object(&example_string).unwrap();
AlgorithmData { version: password_hash.version.unwrap(),
params: password_hash.params.to_string(),
algorithm_type: password_hash.algorithm.to_string() }
}
}
pub struct Hasher {}
impl Hasher {
pub fn hash_string(string_to_hash: &str) -> Result<String, Error> {
let parsed_hash_password = Hasher::get_passwordhash_object(string_to_hash)?;
let result = format!("{}${}",
parsed_hash_password.salt.unwrap().to_string(),
parsed_hash_password.hash.unwrap().to_string());
Ok(result)
}
fn get_passwordhash_object(string_to_hash: &str) -> Result<PasswordHash, Error> {
let bytes_to_hash = string_to_hash.as_bytes();
let salt = SaltString::generate(&mut OsRng);
let argon2 = Argon2::default();
let hashed_password = argon2.hash_password(&bytes_to_hash,
&salt)?.to_string();
let test = PasswordHash::new(&hashed_password).clone().unwrap();
// Ok(PasswordHash::new(&hashed_password).unwrap()) --> here too is problem
Ok(test) // here is the same problem
}
pub fn compare_string_to_hash(string_to_compare: &String,
hash_to_compare: &String) -> Result<bool, Error> {
let bytes_to_compare = string_to_compare.as_bytes();
let bytes_from_hash = PasswordHash::new(&hash_to_compare).unwrap();
Ok(Argon2::default().verify_password(&bytes_to_compare,
&bytes_from_hash).is_ok())
}
}
就像你看到的主要问题是变量:hashed_password及其在新对象PasswordHash中引用。
我尝试使用copy函数来克隆hashed_password变量或对象PasswordHash。第二件事是尝试使用lifetime参数,如〈'a〉。第三个想法是使用Box::new来尝试直接访问内存。
我需要帮助来解决这个问题。我已经阅读了文档。但是仍然没有更多的想法来解决这个问题。
错误编号:E0515很好地解释了原因。
2条答案
按热度按时间kkih6yb81#
这里肯定有一个生存期问题,在您的例子中,
PasswordHash
的生存期依赖于SaltString
,因此,如果您想将PasswordHash
的引用发送给调用者,最好将SaltString
作为函数get_passwordhash_object
的参数。下面是从您的代码中派生的最小示例:
u5rb5r592#
如果你查看
PasswordHash::new
的文档,你会发现它返回一个和参数一样的结构体,在你的例子中,test
变量的生命周期取决于hashed_password
的生命周期,而hashed_password
本身又取决于拥有它的数据的salt
的生命周期。在
get_passwordhash_object
中,您不能返回PasswordHash
类型并丢弃salt,您需要返回两者,或者将数据转换为拥有其数据的其他内容。一种解决方案是将
PasswordHash
序列化为PasswordHashString
,因为此类型拥有其数据