use chrono::{DateTime, Utc};
use crate::action::Action;
use crate::audit::Audit;
use crate::backend::{AuditQuery, Backend, Order};
use crate::error::Result;
use crate::id::AuditId;
pub struct AuditQueryBuilder<'a> {
backend: &'a dyn Backend,
type_name: String,
id: AuditId,
associated: bool,
query: AuditQuery,
}
impl<'a> AuditQueryBuilder<'a> {
pub(crate) fn new(
backend: &'a dyn Backend,
type_name: String,
id: AuditId,
associated: bool,
) -> Self {
AuditQueryBuilder {
backend,
type_name,
id,
associated,
query: AuditQuery::default(),
}
}
pub fn creates(mut self) -> Self {
self.query.action = Some(Action::Create);
self
}
pub fn updates(mut self) -> Self {
self.query.action = Some(Action::Update);
self
}
pub fn destroys(mut self) -> Self {
self.query.action = Some(Action::Destroy);
self
}
pub fn from_version(mut self, version: i32) -> Self {
self.query.from_version = Some(version);
self
}
pub fn to_version(mut self, version: i32) -> Self {
self.query.to_version = Some(version);
self
}
pub fn up_until(mut self, time: DateTime<Utc>) -> Self {
self.query.up_until = Some(time);
self
}
pub fn ascending(mut self) -> Self {
self.query.order = Order::VersionAsc;
self
}
pub fn descending(mut self) -> Self {
self.query.order = Order::VersionDesc;
self
}
pub fn limit(mut self, limit: i64) -> Self {
self.query.limit = Some(limit);
self
}
pub fn offset(mut self, offset: i64) -> Self {
self.query.offset = Some(offset);
self
}
pub async fn fetch(self) -> Result<Vec<Audit>> {
if self.associated {
self.backend
.audits_for_associated(&self.type_name, &self.id, &self.query)
.await
} else {
self.backend
.audits_for_auditable(&self.type_name, &self.id, &self.query)
.await
}
}
pub async fn count(self) -> Result<usize> {
Ok(self.fetch().await?.len())
}
}