From b33d0ef9f9460f92e66951ffa54c3e95af962e75 Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Fri, 20 Oct 2023 12:44:24 +0200 Subject: [PATCH 01/10] refactor: move AdmissionRequest to policy-evaluator Signed-off-by: Fabrizio Sestito --- src/admission_review.rs | 46 +---------------------------------------- 1 file changed, 1 insertion(+), 45 deletions(-) diff --git a/src/admission_review.rs b/src/admission_review.rs index e094a998..404dc4fa 100644 --- a/src/admission_review.rs +++ b/src/admission_review.rs @@ -1,19 +1,6 @@ +use policy_evaluator::admission_request::AdmissionRequest; use policy_evaluator::admission_response::AdmissionResponse; -#[derive(Clone, Debug, Default, serde::Serialize, serde::Deserialize)] -pub(crate) struct GroupVersionKind { - pub group: String, - pub version: String, - pub kind: String, -} - -#[derive(Clone, Debug, serde::Serialize, serde::Deserialize)] -pub(crate) struct GroupVersionResource { - pub group: String, - pub version: String, - pub resource: String, -} - #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)] #[serde(rename_all = "camelCase")] pub(crate) struct AdmissionReview { @@ -49,37 +36,6 @@ impl Default for AdmissionReview { } } } - -#[derive(Clone, Debug, serde::Serialize, serde::Deserialize)] -#[serde(rename_all = "camelCase")] -pub(crate) struct AdmissionRequest { - pub uid: String, - pub kind: GroupVersionKind, - pub resource: GroupVersionResource, - #[serde(skip_serializing_if = "Option::is_none")] - pub sub_resource: Option, - #[serde(skip_serializing_if = "Option::is_none")] - pub request_kind: Option, - #[serde(skip_serializing_if = "Option::is_none")] - pub request_resource: Option, - #[serde(skip_serializing_if = "Option::is_none")] - pub request_sub_resource: Option, - #[serde(skip_serializing_if = "Option::is_none")] - pub name: Option, - #[serde(skip_serializing_if = "Option::is_none")] - pub namespace: Option, - pub operation: String, - pub user_info: k8s_openapi::api::authentication::v1::UserInfo, - #[serde(skip_serializing_if = "Option::is_none")] - pub object: Option, - #[serde(skip_serializing_if = "Option::is_none")] - pub old_object: Option, - #[serde(skip_serializing_if = "Option::is_none")] - pub dry_run: Option, - #[serde(skip_serializing_if = "Option::is_none")] - pub options: Option, -} - #[cfg(test)] pub(crate) mod tests { use super::*; From f9c6c5c5c6e55c090e55201de9a956517941aa05 Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Fri, 20 Oct 2023 12:47:59 +0200 Subject: [PATCH 02/10] feat: add RawReviewRequest and RawReviewResponse types Signed-off-by: Fabrizio Sestito --- src/main.rs | 1 + src/raw_review.rs | 18 ++++++++++++++++++ 2 files changed, 19 insertions(+) create mode 100644 src/raw_review.rs diff --git a/src/main.rs b/src/main.rs index 5784151c..27cbac94 100644 --- a/src/main.rs +++ b/src/main.rs @@ -15,6 +15,7 @@ mod admission_review; mod api; mod cli; mod metrics; +mod raw_review; mod server; mod settings; mod worker; diff --git a/src/raw_review.rs b/src/raw_review.rs new file mode 100644 index 00000000..8a8ca0c6 --- /dev/null +++ b/src/raw_review.rs @@ -0,0 +1,18 @@ +use policy_evaluator::admission_response::AdmissionResponse; +use serde::{Deserialize, Serialize}; + +#[derive(Serialize, Deserialize, Debug)] +pub(crate) struct RawReviewRequest { + pub(crate) request: serde_json::Value, +} + +#[derive(Serialize, Deserialize, Debug)] +pub(crate) struct RawReviewResponse { + pub(crate) response: AdmissionResponse, +} + +impl RawReviewResponse { + pub(crate) fn new(response: AdmissionResponse) -> Self { + RawReviewResponse { response } + } +} From 00838b52437d6890888a0cf0485ff0c317ff03a1 Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Fri, 20 Oct 2023 12:49:53 +0200 Subject: [PATCH 03/10] feat: add RawPolicyEvaluation metric, refactor metrics related functions with generics Signed-off-by: Fabrizio Sestito --- src/metrics/mod.rs | 32 +++++++++++++++++++++++ src/metrics/policy_evaluations_latency.rs | 5 ++-- src/metrics/policy_evaluations_total.rs | 5 ++-- 3 files changed, 38 insertions(+), 4 deletions(-) diff --git a/src/metrics/mod.rs b/src/metrics/mod.rs index e0f6aa50..53baeda0 100644 --- a/src/metrics/mod.rs +++ b/src/metrics/mod.rs @@ -21,6 +21,8 @@ pub(crate) fn init_meter() -> metrics::Result { .build() } +pub trait PolicyEvaluationMetric: Into> {} + #[derive(Clone)] pub struct PolicyEvaluation { pub(crate) policy_name: String, @@ -33,6 +35,8 @@ pub struct PolicyEvaluation { pub(crate) error_code: Option, } +impl PolicyEvaluationMetric for &PolicyEvaluation {} + #[allow(clippy::from_over_into)] impl Into> for &PolicyEvaluation { fn into(self) -> Vec { @@ -59,3 +63,31 @@ impl Into> for &PolicyEvaluation { baggage } } + +#[derive(Clone)] +pub struct RawPolicyEvaluation { + pub(crate) policy_name: String, + pub(crate) policy_mode: String, + pub(crate) accepted: bool, + pub(crate) mutated: bool, + pub(crate) error_code: Option, +} + +impl PolicyEvaluationMetric for &RawPolicyEvaluation {} + +#[allow(clippy::from_over_into)] +impl Into> for &RawPolicyEvaluation { + fn into(self) -> Vec { + let mut baggage = vec![ + KeyValue::new("policy_name", self.policy_name.clone()), + KeyValue::new("policy_mode", self.policy_mode.clone()), + KeyValue::new("accepted", self.accepted), + KeyValue::new("mutated", self.mutated), + ]; + + if let Some(error_code) = self.error_code { + baggage.append(&mut vec![KeyValue::new("error_code", error_code as i64)]); + } + baggage + } +} diff --git a/src/metrics/policy_evaluations_latency.rs b/src/metrics/policy_evaluations_latency.rs index 2c4446e7..c4ef9e32 100644 --- a/src/metrics/policy_evaluations_latency.rs +++ b/src/metrics/policy_evaluations_latency.rs @@ -1,9 +1,10 @@ -use crate::metrics::PolicyEvaluation; use lazy_static::lazy_static; use opentelemetry::{metrics::Histogram, KeyValue}; use std::convert::TryFrom; use std::time::Duration; +use super::PolicyEvaluationMetric; + lazy_static! { static ref POLICY_EVALUATION_LATENCY: Histogram = opentelemetry::global::meter(super::METER_NAME) @@ -11,7 +12,7 @@ lazy_static! { .init(); } -pub fn record_policy_latency(latency: Duration, policy_evaluation: &PolicyEvaluation) { +pub fn record_policy_latency(latency: Duration, policy_evaluation: impl PolicyEvaluationMetric) { let millis_latency = u64::try_from(latency.as_millis()).unwrap_or(u64::MAX); POLICY_EVALUATION_LATENCY.record( millis_latency, diff --git a/src/metrics/policy_evaluations_total.rs b/src/metrics/policy_evaluations_total.rs index fba5a417..a13562d4 100644 --- a/src/metrics/policy_evaluations_total.rs +++ b/src/metrics/policy_evaluations_total.rs @@ -1,7 +1,8 @@ -use crate::metrics::PolicyEvaluation; use lazy_static::lazy_static; use opentelemetry::{metrics::Counter, KeyValue}; +use super::PolicyEvaluationMetric; + lazy_static! { static ref POLICY_EVALUATIONS_TOTAL: Counter = opentelemetry::global::meter(super::METER_NAME) @@ -9,6 +10,6 @@ lazy_static! { .init(); } -pub fn add_policy_evaluation(policy_evaluation: &PolicyEvaluation) { +pub fn add_policy_evaluation(policy_evaluation: impl PolicyEvaluationMetric) { POLICY_EVALUATIONS_TOTAL.add(1, &Into::>::into(policy_evaluation)); } From bcedd79644ccbedfc783cc12ac2cbb43f385496f Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Fri, 20 Oct 2023 12:50:23 +0200 Subject: [PATCH 04/10] feat: add raw policy logic in worker evaluate Signed-off-by: Fabrizio Sestito --- src/communication.rs | 4 +- src/worker.rs | 145 +++++++++++++++++++++++-------------------- 2 files changed, 78 insertions(+), 71 deletions(-) diff --git a/src/communication.rs b/src/communication.rs index 3b584e17..356e531d 100644 --- a/src/communication.rs +++ b/src/communication.rs @@ -1,9 +1,9 @@ use anyhow::Result; use policy_evaluator::admission_response::AdmissionResponse; +use policy_evaluator::policy_evaluator::ValidateRequest; use std::collections::HashMap; use tokio::sync::oneshot; -use crate::admission_review::AdmissionRequest; use crate::policy_downloader::FetchedPolicies; use crate::settings::Policy; @@ -16,7 +16,7 @@ pub(crate) enum RequestOrigin { #[derive(Debug)] pub(crate) struct EvalRequest { pub policy_id: String, - pub req: AdmissionRequest, + pub req: ValidateRequest, pub resp_chan: oneshot::Sender>, pub parent_span: tracing::Span, pub request_origin: RequestOrigin, diff --git a/src/worker.rs b/src/worker.rs index a3222a81..9ce59e36 100644 --- a/src/worker.rs +++ b/src/worker.rs @@ -11,7 +11,7 @@ use tokio::sync::mpsc::{Receiver, Sender}; use tracing::{error, info, info_span}; use crate::communication::{EvalRequest, RequestOrigin}; -use crate::metrics; +use crate::metrics::{self}; use crate::settings::{Policy, PolicyMode}; use crate::worker_pool::PrecompiledPolicies; @@ -173,82 +173,82 @@ impl Worker { } fn evaluate(req: EvalRequest, pes: &mut PolicyEvaluatorWithSettings) -> anyhow::Result<()> { - match serde_json::to_value(req.req.clone()) { - Ok(json) => { - let start_time = Instant::now(); - - let policy_name = pes.policy_evaluator.policy_id(); - let policy_mode = pes.policy_mode.clone(); - let allowed_to_mutate = pes.allowed_to_mutate; - let vanilla_validation_response = - pes.policy_evaluator.validate(ValidateRequest::new(json)); - let policy_evaluation_duration = start_time.elapsed(); - let error_code = if let Some(status) = &vanilla_validation_response.status { - status.code - } else { - None - }; - let validation_response = match req.request_origin { - RequestOrigin::Validate => Worker::validation_response_with_constraints( - &req.policy_id, - &policy_mode, - allowed_to_mutate, - vanilla_validation_response.clone(), - ), - RequestOrigin::Audit => vanilla_validation_response.clone(), + let start_time = Instant::now(); + + let policy_name = pes.policy_evaluator.policy_id(); + let policy_mode = pes.policy_mode.clone(); + let allowed_to_mutate = pes.allowed_to_mutate; + let vanilla_validation_response = pes.policy_evaluator.validate(req.req.clone()); + let policy_evaluation_duration = start_time.elapsed(); + let accepted = vanilla_validation_response.allowed; + let mutated = vanilla_validation_response.patch.is_some(); + let error_code = if let Some(status) = &vanilla_validation_response.status { + status.code + } else { + None + }; + + let mut validation_response = match req.request_origin { + RequestOrigin::Validate => Worker::validation_response_with_constraints( + &req.policy_id, + &policy_mode, + allowed_to_mutate, + vanilla_validation_response.clone(), + ), + RequestOrigin::Audit => vanilla_validation_response.clone(), + }; + + match req.req.clone() { + ValidateRequest::AdmissionRequest(adm_req) => { + if let Some(namespace) = &pes.always_accept_admission_reviews_on_namespace { + // If the policy server is configured to + // always accept admission reviews on a + // given namespace, just set the `allowed` + // part of the response to `true` if the + // request matches this namespace. Keep + // the rest of the behaviors unchanged, + // such as checking if the policy is + // allowed to mutate. + + if adm_req.namespace == Some(namespace.to_string()) { + validation_response = AdmissionResponse { + allowed: true, + status: None, + ..validation_response + }; + } + } + + let policy_evaluation = metrics::PolicyEvaluation { + policy_name, + policy_mode: policy_mode.into(), + resource_namespace: adm_req.clone().namespace, + resource_kind: adm_req.clone().request_kind.unwrap_or_default().kind, + resource_request_operation: adm_req.clone().operation, + accepted, + mutated, + error_code, }; - let validation_response = - if let Some(namespace) = &pes.always_accept_admission_reviews_on_namespace { - // If the policy server is configured to - // always accept admission reviews on a - // given namespace, just set the `allowed` - // part of the response to `true` if the - // request matches this namespace. Keep - // the rest of the behaviors unchanged, - // such as checking if the policy is - // allowed to mutate. - - if req.req.namespace == Some(namespace.to_string()) { - AdmissionResponse { - allowed: true, - status: None, - ..validation_response - } - } else { - validation_response - } - } else { - validation_response - }; + metrics::record_policy_latency(policy_evaluation_duration, &policy_evaluation); + metrics::add_policy_evaluation(&policy_evaluation); + } + ValidateRequest::Raw(_) => { let accepted = vanilla_validation_response.allowed; let mutated = vanilla_validation_response.patch.is_some(); - let res = req.resp_chan.send(Some(validation_response)); - let policy_evaluation = metrics::PolicyEvaluation { + let policy_evaluation = metrics::RawPolicyEvaluation { policy_name, policy_mode: policy_mode.into(), - resource_namespace: req.req.namespace, - resource_kind: req.req.request_kind.unwrap_or_default().kind, - resource_request_operation: req.req.operation, accepted, mutated, error_code, }; metrics::record_policy_latency(policy_evaluation_duration, &policy_evaluation); metrics::add_policy_evaluation(&policy_evaluation); - res.map_err(|_| anyhow!("cannot send response back")) - } - Err(e) => { - let error_msg = format!("Failed to serialize AdmissionReview: {e:?}"); - error!("{}", error_msg); - req.resp_chan - .send(Some(AdmissionResponse::reject( - req.policy_id, - error_msg, - warp::http::StatusCode::BAD_REQUEST.as_u16(), - ))) - .map_err(|_| anyhow!("cannot send response back")) } - } + }; + + let res = req.resp_chan.send(Some(validation_response)); + res.map_err(|_| anyhow!("cannot send response back")) } } @@ -622,10 +622,13 @@ mod tests { #[case] request_origin: RequestOrigin, ) { let (tx, mut rx) = oneshot::channel::>(); + let req = ValidateRequest::AdmissionRequest( + build_admission_review().request.expect("no request"), + ); let eval_req = EvalRequest { policy_id: "test_policy1".to_string(), - req: build_admission_review().request.expect("no request"), + req, resp_chan: tx, parent_span: tracing::Span::none(), request_origin, @@ -661,10 +664,13 @@ mod tests { #[case] accept: bool, ) { let (tx, mut rx) = oneshot::channel::>(); + let req = ValidateRequest::AdmissionRequest( + build_admission_review().request.expect("no request"), + ); let eval_req = EvalRequest { policy_id: "test_policy1".to_string(), - req: build_admission_review().request.expect("no request"), + req, resp_chan: tx, parent_span: tracing::Span::none(), request_origin, @@ -714,8 +720,9 @@ mod tests { let allowed_namespace = "kubewarden_special".to_string(); - let mut req = build_admission_review().request.expect("no request"); - req.namespace = Some(allowed_namespace.clone()); + let mut request = build_admission_review().request.expect("no request"); + request.namespace = Some(allowed_namespace.clone()); + let req = ValidateRequest::AdmissionRequest(request); let eval_req = EvalRequest { policy_id: "test_policy1".to_string(), From d5cf4b261f0ca52c752c7173bae5ee2fecbe0087 Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Fri, 20 Oct 2023 12:50:39 +0200 Subject: [PATCH 05/10] feat: add validate_raw api endpoint Signed-off-by: Fabrizio Sestito --- src/api/audit_and_validation.rs | 93 +++++++++++++++++++++++++++------ src/api/mod.rs | 5 +- src/server.rs | 16 +++++- 3 files changed, 95 insertions(+), 19 deletions(-) diff --git a/src/api/audit_and_validation.rs b/src/api/audit_and_validation.rs index b87d1f84..fc824979 100644 --- a/src/api/audit_and_validation.rs +++ b/src/api/audit_and_validation.rs @@ -1,3 +1,5 @@ +use crate::raw_review::{RawReviewRequest, RawReviewResponse}; +use policy_evaluator::{admission_response::AdmissionResponse, policy_evaluator::ValidateRequest}; use std::convert::Infallible; use tokio::sync::{mpsc, oneshot}; use tracing::{debug, error, span::Span, warn}; @@ -7,8 +9,11 @@ use super::{ populate_span_with_admission_request_data, populate_span_with_policy_evaluation_results, ServerErrorResponse, }; -use crate::admission_review::AdmissionReview; -use crate::communication::{EvalRequest, RequestOrigin}; + +use crate::{ + admission_review::AdmissionReview, + communication::{EvalRequest, RequestOrigin}, +}; // note about tracing: we are manually adding the `policy_id` field // because otherwise the automatic "export" would cause the string to be @@ -43,7 +48,7 @@ pub(crate) async fn audit( tx: mpsc::Sender, ) -> Result { let request_origin = crate::communication::RequestOrigin::Audit; - evaluate(policy_id, admission_review, tx, request_origin).await + extract_admission_request_and_evaluate(policy_id, admission_review, tx, request_origin).await } // note about tracing: we are manually adding the `policy_id` field @@ -79,10 +84,39 @@ pub(crate) async fn validation( tx: mpsc::Sender, ) -> Result { let request_origin = crate::communication::RequestOrigin::Validate; - evaluate(policy_id, admission_review, tx, request_origin).await + extract_admission_request_and_evaluate(policy_id, admission_review, tx, request_origin).await } -pub(crate) async fn evaluate( +#[tracing::instrument( + name = "validation_raw", + fields( + request_uid=tracing::field::Empty, + host=crate::cli::HOSTNAME.as_str(), + policy_id=policy_id.as_str(), + allowed=tracing::field::Empty, + mutated=tracing::field::Empty, + response_code=tracing::field::Empty, + response_message=tracing::field::Empty, + ), + skip_all)] +pub(crate) async fn validation_raw( + policy_id: String, + raw_review: RawReviewRequest, + tx: mpsc::Sender, +) -> Result { + debug!(payload = %serde_json::to_string(&raw_review).unwrap().as_str()); + + let request_origin = crate::communication::RequestOrigin::Validate; + evaluate( + policy_id, + ValidateRequest::Raw(raw_review.request), + tx, + request_origin, + ) + .await +} + +async fn extract_admission_request_and_evaluate( policy_id: String, admission_review: AdmissionReview, tx: mpsc::Sender, @@ -106,10 +140,25 @@ pub(crate) async fn evaluate( }; populate_span_with_admission_request_data(&adm_req); + evaluate( + policy_id, + ValidateRequest::AdmissionRequest(adm_req), + tx, + request_origin, + ) + .await +} + +async fn evaluate( + policy_id: String, + request: ValidateRequest, + tx: mpsc::Sender, + request_origin: RequestOrigin, +) -> Result, Infallible> { let (resp_tx, resp_rx) = oneshot::channel(); let eval_req = EvalRequest { policy_id, - req: adm_req, + req: request.clone(), resp_chan: resp_tx, parent_span: Span::current(), request_origin, @@ -127,16 +176,14 @@ pub(crate) async fn evaluate( let res = resp_rx.await; match res { - Ok(r) => match r { - Some(vr) => { - populate_span_with_policy_evaluation_results(&vr); - let admission_review = AdmissionReview::new_with_response(vr); - debug!(response =? admission_review, "policy evaluated"); + Ok(response) => match response { + Some(admission_response) => { + populate_span_with_policy_evaluation_results(&admission_response); - Ok(warp::reply::with_status( - warp::reply::json(&admission_review), - StatusCode::OK, - )) + let response = build_response(request, admission_response.clone()); + debug!(response =? &admission_response, "policy evaluated"); + + Ok(warp::reply::with_status(response, StatusCode::OK)) } None => { let message = String::from("requested policy not known"); @@ -166,6 +213,22 @@ pub(crate) async fn evaluate( } } +fn build_response( + request: ValidateRequest, + admission_response: AdmissionResponse, +) -> warp::reply::Json { + match request { + ValidateRequest::AdmissionRequest(_) => { + let admission_review = AdmissionReview::new_with_response(admission_response); + warp::reply::json(&admission_review) + } + ValidateRequest::Raw(_) => { + let admission_response = RawReviewResponse::new(admission_response); + warp::reply::json(&admission_response) + } + } +} + #[cfg(test)] mod tests { use crate::admission_review::tests::build_admission_review; diff --git a/src/api/mod.rs b/src/api/mod.rs index 13752624..3a38921f 100644 --- a/src/api/mod.rs +++ b/src/api/mod.rs @@ -1,12 +1,11 @@ +use policy_evaluator::admission_request::AdmissionRequest; use policy_evaluator::admission_response::AdmissionResponse; use std::convert::Infallible; use tracing::span::Span; use warp::http::StatusCode; -use crate::admission_review::AdmissionRequest; - mod audit_and_validation; -pub(crate) use audit_and_validation::{audit, validation}; +pub(crate) use audit_and_validation::{audit, validation, validation_raw}; pub(crate) fn populate_span_with_admission_request_data(adm_req: &AdmissionRequest) { Span::current().record("kind", adm_req.kind.kind.as_str()); diff --git a/src/server.rs b/src/server.rs index 080a3e18..58f9e730 100644 --- a/src/server.rs +++ b/src/server.rs @@ -38,7 +38,10 @@ mod filters { pub(crate) fn routes( api_tx: Sender, ) -> impl Filter + Clone { - validate(api_tx.clone()).or(audit(api_tx)).or(readiness()) + validate(api_tx.clone()) + .or(validate_raw(api_tx.clone())) + .or(audit(api_tx)) + .or(readiness()) } fn validate( @@ -52,6 +55,17 @@ mod filters { .and_then(crate::api::validation) } + fn validate_raw( + api_tx: Sender, + ) -> impl Filter + Clone { + // POST /validate_raw/:policy_id with JSON body + warp::path!("validate_raw" / String) + .and(warp::post()) + .and(warp::body::json()) + .and(warp::any().map(move || api_tx.clone())) + .and_then(crate::api::validation_raw) + } + fn audit( api_tx: Sender, ) -> impl Filter + Clone { From 8b4f7fd88e0cecd95b0e7ec5123f41ee5591e5f5 Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Fri, 20 Oct 2023 12:51:13 +0200 Subject: [PATCH 06/10] test: add unit tests Signed-off-by: Fabrizio Sestito --- src/api/audit_and_validation.rs | 66 ++++++++++++++++++++++++++++++ src/worker.rs | 72 +++++++++++++++++++++++++++++++++ 2 files changed, 138 insertions(+) diff --git a/src/api/audit_and_validation.rs b/src/api/audit_and_validation.rs index fc824979..76a08904 100644 --- a/src/api/audit_and_validation.rs +++ b/src/api/audit_and_validation.rs @@ -389,4 +389,70 @@ mod tests { .expect("cannot send back evaluation response"); } } + + #[tokio::test] + async fn success_raw() { + let (tx, mut rx) = mpsc::channel::(1); + + let policy_id = "test_policy".to_string(); + let raw_review = RawReviewRequest { + request: serde_json::json!(r#"{"foo": "bar"}"#), + }; + + tokio::spawn(async move { + let response = validation_raw(policy_id, raw_review, tx) + .await + .expect("validation should not fail") + .into_response(); + + assert_eq!(response.status(), StatusCode::OK); + }); + + while let Some(eval_req) = rx.recv().await { + assert!(matches!( + eval_req.request_origin, + crate::communication::RequestOrigin::Validate + )); + let admission_response = AdmissionResponse { + uid: "test_uid".to_string(), + allowed: true, + ..Default::default() + }; + eval_req + .resp_chan + .send(Some(admission_response)) + .expect("cannot send back evaluation response"); + } + } + + #[tokio::test] + async fn requested_policy_not_found_raw() { + let (tx, mut rx) = mpsc::channel::(1); + + let policy_id = "test_policy".to_string(); + let raw_review = RawReviewRequest { + request: serde_json::json!(r#"{"foo": "bar"}"#), + }; + + tokio::spawn(async move { + let response = validation_raw(policy_id, raw_review, tx) + .await + .expect("validation should not fail") + .into_response(); + + assert_eq!(response.status(), StatusCode::NOT_FOUND); + }); + + while let Some(eval_req) = rx.recv().await { + assert!(matches!( + eval_req.request_origin, + crate::communication::RequestOrigin::Validate + )); + + eval_req + .resp_chan + .send(None) + .expect("cannot send back evaluation response"); + } + } } diff --git a/src/worker.rs b/src/worker.rs index 9ce59e36..d5fb5693 100644 --- a/src/worker.rs +++ b/src/worker.rs @@ -705,6 +705,78 @@ mod tests { } } + #[test] + fn evaluate_policy_evaluator_accepts_request_raw() { + let (tx, mut rx) = oneshot::channel::>(); + + let request = serde_json::json!(r#"{"foo": "bar"}"#); + let req = ValidateRequest::Raw(request.clone()); + + let eval_req = EvalRequest { + policy_id: "test_policy1".to_string(), + req, + resp_chan: tx, + parent_span: tracing::Span::none(), + request_origin: RequestOrigin::Validate, + }; + + let mock_evaluator = MockPolicyEvaluator::new_allowed(); + let mut pes = PolicyEvaluatorWithSettings { + policy_evaluator: Box::new(mock_evaluator), + policy_mode: PolicyMode::Protect, + allowed_to_mutate: false, + always_accept_admission_reviews_on_namespace: None, + }; + + let result = Worker::evaluate(eval_req, &mut pes); + assert!(result.is_ok()); + + let response = rx + .try_recv() + .expect("Got an error") + .expect("expected a AdmissionResponse object"); + assert!(response.allowed); + } + + #[test] + fn evaluate_policy_evaluator_rejects_request_raw() { + let (tx, mut rx) = oneshot::channel::>(); + + let request = serde_json::json!(r#"{"foo": "bar"}"#); + let req = ValidateRequest::Raw(request.clone()); + + let eval_req = EvalRequest { + policy_id: "test_policy1".to_string(), + req, + resp_chan: tx, + parent_span: tracing::Span::none(), + request_origin: RequestOrigin::Validate, + }; + + let message = Some("boom".to_string()); + let code = Some(500); + let mock_evaluator = MockPolicyEvaluator::new_rejected(message.clone(), code); + let mut pes = PolicyEvaluatorWithSettings { + policy_evaluator: Box::new(mock_evaluator), + policy_mode: PolicyMode::Protect, + allowed_to_mutate: false, + always_accept_admission_reviews_on_namespace: None, + }; + + let result = Worker::evaluate(eval_req, &mut pes); + assert!(result.is_ok()); + + let response = rx + .try_recv() + .expect("Got an error") + .expect("expected a AdmissionResponse object"); + + assert!(!response.allowed); + let response_status = response.status.expect("should be set"); + assert_eq!(response_status.message, message); + assert_eq!(response_status.code, code); + } + #[rstest] #[test] #[case(RequestOrigin::Validate)] From ab31d7f5134da8289ea3dec3ca20c09ca7fcc379 Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Fri, 20 Oct 2023 12:59:38 +0200 Subject: [PATCH 07/10] chore: apply cargo clippy suggestions to tests Signed-off-by: Fabrizio Sestito --- src/policy_downloader.rs | 8 ++++---- src/settings.rs | 2 +- src/worker_pool.rs | 6 +++--- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/policy_downloader.rs b/src/policy_downloader.rs index 8eab4c6c..c60801f2 100644 --- a/src/policy_downloader.rs +++ b/src/policy_downloader.rs @@ -311,7 +311,7 @@ mod tests { url: registry://ghcr.io/kubewarden/tests/pod-privileged:v0.1.9 "#; - let mut policies: HashMap = + let policies: HashMap = serde_yaml::from_str(policies_cfg).expect("Cannot parse policy cfg"); let policy_download_dir = TempDir::new().expect("Cannot create temp dir"); @@ -328,7 +328,7 @@ mod tests { .lock() .unwrap() .download_policies( - &mut policies, + &policies, policy_download_dir.path().to_str().unwrap(), Some(&verification_config), ) @@ -358,7 +358,7 @@ mod tests { url: registry://ghcr.io/kubewarden/tests/pod-privileged:v0.1.9 "#; - let mut policies: HashMap = + let policies: HashMap = serde_yaml::from_str(policies_cfg).expect("Cannot parse policy cfg"); let policy_download_dir = TempDir::new().expect("Cannot create temp dir"); @@ -375,7 +375,7 @@ mod tests { .lock() .unwrap() .download_policies( - &mut policies, + &policies, policy_download_dir.path().to_str().unwrap(), Some(&verification_config), ) diff --git a/src/settings.rs b/src/settings.rs index 8824cd8d..d52d86ef 100644 --- a/src/settings.rs +++ b/src/settings.rs @@ -143,7 +143,7 @@ example: assert!(!policies2.is_empty()); let policy2 = policies2.get("example").unwrap(); - assert_eq!(policy2.allowed_to_mutate.unwrap(), false); + assert!(!policy2.allowed_to_mutate.unwrap()); assert!(policy2.settings.is_some()); } diff --git a/src/worker_pool.rs b/src/worker_pool.rs index d1cc8031..0abbb8ba 100644 --- a/src/worker_pool.rs +++ b/src/worker_pool.rs @@ -500,9 +500,9 @@ mod tests { fn generate_metadata(major: u64, minor: u64, patch: u64) -> Metadata { let minimum_kubewarden_version = Version { - major: major, - minor: minor, - patch: patch, + major, + minor, + patch, pre: Prerelease::EMPTY, build: BuildMetadata::EMPTY, }; From ca5e6dd7ed0437614af96eab69fe48a30e4a8007 Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Fri, 20 Oct 2023 16:08:38 +0200 Subject: [PATCH 08/10] docs: add docstrings Signed-off-by: Fabrizio Sestito --- src/raw_review.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/raw_review.rs b/src/raw_review.rs index 8a8ca0c6..4002f19c 100644 --- a/src/raw_review.rs +++ b/src/raw_review.rs @@ -1,11 +1,13 @@ use policy_evaluator::admission_response::AdmissionResponse; use serde::{Deserialize, Serialize}; +/// A review request that contains a raw json value. #[derive(Serialize, Deserialize, Debug)] pub(crate) struct RawReviewRequest { pub(crate) request: serde_json::Value, } +/// A review response from a raw policy evaluation. #[derive(Serialize, Deserialize, Debug)] pub(crate) struct RawReviewResponse { pub(crate) response: AdmissionResponse, From dbd7d283304f0d9ab8dd93fc9dbc33b7c63fabf5 Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Mon, 23 Oct 2023 09:31:02 +0200 Subject: [PATCH 09/10] test: add e2e tests Signed-off-by: Fabrizio Sestito --- e2e-tests/07-raw-policies.yml | 115 ++++++++++++++++++++++++ e2e-tests/test_data/policies.yaml | 43 +++++++++ e2e-tests/test_data/raw_mutation.json | 3 + e2e-tests/test_data/raw_validation.json | 3 + 4 files changed, 164 insertions(+) create mode 100644 e2e-tests/07-raw-policies.yml create mode 100644 e2e-tests/test_data/raw_mutation.json create mode 100644 e2e-tests/test_data/raw_validation.json diff --git a/e2e-tests/07-raw-policies.yml b/e2e-tests/07-raw-policies.yml new file mode 100644 index 00000000..32b3a27c --- /dev/null +++ b/e2e-tests/07-raw-policies.yml @@ -0,0 +1,115 @@ +name: Raw policies execution + +testcases: + - name: fixtures + steps: + - type: readfile + path: ./test_data/raw_validation.json + assertions: + - result.err ShouldBeEmpty + vars: + raw_validation: + from: result.content + - type: readfile + path: ./test_data/raw_mutation.json + assertions: + - result.err ShouldBeEmpty + vars: + raw_mutation: + from: result.content + + - name: Raw waPC validation policy works as expected + steps: + - name: Accept + type: http + method: POST + url: http://localhost:3000/validate_raw/raw-validation + headers: + Content-Type: application/json + body: "{{ .fixtures.raw_validation }}" + assertions: + - result.statuscode ShouldEqual 200 + - result.bodyjson.response.allowed ShouldEqual true + - result.bodyjson.response.status.code ShouldNotEqual 500 + - result.bodyjson.response ShouldNotContainKey patch + - result.bodyjson.response ShouldNotContainKey patchType + + - name: Raw waPC mutation policy accepts without mutating + steps: + - name: Accept + type: http + method: POST + url: http://localhost:3000/validate_raw/raw-mutation + headers: + Content-Type: application/json + body: "{{ .fixtures.raw_validation }}" + assertions: + - result.statuscode ShouldEqual 200 + - result.bodyjson.response.allowed ShouldEqual true + - result.bodyjson.response.status.code ShouldNotEqual 500 + - result.bodyjson.response ShouldNotContainKey patch + - result.bodyjson.response ShouldNotContainKey patchType + + - name: Raw waPC mutation policy mutates the request + steps: + - name: Accept + type: http + method: POST + url: http://localhost:3000/validate_raw/raw-mutation + headers: + Content-Type: application/json + body: "{{ .fixtures.raw_mutation }}" + assertions: + - result.statuscode ShouldEqual 200 + - result.bodyjson.response.allowed ShouldEqual true + - result.bodyjson.response.status.code ShouldNotEqual 500 + - result.bodyjson.response ShouldContainKey patch + - result.bodyjson.response ShouldContainKey patchType + + - name: Raw OPA validation policy works as expected + steps: + - name: Accept + type: http + method: POST + url: http://localhost:3000/validate_raw/raw-validation-opa + headers: + Content-Type: application/json + body: "{{ .fixtures.raw_validation }}" + assertions: + - result.statuscode ShouldEqual 200 + - result.bodyjson.response.allowed ShouldEqual true + - result.bodyjson.response.status.code ShouldNotEqual 500 + - result.bodyjson.response ShouldNotContainKey patch + - result.bodyjson.response ShouldNotContainKey patchType + + - name: Raw WASI validation policy works as expected + steps: + - name: Accept + type: http + method: POST + url: http://localhost:3000/validate_raw/raw-validation-wasi + headers: + Content-Type: application/json + body: "{{ .fixtures.raw_validation }}" + assertions: + - result.statuscode ShouldEqual 200 + - result.bodyjson.response.allowed ShouldEqual true + - result.bodyjson.response.status.code ShouldNotEqual 500 + - result.bodyjson.response ShouldNotContainKey patch + - result.bodyjson.response ShouldNotContainKey patchType + + - name: Raw WASI mutation policy mutates the request + steps: + - name: Accept + type: http + method: POST + url: http://localhost:3000/validate_raw/raw-mutation-wasi + headers: + Content-Type: application/json + body: "{{ .fixtures.raw_mutation }}" + assertions: + - result.statuscode ShouldEqual 200 + - result.bodyjson.response.allowed ShouldEqual true + - result.bodyjson.response.status.code ShouldNotEqual 500 + - result.bodyjson.response ShouldContainKey patch + - result.bodyjson.response ShouldContainKey patchType diff --git a/e2e-tests/test_data/policies.yaml b/e2e-tests/test_data/policies.yaml index 7d9e2254..03a37b59 100644 --- a/e2e-tests/test_data/policies.yaml +++ b/e2e-tests/test_data/policies.yaml @@ -29,3 +29,46 @@ flux: settings: requiredAnnotations: "fluxcd.io/cat": "felix" + +raw-validation: + url: ghcr.io/kubewarden/tests/raw-validation-policy:v0.1.0 + settings: + validUsers: + - "tonio" + - "wanda" + validActions: + - "eats" + - "likes" + validResources: + - "banana" + - "hay" + +raw-mutation: + url: ghcr.io/kubewarden/tests/raw-mutation-policy:v0.1.0 + allowedToMutate: true + settings: {} + +raw-validation-opa: + url: ghcr.io/kubewarden/tests/raw-validation-opa-policy:v0.1.0 + settings: {} + +raw-validation-wasi: + url: ghcr.io/kubewarden/tests/raw-validation-wasi-policy:v0.1.0 + settings: + validUsers: + - "tonio" + - "wanda" + validActions: + - "eats" + - "likes" + validResources: + - "banana" + - "hay" + +raw-mutation-wasi: + url: ghcr.io/kubewarden/tests/raw-mutation-wasi-policy:v0.1.0 + allowedToMutate: true + settings: + forbiddenResources: + - "banana" + - "carrot" diff --git a/e2e-tests/test_data/raw_mutation.json b/e2e-tests/test_data/raw_mutation.json new file mode 100644 index 00000000..821009bb --- /dev/null +++ b/e2e-tests/test_data/raw_mutation.json @@ -0,0 +1,3 @@ +{ + "request": { "user": "tonio", "action": "eats", "resource": "banana" } +} diff --git a/e2e-tests/test_data/raw_validation.json b/e2e-tests/test_data/raw_validation.json new file mode 100644 index 00000000..d7744ae4 --- /dev/null +++ b/e2e-tests/test_data/raw_validation.json @@ -0,0 +1,3 @@ +{ + "request": { "user": "tonio", "action": "eats", "resource": "hay" } +} From 4e92d03abbcb36be20532a64596211e99225d620 Mon Sep 17 00:00:00 2001 From: Fabrizio Sestito Date: Thu, 26 Oct 2023 10:46:22 +0200 Subject: [PATCH 10/10] build(deps): update PolicyEvaluator v0.12.0 Signed-off-by: Fabrizio Sestito --- Cargo.lock | 399 ++++++++++++++++++++++------------------------------- Cargo.toml | 2 +- 2 files changed, 164 insertions(+), 237 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 41928793..191cdefd 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2,22 +2,13 @@ # It is not intended for manual editing. version = 3 -[[package]] -name = "addr2line" -version = "0.20.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f4fa78e18c64fce05e902adecd7a5eed15a5e0a3439f7b0e169f0252214865e3" -dependencies = [ - "gimli 0.27.3", -] - [[package]] name = "addr2line" version = "0.21.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8a30b2e23b9e17a9f90641c7ab1549cd9b44f296d3ccbf309d2863cfe398a0cb" dependencies = [ - "gimli 0.28.0", + "gimli", ] [[package]] @@ -67,6 +58,12 @@ dependencies = [ "memchr", ] +[[package]] +name = "allocator-api2" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0942ffc6dcaadf03badf6e6a2d0228460359d5e34b57ccdc720b7382dfbd5ec5" + [[package]] name = "ambient-authority" version = "0.0.2" @@ -345,12 +342,12 @@ version = "0.3.69" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2089b7e3f35b9dd2d0ed921ead4f6d318c27680d4a5bd167b3ee120edb105837" dependencies = [ - "addr2line 0.21.0", + "addr2line", "cc", "cfg-if", "libc", "miniz_oxide", - "object 0.32.1", + "object", "rustc-demangle", ] @@ -467,7 +464,7 @@ checksum = "7f30e7476521f6f8af1a1c4c0b8cc94f0bee37d91763d0ca2665f299b6cd8aec" [[package]] name = "burrego" version = "0.3.4" -source = "git+https://github.com/kubewarden/policy-evaluator?tag=v0.11.5#d8b7d5e28b838027d4dbeec1f03da23596956d37" +source = "git+https://github.com/kubewarden/policy-evaluator?tag=v0.12.0#3f8ffc45f370c7c45a61510554cadd52c88e486a" dependencies = [ "base64 0.21.4", "chrono", @@ -520,15 +517,16 @@ dependencies = [ [[package]] name = "cached" -version = "0.45.1" +version = "0.46.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "90eb5776f28a149524d1d8623035760b4454ec881e8cf3838fa8d7e1b11254b3" +checksum = "8cead8ece0da6b744b2ad8ef9c58a4cdc7ef2921e60a6ddfb9eaaa86839b5fc5" dependencies = [ + "ahash", "async-trait", "cached_proc_macro 0.18.0", "cached_proc_macro_types", "futures", - "hashbrown 0.13.2", + "hashbrown 0.14.2", "instant", "once_cell", "thiserror", @@ -578,6 +576,18 @@ dependencies = [ "windows-sys 0.48.0", ] +[[package]] +name = "cap-net-ext" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6ffc30dee200c20b4dcb80572226f42658e1d9c4b668656d7cc59c33d50e396e" +dependencies = [ + "cap-primitives", + "cap-std", + "rustix 0.38.20", + "smallvec", +] + [[package]] name = "cap-primitives" version = "2.0.0" @@ -802,18 +812,18 @@ dependencies = [ [[package]] name = "cranelift-bforest" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5a91a1ccf6fb772808742db2f51e2179f25b1ec559cbe39ea080c72ff61caf8f" +checksum = "c1512c3bb6b13018e7109fc3ac964bc87b329eaf3a77825d337558d0c7f6f1be" dependencies = [ "cranelift-entity", ] [[package]] name = "cranelift-codegen" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "169db1a457791bff4fd1fc585bb5cc515609647e0420a7d5c98d7700c59c2d00" +checksum = "16cb8fb9220a6ea7a226705a273ab905309ee546267bdf34948d57932d7f0396" dependencies = [ "bumpalo", "cranelift-bforest", @@ -822,8 +832,8 @@ dependencies = [ "cranelift-control", "cranelift-entity", "cranelift-isle", - "gimli 0.27.3", - "hashbrown 0.13.2", + "gimli", + "hashbrown 0.14.2", "log", "regalloc2", "smallvec", @@ -832,42 +842,43 @@ dependencies = [ [[package]] name = "cranelift-codegen-meta" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3486b93751ef19e6d6eef66d2c0e83ed3d2ba01da1919ed2747f2f7bd8ba3419" +checksum = "ab3a8d3b0d4745b183da5ea0792b13d79f5c23d6e69ac04761728e2532b56649" dependencies = [ "cranelift-codegen-shared", ] [[package]] name = "cranelift-codegen-shared" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "86a1205ab18e7cd25dc4eca5246e56b506ced3feb8d95a8d776195e48d2cd4ef" +checksum = "524141c8e68f2abc2043de4c2b31f6d9dd42432738c246431d0572a1422a4a84" [[package]] name = "cranelift-control" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1b108cae0f724ddfdec1871a0dc193a607e0c2d960f083cfefaae8ccf655eff2" +checksum = "97513b57c961c713789a03886a57b43e14ebcd204cbaa8ae50ca6c70a8e716b3" dependencies = [ "arbitrary", ] [[package]] name = "cranelift-entity" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "720444006240622798665bfc6aa8178e2eed556da342fda62f659c5267c3c659" +checksum = "e3f23d3cf3afa7e45f239702612c76d87964f652a55e28d13ed6d7e20f3479dd" dependencies = [ "serde", + "serde_derive", ] [[package]] name = "cranelift-frontend" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b7a94c4c5508b7407e125af9d5320694b7423322e59a4ac0d07919ae254347ca" +checksum = "554cd4947ec9209b58bf9ae5bf83581b5ddf9128bd967208e334b504a57db54e" dependencies = [ "cranelift-codegen", "log", @@ -877,15 +888,15 @@ dependencies = [ [[package]] name = "cranelift-isle" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ef1f888d0845dcd6be4d625b91d9d8308f3d95bed5c5d4072ce38e1917faa505" +checksum = "6c1892a439696b6413cb54083806f5fd9fc431768b8de74864b3d9e8b93b124f" [[package]] name = "cranelift-native" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ad5966da08f1e96a3ae63be49966a85c9b249fa465f8cf1b66469a82b1004a0" +checksum = "e0c2d3badd4b9690865f5bb68a71fa94de592fa2df3f3d11a5a062c60c0a107a" dependencies = [ "cranelift-codegen", "libc", @@ -894,9 +905,9 @@ dependencies = [ [[package]] name = "cranelift-wasm" -version = "0.99.2" +version = "0.101.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d8635c88b424f1d232436f683a301143b36953cd98fc6f86f7bac862dfeb6f5" +checksum = "11e11f017991fc37e69a1f6799b0d8ec34b53c9ea63564b41a387c12efc55fff" dependencies = [ "cranelift-codegen", "cranelift-entity", @@ -904,7 +915,7 @@ dependencies = [ "itertools 0.10.5", "log", "smallvec", - "wasmparser 0.110.0", + "wasmparser", "wasmtime-types", ] @@ -1340,19 +1351,6 @@ dependencies = [ "cfg-if", ] -[[package]] -name = "env_logger" -version = "0.10.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "85cdab6a89accf66733ad5a1693a4dcced6aeff64602b634530dd73c1f3ee9f0" -dependencies = [ - "humantime", - "is-terminal", - "log", - "regex", - "termcolor", -] - [[package]] name = "equivalent" version = "1.0.1" @@ -1377,9 +1375,9 @@ checksum = "0206175f82b8d6bf6652ff7d71a1e27fd2e4efde587fd368662814d6ec1d9ce0" [[package]] name = "fallible-iterator" -version = "0.2.0" +version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4443176a9f2c162692bd3d352d745ef9413eec5782a80d8fd6f8a1ac692a07f7" +checksum = "2acce4a10f12dc2fb14a218589d4f1f62ef011b2d0cc4b3cb1bba8e94da14649" [[package]] name = "fastrand" @@ -1423,16 +1421,6 @@ version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d0870c84016d4b481be5c9f323c24f65e31e901ae618f0e80f4308fb00de1d2d" -[[package]] -name = "file-per-thread-logger" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8a3cc21c33af89af0930c8cae4ade5e6fdc17b5d2c97b3d2e2edb67a1cf683f3" -dependencies = [ - "env_logger", - "log", -] - [[package]] name = "flagset" version = "0.4.4" @@ -1633,21 +1621,15 @@ dependencies = [ [[package]] name = "gimli" -version = "0.27.3" +version = "0.28.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6c80984affa11d98d1b88b66ac8853f143217b399d3c74116778ff8fdb4ed2e" +checksum = "6fb8d784f27acf97159b40fc4db5ecd8aa23b9ad5ef69cdd136d3bc80665f0c0" dependencies = [ "fallible-iterator", - "indexmap 1.9.3", + "indexmap 2.0.2", "stable_deref_trait", ] -[[package]] -name = "gimli" -version = "0.28.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6fb8d784f27acf97159b40fc4db5ecd8aa23b9ad5ef69cdd136d3bc80665f0c0" - [[package]] name = "glob" version = "0.3.1" @@ -1752,6 +1734,10 @@ name = "hashbrown" version = "0.14.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f93e7192158dbcda357bdec5fb5788eebf8bbac027f3f33e719d29135ae84156" +dependencies = [ + "ahash", + "allocator-api2", +] [[package]] name = "headers" @@ -1880,12 +1866,6 @@ dependencies = [ "libm", ] -[[package]] -name = "humantime" -version = "2.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4" - [[package]] name = "hyper" version = "0.14.27" @@ -2063,17 +2043,6 @@ version = "2.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8f518f335dce6725a761382244631d86cf0ccb2863413590b31338feb467f9c3" -[[package]] -name = "is-terminal" -version = "0.4.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cb0889898416213fab133e1d33a0e5858a48177452750691bde3666d0fdbaf8b" -dependencies = [ - "hermit-abi", - "rustix 0.38.20", - "windows-sys 0.48.0", -] - [[package]] name = "itertools" version = "0.10.5" @@ -2674,24 +2643,15 @@ dependencies = [ "malloc_buf", ] -[[package]] -name = "object" -version = "0.31.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8bda667d9f2b5051b8833f59f3bf748b28ef54f850f4fcb389a252aa383866d1" -dependencies = [ - "crc32fast", - "hashbrown 0.13.2", - "indexmap 1.9.3", - "memchr", -] - [[package]] name = "object" version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9cf5f9dd3933bd50a9e1f149ec995f39ae2c496d31fd772c1fd45ebc27e902b0" dependencies = [ + "crc32fast", + "hashbrown 0.14.2", + "indexmap 2.0.2", "memchr", ] @@ -3267,13 +3227,13 @@ checksum = "4503fa043bf02cee09a9582e9554b4c6403b2ef55e4612e96561d294419429f8" [[package]] name = "policy-evaluator" -version = "0.11.5" -source = "git+https://github.com/kubewarden/policy-evaluator?tag=v0.11.5#d8b7d5e28b838027d4dbeec1f03da23596956d37" +version = "0.12.0" +source = "git+https://github.com/kubewarden/policy-evaluator?tag=v0.12.0#3f8ffc45f370c7c45a61510554cadd52c88e486a" dependencies = [ "anyhow", "base64 0.21.4", "burrego", - "cached 0.45.1", + "cached 0.46.0", "chrono", "dns-lookup", "email_address", @@ -3301,7 +3261,7 @@ dependencies = [ "wapc", "wasi-cap-std-sync", "wasi-common", - "wasmparser 0.112.0", + "wasmparser", "wasmtime", "wasmtime-provider", "wasmtime-wasi", @@ -3497,17 +3457,6 @@ dependencies = [ "cc", ] -[[package]] -name = "pulldown-cmark" -version = "0.9.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "77a1a2f1f0a7ecff9c31abbe177637be0e97a0aef46cf8738ece09327985d998" -dependencies = [ - "bitflags 1.3.2", - "memchr", - "unicase", -] - [[package]] name = "quote" version = "1.0.33" @@ -4475,15 +4424,6 @@ dependencies = [ "windows-sys 0.48.0", ] -[[package]] -name = "termcolor" -version = "1.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6093bad37da69aab9d123a8091e4be0aa4a03e4d601ec641c327398315f62b64" -dependencies = [ - "winapi-util", -] - [[package]] name = "thiserror" version = "1.0.50" @@ -5112,9 +5052,9 @@ checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" [[package]] name = "wasi-cap-std-sync" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3b8bb7213a65e753e110c36f904d9491e23c763183bd8aa82f5ce721ca647177" +checksum = "817188af459a2dc99cf2f51bbd4b6f4a632c56ed0b276721b68690d61e5b5fd6" dependencies = [ "anyhow", "async-trait", @@ -5125,7 +5065,6 @@ dependencies = [ "fs-set-times", "io-extras", "io-lifetimes 2.0.2", - "is-terminal", "once_cell", "rustix 0.38.20", "system-interface", @@ -5136,9 +5075,9 @@ dependencies = [ [[package]] name = "wasi-common" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a99e7c55c22a7c776a2169bcd72a310806004e3d298151036f0452a6c3ebe56d" +checksum = "00375e5c7969c8422bd469120a9bc07ff94d49ec0b660109c282ecf939533ab1" dependencies = [ "anyhow", "bitflags 2.4.1", @@ -5220,15 +5159,6 @@ version = "0.2.87" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ca6ad05a4870b2bf5fe995117d3728437bd27d7cd5f06f13c17443ef369775a1" -[[package]] -name = "wasm-encoder" -version = "0.31.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "41763f20eafed1399fff1afb466496d3a959f58241436cfdc17e3f5ca954de16" -dependencies = [ - "leb128", -] - [[package]] name = "wasm-encoder" version = "0.35.0" @@ -5251,26 +5181,6 @@ dependencies = [ "web-sys", ] -[[package]] -name = "wasmparser" -version = "0.110.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1dfcdb72d96f01e6c85b6bf20102e7423bdbaad5c337301bab2bbf253d26413c" -dependencies = [ - "indexmap 2.0.2", - "semver", -] - -[[package]] -name = "wasmparser" -version = "0.112.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e986b010f47fcce49cf8ea5d5f9e5d2737832f12b53ae8ae785bbe895d0877bf" -dependencies = [ - "indexmap 2.0.2", - "semver", -] - [[package]] name = "wasmparser" version = "0.115.0" @@ -5288,14 +5198,14 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e74458a9bc5cc9c7108abfa0fe4dc88d5abf1f3baf194df3264985f17d559b5e" dependencies = [ "anyhow", - "wasmparser 0.115.0", + "wasmparser", ] [[package]] name = "wasmtime" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c4e87029cc5760db9a3774aff4708596fe90c20ed2baeef97212e98b812fd0fc" +checksum = "24b2f2c8a3e88235f48fbbd46662d813dd6a2ce0c3d6ea87e2892b833ed948a1" dependencies = [ "anyhow", "async-trait", @@ -5307,16 +5217,17 @@ dependencies = [ "indexmap 2.0.2", "libc", "log", - "object 0.31.1", + "object", "once_cell", "paste", "psm", "rayon", "serde", + "serde_derive", "serde_json", "target-lexicon", - "wasm-encoder 0.31.1", - "wasmparser 0.110.0", + "wasm-encoder", + "wasmparser", "wasmtime-cache", "wasmtime-component-macro", "wasmtime-component-util", @@ -5332,27 +5243,27 @@ dependencies = [ [[package]] name = "wasmtime-asm-macros" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "96d84f68d831200016e120f2ee79d81b50cf4c4123112914aefb168d036d445d" +checksum = "a6770280be3897d860f2c540773fd0b73080bc5e02f9b5f9f38e087c24426311" dependencies = [ "cfg-if", ] [[package]] name = "wasmtime-cache" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "31561fbbaa86d3c042696940bc9601146bf4aaec39ae725c86b5f1358d8d7023" +checksum = "439a73eff59a45862325630b3f7dbca1501ec06d871dd1be7714202f04f3d8ff" dependencies = [ "anyhow", "base64 0.21.4", "bincode", "directories-next", - "file-per-thread-logger", "log", "rustix 0.38.20", "serde", + "serde_derive", "sha2", "toml", "windows-sys 0.48.0", @@ -5361,9 +5272,9 @@ dependencies = [ [[package]] name = "wasmtime-component-macro" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8e7e07b8da23838e870c4c092027208ac546398a2ac4f5afff33a1ea1d763ec0" +checksum = "e98193dcd184aa9f04c9cc62e02931ee65c8796411c2569da5e8271cfd200c89" dependencies = [ "anyhow", "proc-macro2", @@ -5376,29 +5287,30 @@ dependencies = [ [[package]] name = "wasmtime-component-util" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "74f421bc59c753dcd24e39601928a0f2915adf15f40d8ba0066c4cf23f92c9a0" +checksum = "c182d089edf8798f334442be4a72b93a47bbb2a4fce01323fa0936b72d6fecfd" [[package]] name = "wasmtime-cranelift" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8ae8ed7a4845f22be6b1ad80f33f43fa03445b03a02f2d40dca695129769cd1a" +checksum = "b9d785f0807f4a90553e50781494fabf2ccace948634593841dafdb244b0fa75" dependencies = [ "anyhow", + "cfg-if", "cranelift-codegen", "cranelift-control", "cranelift-entity", "cranelift-frontend", "cranelift-native", "cranelift-wasm", - "gimli 0.27.3", + "gimli", "log", - "object 0.31.1", + "object", "target-lexicon", "thiserror", - "wasmparser 0.110.0", + "wasmparser", "wasmtime-cranelift-shared", "wasmtime-environ", "wasmtime-versioned-export-macros", @@ -5406,37 +5318,38 @@ dependencies = [ [[package]] name = "wasmtime-cranelift-shared" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "86b17099f9320a1c481634d88101258917d5065717cf22b04ed75b1a8ea062b4" +checksum = "bfc90cb7d3912892b5791a8a8792c384d413f56ec3e59846ec48e2b7fd78af84" dependencies = [ "anyhow", "cranelift-codegen", "cranelift-control", "cranelift-native", - "gimli 0.27.3", - "object 0.31.1", + "gimli", + "object", "target-lexicon", "wasmtime-environ", ] [[package]] name = "wasmtime-environ" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e8b9227b1001229ff125e0f76bf1d5b9dc4895e6bcfd5cc35a56f84685964ec7" +checksum = "f07170a1d9be1e1d0a4e1532783c8e5c1734f86871c2ff9af6f713a189810ba7" dependencies = [ "anyhow", "cranelift-entity", - "gimli 0.27.3", + "gimli", "indexmap 2.0.2", "log", - "object 0.31.1", + "object", "serde", + "serde_derive", "target-lexicon", "thiserror", - "wasm-encoder 0.31.1", - "wasmparser 0.110.0", + "wasm-encoder", + "wasmparser", "wasmprinter", "wasmtime-component-util", "wasmtime-types", @@ -5444,9 +5357,9 @@ dependencies = [ [[package]] name = "wasmtime-fiber" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fc8c8410c03a79073ea06806ccde3da4854c646bd646b3b2707b99b3746c3f70" +checksum = "964eaf5108aff57abbc3ca3cdcd9021b7f8f525d87d4c76fc99259ca5756bb6a" dependencies = [ "cc", "cfg-if", @@ -5458,22 +5371,23 @@ dependencies = [ [[package]] name = "wasmtime-jit" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cce606b392c321d7272928003543447119ef937a9c3ebfce5c4bb0bf6b0f5bac" +checksum = "e7c85db89eff1d4ab312e6ea2fe4cbefbd6767adc4e83562774913bb2d97009d" dependencies = [ - "addr2line 0.20.0", + "addr2line", "anyhow", "bincode", "cfg-if", "cpp_demangle", - "gimli 0.27.3", + "gimli", "ittapi", "log", - "object 0.31.1", + "object", "rustc-demangle", "rustix 0.38.20", "serde", + "serde_derive", "target-lexicon", "wasmtime-environ", "wasmtime-jit-debug", @@ -5484,11 +5398,11 @@ dependencies = [ [[package]] name = "wasmtime-jit-debug" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aef27ea6c34ef888030d15560037fe7ef27a5609fbbba8e1e3e41dc4245f5bb2" +checksum = "ab4e03e121a10b7516dc5b131d77d24d92f9a980d491487b510e56025b56de06" dependencies = [ - "object 0.31.1", + "object", "once_cell", "rustix 0.38.20", "wasmtime-versioned-export-macros", @@ -5496,9 +5410,9 @@ dependencies = [ [[package]] name = "wasmtime-jit-icache-coherence" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b59f94b0409221873565419168e20b5aedf18c4bd64de5c38acf8f0634efeee3" +checksum = "9aaf2fa8fd2d6b65abae9b92edfe69254cc5d6b166e342364036c3e347de8da9" dependencies = [ "cfg-if", "libc", @@ -5507,9 +5421,9 @@ dependencies = [ [[package]] name = "wasmtime-provider" -version = "1.9.0" +version = "1.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2380d6a1c862aab685fe93abb13f875a326c3f487236d215d659412d4da4fccc" +checksum = "559e7c5b79fbee0619789b0b51d8dae7a6efe46abfb2f3d90e1e2082ec49b6b0" dependencies = [ "anyhow", "cfg-if", @@ -5526,9 +5440,9 @@ dependencies = [ [[package]] name = "wasmtime-runtime" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ceb587a88ae5bb6ca248455a391aff29ac63329a404b2cdea36d91267c797db4" +checksum = "44d848064874297fe144ac226a4abeb99e231197a82e4d9eb967ce24b9431847" dependencies = [ "anyhow", "cc", @@ -5544,32 +5458,34 @@ dependencies = [ "rand", "rustix 0.38.20", "sptr", - "wasm-encoder 0.31.1", + "wasm-encoder", "wasmtime-asm-macros", "wasmtime-environ", "wasmtime-fiber", "wasmtime-jit-debug", "wasmtime-versioned-export-macros", + "wasmtime-wmemcheck", "windows-sys 0.48.0", ] [[package]] name = "wasmtime-types" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "77943729d4b46141538e8d0b6168915dc5f88575ecdfea26753fd3ba8bab244a" +checksum = "c17af844f80ac4c7afb35f338e705e3484a4d9f2fa53dcc9bb26a5a90591e96d" dependencies = [ "cranelift-entity", "serde", + "serde_derive", "thiserror", - "wasmparser 0.110.0", + "wasmparser", ] [[package]] name = "wasmtime-versioned-export-macros" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ca7af9bb3ee875c4907835e607a275d10b04d15623d3aebe01afe8fbd3f85050" +checksum = "5ea1c14fe655234d8c808a0b32e7192fb196896541fd3df02c3faa829bcaf09d" dependencies = [ "proc-macro2", "quote", @@ -5578,28 +5494,32 @@ dependencies = [ [[package]] name = "wasmtime-wasi" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "50e107275b5a0144e2965985d14fac61fa46f804755e71c44eeef7b37510db54" +checksum = "5a0c4cc6479d96a8ee3410cc29005a083f39c27730fa63897d41e6668401eae2" dependencies = [ "anyhow", "async-trait", "bitflags 2.4.1", "bytes", "cap-fs-ext", + "cap-net-ext", "cap-rand", "cap-std", "cap-time-ext", "fs-set-times", "futures", "io-extras", + "io-lifetimes 2.0.2", "libc", + "log", "once_cell", "rustix 0.38.20", "system-interface", "thiserror", "tokio", "tracing", + "url", "wasi-cap-std-sync", "wasi-common", "wasmtime", @@ -5609,16 +5529,16 @@ dependencies = [ [[package]] name = "wasmtime-winch" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bcdfbdbb400f63e4dfc6dd32f42c77484da58c9622cdd9e9aac238c7347afdf1" +checksum = "b5270c63338875741ff6b51c55dbd2ea474c67b1f1ded186c17b67171e5f43e3" dependencies = [ "anyhow", "cranelift-codegen", - "gimli 0.27.3", - "object 0.31.1", + "gimli", + "object", "target-lexicon", - "wasmparser 0.110.0", + "wasmparser", "wasmtime-cranelift-shared", "wasmtime-environ", "winch-codegen", @@ -5626,9 +5546,9 @@ dependencies = [ [[package]] name = "wasmtime-wit-bindgen" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "14770d0820f56ba86cdd9987aef97cc3bacbb0394633c37dbfbc61ef29603a71" +checksum = "0b72f3ec7faf503abf4538858de9ca677742e6e7100e0372257cccad0cbb0ffc" dependencies = [ "anyhow", "heck", @@ -5636,6 +5556,12 @@ dependencies = [ "wit-parser", ] +[[package]] +name = "wasmtime-wmemcheck" +version = "14.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "19e2168a6e2a5f3b415903025b4c18f532731f2c8f4dceb6725959a07bc4e496" + [[package]] name = "wast" version = "35.0.2" @@ -5654,7 +5580,7 @@ dependencies = [ "leb128", "memchr", "unicode-width", - "wasm-encoder 0.35.0", + "wasm-encoder", ] [[package]] @@ -5701,9 +5627,9 @@ checksum = "14247bb57be4f377dfb94c72830b8ce8fc6beac03cf4bf7b9732eadd414123fc" [[package]] name = "wiggle" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3b68b8c7e33b826fefcedd4fdaba18b45e802949039976dfed2ec4eed62e01dc" +checksum = "dc86a60aa99979d11d9d370380e8bce677832a8fca240c148de8dfd77b112680" dependencies = [ "anyhow", "async-trait", @@ -5716,9 +5642,9 @@ dependencies = [ [[package]] name = "wiggle-generate" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a1993fafe27277a5f3d3e8799d027fb1d4cf715cb7706bc50f13dbc06197800e" +checksum = "463676f18e779c4a967bb6f57113bd0be9dd426d15efe746829071b4b60dcb10" dependencies = [ "anyhow", "heck", @@ -5731,9 +5657,9 @@ dependencies = [ [[package]] name = "wiggle-macro" -version = "12.0.2" +version = "14.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b71eb22a17666b04cd9273983ec00ccbd3085cae494ae08dba733e65465cf6e7" +checksum = "6ae27b80ece4338002d9be720aa848a1fe581a73f28fa9e780c27348cd7b3046" dependencies = [ "proc-macro2", "quote", @@ -5774,17 +5700,17 @@ checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" [[package]] name = "winch-codegen" -version = "0.10.2" +version = "0.12.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9722f5d601e3ea1cab8cc23f8e4c07c57d6657a1d72ef4c3a064100cca725a20" +checksum = "fb430165599b116b2257d0e5cf7be45812d3e768f0eb55c54074f3187806b45f" dependencies = [ "anyhow", "cranelift-codegen", - "gimli 0.27.3", + "gimli", "regalloc2", "smallvec", "target-lexicon", - "wasmparser 0.110.0", + "wasmparser", "wasmtime-environ", ] @@ -5951,18 +5877,19 @@ dependencies = [ [[package]] name = "wit-parser" -version = "0.9.2" +version = "0.12.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "541efa2046e544de53a9da1e2f6299e63079840360c9e106f1f8275a97771318" +checksum = "f6ace9943d89bbf3dbbc71b966da0e7302057b311f36a4ac3d65ddfef17b52cf" dependencies = [ "anyhow", "id-arena", "indexmap 2.0.2", "log", - "pulldown-cmark", "semver", + "serde", + "serde_derive", + "serde_json", "unicode-xid", - "url", ] [[package]] diff --git a/Cargo.toml b/Cargo.toml index 6761820d..94f08f36 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -28,7 +28,7 @@ opentelemetry = { version = "0.20", default-features = false, features = [ "rt-tokio", ] } procfs = "0.15" -policy-evaluator = { git = "https://github.com/kubewarden/policy-evaluator", tag = "v0.11.5" } +policy-evaluator = { git = "https://github.com/kubewarden/policy-evaluator", tag = "v0.12.0" } rayon = "1.8" serde_json = "1.0" serde = { version = "1.0", features = ["derive"] }