refactor: address 5-pass audit findings for antipatterns, bottlenecks, memory efficiency, and LLM handlers
This commit is contained in:
1 parent
626403900f
commit
924b6d09fa
30 files changed
+1120
-503
No files matched your search
+119
-41
@@ -84,6 +84,96 @@ impl McpTool for WriteClipboardHandler {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_native_clipboard_text() -> Option<String> {
|
||||
if let Ok(mut clipboard) = arboard::Clipboard::new() {
|
||||
if let Ok(text) = clipboard.get_text() {
|
||||
if !text.trim().is_empty() {
|
||||
return Some(text);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let mut cmd_wl = std::process::Command::new("wl-paste");
|
||||
cmd_wl.arg("--no-newline");
|
||||
if std::env::var("WAYLAND_DISPLAY").is_err() && std::path::Path::new("/mnt/wslg/runtime-dir").exists() {
|
||||
cmd_wl.env("WAYLAND_DISPLAY", "wayland-0");
|
||||
cmd_wl.env("XDG_RUNTIME_DIR", "/mnt/wslg/runtime-dir");
|
||||
}
|
||||
if let Ok(output) = cmd_wl.output() {
|
||||
if output.status.success() && !output.stdout.is_empty() {
|
||||
if let Ok(text) = String::from_utf8(output.stdout) {
|
||||
if !text.trim().is_empty() {
|
||||
return Some(text);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let mut cmd_xc = std::process::Command::new("xclip");
|
||||
cmd_xc.args(["-selection", "clipboard", "-o"]);
|
||||
if std::env::var("DISPLAY").is_err() {
|
||||
cmd_xc.env("DISPLAY", ":0");
|
||||
}
|
||||
if let Ok(output) = cmd_xc.output() {
|
||||
if output.status.success() && !output.stdout.is_empty() {
|
||||
if let Ok(text) = String::from_utf8(output.stdout) {
|
||||
if !text.trim().is_empty() {
|
||||
return Some(text);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
None
|
||||
}
|
||||
|
||||
pub fn get_native_clipboard_image() -> Option<image::DynamicImage> {
|
||||
if let Ok(mut clipboard) = arboard::Clipboard::new() {
|
||||
if let Ok(image_data) = clipboard.get_image() {
|
||||
if let Some(img) = ImageBuffer::<image::Rgba<u8>, _>::from_raw(
|
||||
image_data.width as u32,
|
||||
image_data.height as u32,
|
||||
image_data.bytes.into_owned(),
|
||||
) {
|
||||
return Some(image::DynamicImage::ImageRgba8(img));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for mime in &["image/png", "image/jpeg", "image/bmp", "image/tiff"] {
|
||||
let mut cmd_wl = std::process::Command::new("wl-paste");
|
||||
cmd_wl.args(["--type", mime]);
|
||||
if std::env::var("WAYLAND_DISPLAY").is_err() && std::path::Path::new("/mnt/wslg/runtime-dir").exists() {
|
||||
cmd_wl.env("WAYLAND_DISPLAY", "wayland-0");
|
||||
cmd_wl.env("XDG_RUNTIME_DIR", "/mnt/wslg/runtime-dir");
|
||||
}
|
||||
if let Ok(output) = cmd_wl.output() {
|
||||
if output.status.success() && !output.stdout.is_empty() {
|
||||
if let Ok(img) = image::load_from_memory(&output.stdout) {
|
||||
return Some(img);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for mime in &["image/png", "image/jpeg", "image/bmp"] {
|
||||
let mut cmd_xc = std::process::Command::new("xclip");
|
||||
cmd_xc.args(["-selection", "clipboard", "-t", mime, "-o"]);
|
||||
if std::env::var("DISPLAY").is_err() {
|
||||
cmd_xc.env("DISPLAY", ":0");
|
||||
}
|
||||
if let Ok(output) = cmd_xc.output() {
|
||||
if output.status.success() && !output.stdout.is_empty() {
|
||||
if let Ok(img) = image::load_from_memory(&output.stdout) {
|
||||
return Some(img);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
None
|
||||
}
|
||||
|
||||
pub struct ReadClipboardHandler;
|
||||
|
||||
#[async_trait]
|
||||
@@ -104,51 +194,40 @@ impl McpTool for ReadClipboardHandler {
|
||||
tokio::task::spawn_blocking(move || -> crate::error::Result<serde_json::Value> {
|
||||
let mut out = serde_json::Map::new();
|
||||
|
||||
if let Ok(mut clipboard) = arboard::Clipboard::new() {
|
||||
if let Ok(text) = clipboard.get_text() {
|
||||
if !text.trim().is_empty() {
|
||||
out.insert("text".into(), json!(text));
|
||||
}
|
||||
if let Some(text) = get_native_clipboard_text() {
|
||||
out.insert("text".into(), json!(text));
|
||||
}
|
||||
|
||||
if let Some(dynamic_img) = get_native_clipboard_image() {
|
||||
let mut img = dynamic_img;
|
||||
let max_dim = 1024;
|
||||
if img.width() > max_dim || img.height() > max_dim {
|
||||
img = img.resize(max_dim, max_dim, FilterType::Lanczos3);
|
||||
}
|
||||
let rgb_img = img.into_rgb8();
|
||||
|
||||
if let Ok(image_data) = clipboard.get_image() {
|
||||
if let Some(img) = ImageBuffer::<image::Rgba<u8>, _>::from_raw(
|
||||
image_data.width as u32,
|
||||
image_data.height as u32,
|
||||
image_data.bytes.into_owned(),
|
||||
) {
|
||||
let mut dynamic_img = image::DynamicImage::ImageRgba8(img);
|
||||
let max_dim = 1024;
|
||||
if dynamic_img.width() > max_dim || dynamic_img.height() > max_dim {
|
||||
dynamic_img = dynamic_img.resize(max_dim, max_dim, FilterType::Lanczos3);
|
||||
}
|
||||
let rgb_img = dynamic_img.into_rgb8();
|
||||
let cache_dir = dirs::home_dir()
|
||||
.unwrap_or_default()
|
||||
.join(".gemini/mcp_memory/clipboard");
|
||||
let _ = std::fs::create_dir_all(&cache_dir);
|
||||
|
||||
let cache_dir = dirs::home_dir()
|
||||
.unwrap_or_default()
|
||||
.join(".gemini/mcp_memory/clipboard");
|
||||
let _ = std::fs::create_dir_all(&cache_dir);
|
||||
let timestamp = std::time::SystemTime::now()
|
||||
.duration_since(std::time::UNIX_EPOCH)
|
||||
.unwrap()
|
||||
.as_secs();
|
||||
let file_path = cache_dir.join(format!("clipboard_{}.jpg", timestamp));
|
||||
|
||||
let timestamp = std::time::SystemTime::now()
|
||||
.duration_since(std::time::UNIX_EPOCH)
|
||||
.unwrap()
|
||||
.as_secs();
|
||||
let file_path = cache_dir.join(format!("clipboard_{}.jpg", timestamp));
|
||||
if rgb_img
|
||||
.save_with_format(&file_path, image::ImageFormat::Jpeg)
|
||||
.is_ok()
|
||||
{
|
||||
let path_str = file_path.to_string_lossy().to_string();
|
||||
out.insert("image_path".into(), json!(path_str));
|
||||
|
||||
if rgb_img
|
||||
.save_with_format(&file_path, image::ImageFormat::Jpeg)
|
||||
.is_ok()
|
||||
{
|
||||
let path_str = file_path.to_string_lossy().to_string();
|
||||
out.insert("image_path".into(), json!(path_str));
|
||||
|
||||
// Read image bytes for base64 encoding if needed by vision
|
||||
if let Ok(bytes) = std::fs::read(&file_path) {
|
||||
use base64::Engine;
|
||||
let b64 = base64::engine::general_purpose::STANDARD.encode(&bytes);
|
||||
out.insert("image_base64".into(), json!(b64));
|
||||
}
|
||||
}
|
||||
if let Ok(bytes) = std::fs::read(&file_path) {
|
||||
use base64::Engine;
|
||||
let b64 = base64::engine::general_purpose::STANDARD.encode(&bytes);
|
||||
out.insert("image_base64".into(), json!(b64));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -161,7 +240,6 @@ impl McpTool for ReadClipboardHandler {
|
||||
let mut final_obj = result;
|
||||
if let Some(b64) = final_obj.get("image_base64").and_then(|v| v.as_str()) {
|
||||
let b64_str = b64.to_string();
|
||||
// Remove huge base64 string from final user output
|
||||
if let Some(obj) = final_obj.as_object_mut() {
|
||||
obj.remove("image_base64");
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user