From c8afbb39844dd94002b0e687b4bad263de6e3e2c Mon Sep 17 00:00:00 2001 From: Andrew Phillips Date: Tue, 26 Aug 2025 18:42:14 -0300 Subject: [PATCH] feat: implement finalization tracking for system plugins Co-authored-by: aider (openai/andrew/openrouter/qwen/qwen3-coder) --- src/meta_plugin/system.rs | 217 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 217 insertions(+) diff --git a/src/meta_plugin/system.rs b/src/meta_plugin/system.rs index 1e9692a..a19404e 100644 --- a/src/meta_plugin/system.rs +++ b/src/meta_plugin/system.rs @@ -48,7 +48,26 @@ impl CwdMetaPlugin { } impl MetaPlugin for CwdMetaPlugin { + fn is_finalized(&self) -> bool { + self.is_finalized + } + + fn set_finalized(&mut self, finalized: bool) { + self.is_finalized = finalized; + } + fn finalize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + + // Mark as finalized + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: true, @@ -60,6 +79,14 @@ impl MetaPlugin for CwdMetaPlugin { } fn initialize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + let mut metadata = Vec::new(); let cwd = match env::current_dir() { Ok(path) => path.to_string_lossy().to_string(), @@ -256,7 +283,26 @@ impl ShellMetaPlugin { } impl MetaPlugin for ShellMetaPlugin { + fn is_finalized(&self) -> bool { + self.is_finalized + } + + fn set_finalized(&mut self, finalized: bool) { + self.is_finalized = finalized; + } + fn finalize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + + // Mark as finalized + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: true, @@ -264,6 +310,14 @@ impl MetaPlugin for ShellMetaPlugin { } fn update(&mut self, _data: &[u8]) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process more data + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: false, @@ -275,6 +329,14 @@ impl MetaPlugin for ShellMetaPlugin { } fn initialize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + let mut metadata = Vec::new(); let shell = match env::var("SHELL") { Ok(shell) => shell, @@ -290,6 +352,9 @@ impl MetaPlugin for ShellMetaPlugin { metadata.push(meta_data); } + // Mark as finalized since this plugin only needs to run once + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata, is_finalized: true, @@ -368,7 +433,26 @@ impl ShellPidMetaPlugin { } impl MetaPlugin for ShellPidMetaPlugin { + fn is_finalized(&self) -> bool { + self.is_finalized + } + + fn set_finalized(&mut self, finalized: bool) { + self.is_finalized = finalized; + } + fn finalize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + + // Mark as finalized + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: true, @@ -376,6 +460,14 @@ impl MetaPlugin for ShellPidMetaPlugin { } fn update(&mut self, _data: &[u8]) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process more data + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: false, @@ -387,6 +479,14 @@ impl MetaPlugin for ShellPidMetaPlugin { } fn initialize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + let mut metadata = Vec::new(); let pid = match env::var("PPID") { Ok(ppid) => ppid, @@ -402,6 +502,9 @@ impl MetaPlugin for ShellPidMetaPlugin { metadata.push(meta_data); } + // Mark as finalized since this plugin only needs to run once + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata, is_finalized: true, @@ -480,7 +583,26 @@ impl KeepPidMetaPlugin { } impl MetaPlugin for KeepPidMetaPlugin { + fn is_finalized(&self) -> bool { + self.is_finalized + } + + fn set_finalized(&mut self, finalized: bool) { + self.is_finalized = finalized; + } + fn finalize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + + // Mark as finalized + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: true, @@ -488,6 +610,14 @@ impl MetaPlugin for KeepPidMetaPlugin { } fn update(&mut self, _data: &[u8]) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process more data + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: false, @@ -499,6 +629,14 @@ impl MetaPlugin for KeepPidMetaPlugin { } fn initialize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + let mut metadata = Vec::new(); let pid = process::id().to_string(); @@ -511,6 +649,9 @@ impl MetaPlugin for KeepPidMetaPlugin { metadata.push(meta_data); } + // Mark as finalized since this plugin only needs to run once + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata, is_finalized: true, @@ -589,7 +730,26 @@ impl HostnameMetaPlugin { } impl MetaPlugin for HostnameMetaPlugin { + fn is_finalized(&self) -> bool { + self.is_finalized + } + + fn set_finalized(&mut self, finalized: bool) { + self.is_finalized = finalized; + } + fn finalize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + + // Mark as finalized + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: true, @@ -597,6 +757,14 @@ impl MetaPlugin for HostnameMetaPlugin { } fn update(&mut self, _data: &[u8]) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process more data + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: false, @@ -608,6 +776,14 @@ impl MetaPlugin for HostnameMetaPlugin { } fn initialize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + let mut metadata = Vec::new(); let hostname = match gethostname().into_string() { Ok(hostname) => hostname, @@ -623,6 +799,9 @@ impl MetaPlugin for HostnameMetaPlugin { metadata.push(meta_data); } + // Mark as finalized since this plugin only needs to run once + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata, is_finalized: true, @@ -701,7 +880,26 @@ impl FullHostnameMetaPlugin { } impl MetaPlugin for FullHostnameMetaPlugin { + fn is_finalized(&self) -> bool { + self.is_finalized + } + + fn set_finalized(&mut self, finalized: bool) { + self.is_finalized = finalized; + } + fn finalize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + + // Mark as finalized + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: true, @@ -709,6 +907,14 @@ impl MetaPlugin for FullHostnameMetaPlugin { } fn update(&mut self, _data: &[u8]) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process more data + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + crate::meta_plugin::MetaPluginResponse { metadata: Vec::new(), is_finalized: false, @@ -720,6 +926,14 @@ impl MetaPlugin for FullHostnameMetaPlugin { } fn initialize(&mut self) -> crate::meta_plugin::MetaPluginResponse { + // If already finalized, don't process again + if self.is_finalized { + return crate::meta_plugin::MetaPluginResponse { + metadata: Vec::new(), + is_finalized: true, + }; + } + let mut metadata = Vec::new(); // For now, use regular hostname since local_ip and lookup_addr aren't available let hostname = match gethostname().into_string() { @@ -736,6 +950,9 @@ impl MetaPlugin for FullHostnameMetaPlugin { metadata.push(meta_data); } + // Mark as finalized since this plugin only needs to run once + self.is_finalized = true; + crate::meta_plugin::MetaPluginResponse { metadata, is_finalized: true,