I am new to rust, I've been trying to spawn a new Tokio thread to insert the Redis key value but I am facing this error
error[E0759]: `self` has an anonymous lifetime `'_` but it needs to satisfy a `'static` lifetime requirement
--> src/main.rs:27:25
|
27 | pub async fn insert(&mut self) {
| ^^^^^^^^^ this data with an anonymous lifetime `'_`...
28 | let th = tokio::spawn(async move {
| ------------ ...is used and required to live as long as `'static` here
|
note: `'static` lifetime requirement introduced by this bound
|
127 | T: Future + Send + 'static,
| ^^^^^^^
error[E0477]: the type `impl Future<Output = [async output]>` does not fulfill the required lifetime
--> src/main.rs:28:18
|
28 | let th = tokio::spawn(async move {
| ^^^^^^^^^^^^
|
note: type must satisfy the static lifetime as required by this binding
|
127 | T: Future + Send + 'static,
| ^^^^^^^
Code:
use std::{error::Error};
use tokio;
use redis::{
AsyncCommands, Client,
};
#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
// 1) Create Connection
let client = Client::open("redis://127.0.0.1:6379")?;
let mut con = client.get_tokio_connection().await?;
let mut cache_ops = CacheOperations::new(&mut con);
cache_ops.insert();
Ok(())
}
struct CacheOperations<'a> {
redis_client: &'a mut redis::aio::Connection,
}
impl<'a> CacheOperatios<'a> {
pub fn new(redis_client: &'a mut redis::aio::Connection) -> Self {
Self { redis_client }
}
pub async fn insert(&mut self) {
let th = tokio::spawn(async move {
let h = self
.redis_client
.set::<String, String, String>("ok final".to_string(), "Hello world!".to_string())
.await;
let result = self
.redis_client
.get::<String, String>("my_key".to_string())
.await;
println!("->> my_key: {:?}\n", result);
});
th.await.unwrap();
}
}
If you wanted to parallelize inserts, then the tokio::spawn call would go outside the insert calls. Additionally, since your insert method takes &mut self, it's impossible to call it from several places in parallel, so you would need to create a separate connection per spawned task.
I don't know what the redis library supports, but if there is, such a solution requires that you can change the insert function to take &self instead of &mut self.
I've never used this redis crate myself, but I've answered someone else's question before and came across MultiplexedConnection and ConnectionManager which claim to support "requests to be be sent concurrently on the same underlying connection". You can clone those handles to a connection (they implement Clone), so each parallel task/thread can have its own clone to call the necessary &mut self methods on concurrently. As mentioned, I've never used this stuff, or "redis" in general, so no guarantees if this will have any of the desired performance benefit you might expect from parallelizing stuff.
I don't remember how I came across them at the time, possibly by looking at the module-level docs of the aio module and seeing those types listed there, then just being curious to find out what those are for. It also was fairly hard to me to find out how to construct those, until I somehow came across the Client struct's methods like "get_tokio_connection_manager" or "get_multiplexed_tokio_connection", etc.