fix one-off commands

todo: exec_end
Signed-off-by: blob42 <contact@blob42.xyz>
one-off-cmd
blob42 3 months ago
parent 6f1d51615f
commit fb90ec4850

@ -1,8 +1,11 @@
- match multiple patterns
- cmd exec:
[ ] use state machine
[ ] match multiple patterns
[ ] cmd exec:
[x] repeat on cmd failure
[x] disable profile on cmd failure
- exec_end: cmd to execute when process vanishes
- same as not_seen condition !?
[x] exec_end: cmd to execute when matching state ends
[ ] on-off commands
[x] should execute cmd once if `run_once` is true
[ ] should reset the state next time process appears
- conditions:
- resource conditions: ram, cpu, net usage ...

@ -112,7 +112,11 @@ impl Process {
if !matches!(self.state(), ProcState::NeverSeen) {
self.lifetime.prev_state = Some(self.lifetime.state.clone());
self.lifetime.state = ProcState::NotSeen;
self.lifetime.state_exit = true;
if self.lifetime.prev_state != Some(ProcState::NotSeen) {
self.lifetime.state_exit = true;
} else {
self.lifetime.state_exit = false;
}
debug!("<{}>: process disappread", self.pattern);
} else {
self.lifetime.state_exit = false;
@ -130,6 +134,9 @@ impl Process {
ProcState::NotSeen => {
debug!("<{}>: process reappeared", self.pattern);
self.lifetime.state_exit = true;
// reset first_seen
self.lifetime.first_seen = self.lifetime.last_refresh;
}
ProcState::Seen => {
self.lifetime.state_exit = false;
@ -140,7 +147,6 @@ impl Process {
self.lifetime.state = ProcState::Seen;
self.lifetime.last_seen = self.lifetime.last_refresh;
}
dbg!(self.lifetime.state_exit);
}
}

@ -11,7 +11,7 @@ use std::time::Instant;
use sysinfo::{ProcessRefreshKind, RefreshKind, System, UpdateKind};
use crate::config::{CmdSchedule, Profile, ProfileMatching};
use crate::process::{ProcLifetime, ProcState};
use crate::process::ProcLifetime;
use crate::state::{ConditionMatcher, StateTracker};
use super::process::Process;
@ -46,6 +46,8 @@ fn run_cmd(cmd: &mut CmdSchedule, matching: ProfileMatching, exec_end: bool) {
let out = if exec_end && cmd.exec_end.is_some() {
dbg!("run exec_end !");
Command::new(&cmd.exec_end.as_ref().unwrap()[0]).args(&cmd.exec_end.as_ref().unwrap()[1..]).output()
} else if exec_end && cmd.exec_end.is_none() {
return;
} else {
dbg!("running command !");
Command::new(&cmd.exec[0]).args(&cmd.exec[1..]).output()
@ -73,8 +75,6 @@ fn run_cmd(cmd: &mut CmdSchedule, matching: ProfileMatching, exec_end: bool) {
if cmd.run_once {
cmd.disabled = true
}
}
impl Job for ProfileJob<Process> {
@ -83,13 +83,22 @@ impl Job for ProfileJob<Process> {
fn update(&mut self, sysinfo: &System, last_refresh: Instant) {
let _ = self.object.update_state(sysinfo, last_refresh);
// self.profile.commands.iter_mut()
// // only process enabled commands
// .filter(|cmd| cmd.disabled && cmd.run_once)
// .for_each(|cmd| {
// cmd.disabled = false;
// });
// dbg!(&self.object);
dbg!(&self.object);
// run commands when entering match state `exec`
self.profile.commands.iter_mut()
// only process enabled commands
.filter(|cmd| !cmd.disabled)
.filter(|cmd| self.object.matches(cmd.condition.clone()))
.filter(|cmd| dbg!(self.object.matches(cmd.condition.clone())))
.for_each(|cmd| {
debug!("running exec cmd");
// if we should run the exec_end command
// dbg!(&self.object);
@ -102,14 +111,28 @@ impl Job for ProfileJob<Process> {
run_cmd(cmd, self.profile.matching.clone(), false);
});
// run commands on exit of matching state `exec_end`
if self.object.exiting() {
self.profile.commands.iter_mut()
.filter(|cmd| !cmd.disabled)
// .filter(|cmd| !cmd.disabled)
.for_each(|cmd| {
//FIX: current state should be opposite of condition
//ie cond=Seen, exec_end runs when state is NotSeen after Seen
run_cmd(cmd, self.profile.matching.clone(), true);
});
}
// if object does not match since 2 cycles, reset the run_once state
self.profile.commands.iter_mut()
.filter(|cmd| cmd.disabled && cmd.run_once)
.for_each(|cmd| {
if !self.object.matches(cmd.condition.clone()) &&
self.object.prev_state().is_some_and(|s| s == self.object.state()) {
debug!("disabling cmd");
cmd.disabled = false;
}
});
// for cmd in self.profile.commands.iter_mut().filter(|c| !c.disabled) {
// if self.object.matches(cmd.condition.clone()) {
// let _ = run_cmd(cmd, self.profile.matching.clone()).inspect_err(|e|{
@ -203,6 +226,9 @@ impl Scheduler {
trace!("refresh sysinfo");
sleep(Self::SAMPLING_RATE);
#[cfg(debug_assertions)]
let _ = Command::new("clear").spawn();
}
}
}

@ -14,6 +14,7 @@ condition = {seen = "5s"}
exec = ["sh", "-c", "notify-send 'foo seen'"]
# when exec_end is defined the schedule behaves like a toggle
# cmd is executed when exiting condition
exec_end = ["sh", "-c", "notify-send 'foo end'"]
run_once = true

Loading…
Cancel
Save