uds
This commit is contained in:
3
Cargo.lock
generated
3
Cargo.lock
generated
@ -2229,6 +2229,7 @@ dependencies = [
|
|||||||
"ratatui-image",
|
"ratatui-image",
|
||||||
"rklipd",
|
"rklipd",
|
||||||
"serde",
|
"serde",
|
||||||
|
"serde_json",
|
||||||
"uuid",
|
"uuid",
|
||||||
]
|
]
|
||||||
|
|
||||||
@ -2241,6 +2242,8 @@ dependencies = [
|
|||||||
"directories",
|
"directories",
|
||||||
"image",
|
"image",
|
||||||
"rusqlite",
|
"rusqlite",
|
||||||
|
"serde",
|
||||||
|
"serde_json",
|
||||||
"uuid",
|
"uuid",
|
||||||
"wayland-clipboard-listener",
|
"wayland-clipboard-listener",
|
||||||
]
|
]
|
||||||
|
|||||||
@ -11,5 +11,6 @@ image = "0.25.9"
|
|||||||
ratatui = "0.30.0"
|
ratatui = "0.30.0"
|
||||||
ratatui-image = { version = "10.0.6", features = ["crossterm"] }
|
ratatui-image = { version = "10.0.6", features = ["crossterm"] }
|
||||||
rklipd = {path = "rklipd"}
|
rklipd = {path = "rklipd"}
|
||||||
serde = "1.0.228"
|
serde = { version = "1.0.228", features = ["derive"] }
|
||||||
|
serde_json = "1.0.149"
|
||||||
uuid = "1.22.0"
|
uuid = "1.22.0"
|
||||||
|
|||||||
3
rklipd/Cargo.lock
generated
3
rklipd/Cargo.lock
generated
@ -1303,6 +1303,8 @@ dependencies = [
|
|||||||
"directories",
|
"directories",
|
||||||
"image",
|
"image",
|
||||||
"rusqlite",
|
"rusqlite",
|
||||||
|
"serde",
|
||||||
|
"serde_json",
|
||||||
"uuid",
|
"uuid",
|
||||||
"wayland-clipboard-listener",
|
"wayland-clipboard-listener",
|
||||||
]
|
]
|
||||||
@ -1370,6 +1372,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||||||
checksum = "9a8e94ea7f378bd32cbbd37198a4a91436180c5bb472411e48b5ec2e2124ae9e"
|
checksum = "9a8e94ea7f378bd32cbbd37198a4a91436180c5bb472411e48b5ec2e2124ae9e"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"serde_core",
|
"serde_core",
|
||||||
|
"serde_derive",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
|
|||||||
@ -11,6 +11,8 @@ uuid = {version = "1.22.0", features = ["v4", "serde"]}
|
|||||||
rusqlite = "0.38.0"
|
rusqlite = "0.38.0"
|
||||||
wayland-clipboard-listener = "0.6.0"
|
wayland-clipboard-listener = "0.6.0"
|
||||||
directories = "6.0.0"
|
directories = "6.0.0"
|
||||||
|
serde = { version = "1.0.228", features = ["derive"] }
|
||||||
|
serde_json = "1.0.149"
|
||||||
|
|
||||||
[features]
|
[features]
|
||||||
x11 = []
|
x11 = []
|
||||||
|
|||||||
74
rklipd/src/ipc.rs
Normal file
74
rklipd/src/ipc.rs
Normal file
@ -0,0 +1,74 @@
|
|||||||
|
use crate::database::Database;
|
||||||
|
use crate::models::ClipboardData;
|
||||||
|
use serde::{Deserialize, Serialize};
|
||||||
|
use std::fs;
|
||||||
|
use std::io::{Read, Write};
|
||||||
|
use std::os::unix::net::UnixListener;
|
||||||
|
use std::path::Path;
|
||||||
|
use std::sync::{Arc, Mutex};
|
||||||
|
|
||||||
|
// --- LE CONTRAT (Protocole) ---
|
||||||
|
#[derive(Serialize, Deserialize, Debug)]
|
||||||
|
pub enum IpcRequest {
|
||||||
|
GetHistory { limit: usize },
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Serialize, Deserialize, Debug)]
|
||||||
|
pub enum IpcResponse {
|
||||||
|
History(Vec<String>),
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn start_server(db: Arc<Mutex<Database>>, socket_path: &Path) {
|
||||||
|
if socket_path.exists() {
|
||||||
|
let _ = fs::remove_file(socket_path);
|
||||||
|
}
|
||||||
|
|
||||||
|
let listener = match UnixListener::bind(socket_path) {
|
||||||
|
Ok(l) => l,
|
||||||
|
Err(e) => {
|
||||||
|
eprintln!("Error while creating socket {}", e);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
println!("ipc server listening {:?}", socket_path);
|
||||||
|
|
||||||
|
for stream in listener.incoming() {
|
||||||
|
match stream {
|
||||||
|
Ok(mut stream) => {
|
||||||
|
let db_clone = Arc::clone(&db);
|
||||||
|
|
||||||
|
std::thread::spawn(move || {
|
||||||
|
let mut buffer = String::new();
|
||||||
|
|
||||||
|
if stream.read_to_string(&mut buffer).is_ok() {
|
||||||
|
if let Ok(request) = serde_json::from_str::<IpcRequest>(&buffer) {
|
||||||
|
match request {
|
||||||
|
IpcRequest::GetHistory { limit } => {
|
||||||
|
let db_lock = db_clone.lock().unwrap();
|
||||||
|
|
||||||
|
// TODO Implem read_history(limit)
|
||||||
|
let history = db_lock.read_history().unwrap_or_default();
|
||||||
|
|
||||||
|
let items: Vec<String> = history
|
||||||
|
.into_iter()
|
||||||
|
.rev()
|
||||||
|
.take(limit)
|
||||||
|
.map(|entry| match entry.content {
|
||||||
|
ClipboardData::Text(t) => t,
|
||||||
|
ClipboardData::Image(img) => format!("{}.jpg", img.id),
|
||||||
|
})
|
||||||
|
.collect();
|
||||||
|
|
||||||
|
let response = IpcResponse::History(items);
|
||||||
|
let response_json = serde_json::to_string(&response).unwrap();
|
||||||
|
let _ = stream.write_all(response_json.as_bytes());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
Err(e) => eprintln!("Erreur de connexion IPC: {}", e),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -5,6 +5,7 @@ use std::sync::{Arc, Mutex};
|
|||||||
|
|
||||||
mod clipboard;
|
mod clipboard;
|
||||||
mod database;
|
mod database;
|
||||||
|
mod ipc;
|
||||||
mod models;
|
mod models;
|
||||||
mod monitor;
|
mod monitor;
|
||||||
mod ws;
|
mod ws;
|
||||||
@ -18,8 +19,13 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
|
|||||||
|
|
||||||
let db = Arc::new(Mutex::new(Database::init(&dir_path_str)?));
|
let db = Arc::new(Mutex::new(Database::init(&dir_path_str)?));
|
||||||
|
|
||||||
// println!("{:#?}", db.lock().unwrap().read_history());
|
let socket_path = dir_path.join("rklip.sock");
|
||||||
|
let db_for_ipc = Arc::clone(&db);
|
||||||
|
std::thread::spawn(move || {
|
||||||
|
crate::ipc::start_server(db_for_ipc, &socket_path);
|
||||||
|
});
|
||||||
|
|
||||||
|
println!("rklipd starting...");
|
||||||
monitor::start(db, clipboard)?;
|
monitor::start(db, clipboard)?;
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
|
|||||||
12
src/app.rs
12
src/app.rs
@ -1,7 +1,7 @@
|
|||||||
|
use crate::ipc;
|
||||||
use fuzzy_matcher::{FuzzyMatcher, skim::SkimMatcherV2};
|
use fuzzy_matcher::{FuzzyMatcher, skim::SkimMatcherV2};
|
||||||
use ratatui::widgets::ListState;
|
use ratatui::widgets::ListState;
|
||||||
use ratatui_image::{picker::Picker, protocol};
|
use ratatui_image::{picker::Picker, protocol};
|
||||||
use std::path::Path;
|
|
||||||
|
|
||||||
#[derive(PartialEq)]
|
#[derive(PartialEq)]
|
||||||
pub enum Mode {
|
pub enum Mode {
|
||||||
@ -27,13 +27,9 @@ impl App {
|
|||||||
pub fn new() -> Self {
|
pub fn new() -> Self {
|
||||||
let mut list_state = ListState::default();
|
let mut list_state = ListState::default();
|
||||||
list_state.select(Some(0));
|
list_state.select(Some(0));
|
||||||
let items = vec![
|
|
||||||
"Ceci est un texte copié.".to_string(),
|
let items = ipc::fetch_history(100)
|
||||||
"https://github.com/ratatui-org/ratatui".to_string(),
|
.unwrap_or_else(|| vec!["rklipd deamon unaccessible".to_string()]);
|
||||||
"30426b4d-26e0-45af-9fa4-25f4476387a8.jpg".to_string(),
|
|
||||||
"35789d6a-dea4-46de-90da-aee693a16031.jpg".to_string(),
|
|
||||||
"fn main() {\n println!(\"Hello\");\n}".to_string(),
|
|
||||||
];
|
|
||||||
|
|
||||||
let picker = Picker::from_query_stdio().unwrap_or_else(|_| Picker::halfblocks());
|
let picker = Picker::from_query_stdio().unwrap_or_else(|_| Picker::halfblocks());
|
||||||
|
|
||||||
|
|||||||
37
src/ipc.rs
37
src/ipc.rs
@ -0,0 +1,37 @@
|
|||||||
|
use serde::{Deserialize, Serialize};
|
||||||
|
use std::io::{Read, Write};
|
||||||
|
use std::os::unix::net::UnixStream;
|
||||||
|
|
||||||
|
#[derive(Serialize, Deserialize, Debug)]
|
||||||
|
pub enum IpcRequest {
|
||||||
|
GetHistory { limit: usize },
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Serialize, Deserialize, Debug)]
|
||||||
|
pub enum IpcResponse {
|
||||||
|
History(Vec<String>),
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn fetch_history(limit: usize) -> Option<Vec<String>> {
|
||||||
|
let base_dir = directories::ProjectDirs::from("com", "zefad", "rklipd")?
|
||||||
|
.data_dir()
|
||||||
|
.to_path_buf();
|
||||||
|
let socket_path = base_dir.join("rklip.sock");
|
||||||
|
|
||||||
|
if let Ok(mut stream) = UnixStream::connect(&socket_path) {
|
||||||
|
let req = IpcRequest::GetHistory { limit };
|
||||||
|
let req_json = serde_json::to_string(&req).unwrap();
|
||||||
|
|
||||||
|
let _ = stream.write_all(req_json.as_bytes());
|
||||||
|
let _ = stream.shutdown(std::net::Shutdown::Write);
|
||||||
|
|
||||||
|
let mut response_buffer = String::new();
|
||||||
|
if stream.read_to_string(&mut response_buffer).is_ok() {
|
||||||
|
if let Ok(IpcResponse::History(items)) = serde_json::from_str(&response_buffer) {
|
||||||
|
return Some(items);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
None
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user