From 9e84afecbf9dbc7865c8b8b8c0be55bb7fd8d20c Mon Sep 17 00:00:00 2001 From: Lars Wirzenius Date: Thu, 30 Jan 2025 15:36:57 +0200 Subject: [PATCH] feat! change the "Not" event filter to take a list of filters Change the logical negation operator `Not` to take a list of filters as operands. The operator returns true, if and only if all of the operands are false. The syntax is now consistent with logical `And` and `Or`, which simplifies code, and is expected to simplify use. In YAML syntax, `Not` now works like this: ~~~ !Not - !Allow ~~~ Previously, `!Not` only had one operand, so that above would have been expressed as `!Not Allow`. Signed-off-by: Lars Wirzenius --- ci-broker.md | 3 ++- src/filter.rs | 12 ++++++------ src/filter/arbitrary.rs | 2 +- 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/ci-broker.md b/ci-broker.md index b3f56fcd..100d4d9e 100644 --- a/ci-broker.md +++ b/ci-broker.md @@ -1152,7 +1152,8 @@ adapters: triggers: - adapter: default filters: - - !Not Allow + - !Not + - !Allow ~~~ diff --git a/src/filter.rs b/src/filter.rs index 47862567..ad1fe3e8 100644 --- a/src/filter.rs +++ b/src/filter.rs @@ -77,7 +77,7 @@ pub enum EventFilter { Deny, /// Allow the opposite of the contained filter. - Not(#[serde(with = "serde_yml::with::singleton_map")] Box), + Not(Vec), /// Allow if all contained filters allow. And(Vec), @@ -91,7 +91,7 @@ impl EventFilter { match self { Self::Allow => return true, Self::Deny => return false, - Self::Not(expr) => return !expr.allows(event), + Self::Not(expr) => return !expr.iter().any(|e| e.allows(event)), Self::And(exprs) => return exprs.iter().all(|e| e.allows(event)), Self::Or(exprs) => return exprs.iter().any(|e| e.allows(event)), _ => (), @@ -575,7 +575,7 @@ mod test { #[test] fn allows_opposite() { - let filter = EventFilter::Not(Box::new(EventFilter::Deny)); + let filter = EventFilter::Not(vec![EventFilter::Deny]); eprintln!("filter: {filter:#?}"); for e in all_events(did(), rid(), refstring("main"), patch_id(), oid(), oid()).iter() { @@ -612,18 +612,18 @@ mod test { #[test] fn deserialize_yaml_nested_not() { let expected = EventFilter::And(vec![ - EventFilter::Not(Box::new(EventFilter::Repository( + EventFilter::Not(vec![EventFilter::Repository( "rad:z32iyJDyFLqvPFzwHm8YadK4HQ2EY" .parse::() .unwrap(), - ))), + )]), EventFilter::BranchCreated, EventFilter::PatchCreated, ]); let filters = r#" !And - !Not - Repository: rad:z32iyJDyFLqvPFzwHm8YadK4HQ2EY + - !Repository "rad:z32iyJDyFLqvPFzwHm8YadK4HQ2EY" - !BranchCreated - !PatchCreated "#; diff --git a/src/filter/arbitrary.rs b/src/filter/arbitrary.rs index 0989793e..1452e6fc 100644 --- a/src/filter/arbitrary.rs +++ b/src/filter/arbitrary.rs @@ -73,7 +73,7 @@ impl Arbitrary for EventFilter { Variants::Deny => Deny, Variants::Not => { g.set_size(size); - Not(Box::new(Self::arbitrary(g))) + Not(vec![Self::arbitrary(g)]) } Variants::And => { g.set_size(size);