use crate::cryptotensors::CryptoTensorsError;
use regorus::Engine;
use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct AccessPolicy {
#[serde(rename = "local")]
local_policy: String,
#[serde(rename = "remote")]
remote_policy: String,
}
impl Default for AccessPolicy {
fn default() -> Self {
let default_policy = "package model\nallow = true".to_string();
Self {
local_policy: default_policy.clone(),
remote_policy: default_policy,
}
}
}
impl AccessPolicy {
pub fn new(local: Option<String>, remote: Option<String>) -> Self {
let default_policy = "package model\nallow = true".to_string();
Self {
local_policy: local.unwrap_or_else(|| default_policy.clone()),
remote_policy: remote.unwrap_or(default_policy),
}
}
pub fn evaluate(&self, _input: String) -> Result<bool, CryptoTensorsError> {
let mut engine = Engine::new();
engine
.add_policy(String::from("model.rego"), self.local_policy.clone())
.map_err(|e| CryptoTensorsError::Policy(format!("Failed to add policy: {e}")))?;
let result = engine
.eval_rule(String::from("data.model.allow"))
.map_err(|e| CryptoTensorsError::Policy(format!("Policy evaluation failed: {e}")))?;
match result {
regorus::Value::Bool(allowed) => Ok(allowed),
regorus::Value::Undefined => Err(CryptoTensorsError::Policy(
"Policy returned undefined".to_string(),
)),
_ => Err(CryptoTensorsError::Policy(
"Policy did not return a boolean".to_string(),
)),
}
}
}