I realize this might be a duplicate question, but I'm unable to find a satisfactory answer.
Let's say I borrow something locally and try to use it for something that has a declared lifetime:
extern crate serde;
extern crate serde_json;
use serde::Deserialize;
pub trait Item: {}
fn transform<'de, ITM: Deserialize<'de> + Item>(item_json: String) -> ITM {
let item_typed: ITM = ::serde_json::from_str(&item_json).unwrap();
item_typed
}
This fails with the following error:
error[E0597]: `item_json` does not live long enough
--> src/main.rs:9:50
|
8 | fn transform<'de, ITM: Deserialize<'de> + Item>(item_json: String) -> ITM {
| --- lifetime `'de` defined here
9 | let item_typed: ITM = ::serde_json::from_str(&item_json).unwrap();
| -----------------------^^^^^^^^^^-
| | |
| | borrowed value does not live long enough
| argument requires that `item_json` is borrowed for `'de`
10 | item_typed
11 | }
| - `item_json` dropped here while still borrowed
Digging in, from_str
wants a reference that lives as long as the lifetime declared for Deserialize
pub fn from_str<'a, T>(s: &'a str) -> Result<T>
where
T: de::Deserialize<'a>, {
from_trait(read::StrRead::new(s))
}
Understandable.
Ok, but how to resolve this?
Changing the signature of the function so it uses a lifetimed &str just kicks the can down the road:
fn transform_str<'de, ITM: Deserialize<'de> + Item + Clone>(item_json: &'de str) -> ITM {
::serde_json::from_str(item_json).unwrap()
}
fn transform<'de, ITM: Deserialize<'de> + Item>(item_json: String) -> ITM {
transform_str(&item_json) //error
}