我无法理解这段代码的生命周期之间的关系。基本上,我有一个 Rocket API 可以接收一些x-www-form-urlencoded
数据,只有一个键:json
. 直观地说,这个键包含一个 JSON 值,用百分比编码编码,一个 struct Message<T>
。
(我知道这是次优的 API 设计,但这是逆向工程工作,所以我别无选择)
为了方便地用作请求保护From<Message<T>>
,我正在实施FromForm
. 为此,我需要FromForm<'f>
为任何Message<T>
地方T
实现 implements Deserialize<'de>
。我将我的 impl 签名写为impl<'f, 'de, T> FromForm<'f> for Message<T> where T: Deserialize<'de>
.
要实际执行解码,我:
- 获取
"json"
表单数据的key; - URL解码值;
- 解析值中包含的 JSON。
尽快出手。执行此操作的代码(为方便读者使用显式类型注释):
fn from_form(items: &mut FormItems<'f>, strict: bool) -> Result<Self, Self::Error> {
// Get JSON field
let encoded: Option<&RawStr> = items.find(|&(k, _)| k.as_str() == "json")
.map(|(_, v)| v);
if let None = encoded {
return Err(MessageFormError::MissingJsonKey);
}
// Decode URL-string
let decoded: Result<String, Utf8Error> = encoded.unwrap().url_decode();
if let Err(e) = decoded {
return Err(MessageFormError::InvalidUrl(e));
}
// Parse JSON
let json: String = decoded.unwrap();
serde_json::from_str::<Self>(&json) // Line 205
.map_err(|e| MessageFormError::InvalidJson(e))
}
以粘贴运行方式演示问题的要点(不适用于 Playground,因为它依赖于 Rocket)。
我认为:
- 的
&RawStr
有encoded
一生'f
。 - A
String
是由它创建的url_decode
,它一直存在到函数结束 serde_json
接受一个不需要与 重合的&'x str
地方,并返回一个值(因此它一直存在到函数的末尾,并且由于它被返回,因此被移到它之外)'x
'de
但似乎我的理解是不正确的:
205 | serde_json::from_str::<Self>(&json)
| ^^^^ does not live long enough
206 | .map_err(|e| MessageFormError::InvalidJson(e))
207 | }
| - borrowed value only lives until here
|
note: borrowed value must be valid for the lifetime 'f as defined on the impl at 184:1...
--> src/transport.rs:184:1
|
184 | / impl<'f, T> FromForm<'f> for Message<T>
185 | | where T: Deserialize<'f>
186 | | {
187 | | type Error = MessageFormError;
... |
207 | | }
208 | | }
| |_^
我做错了什么,如何正确返回反序列化值?