Implement PERMISSIONS clauses

This commit is contained in:
Tobie Morgan Hitchcock 2022-04-05 21:41:49 +01:00
parent 200741a35e
commit 5df1040dd8
5 changed files with 43 additions and 8 deletions

View file

@ -86,6 +86,11 @@ impl fmt::Display for Statement {
} }
impl Statement { impl Statement {
// Check the type of statement
#[inline]
pub fn is_select(&self) -> bool {
matches!(self, Statement::Select(_))
}
// Returns any query fields if specified // Returns any query fields if specified
#[inline] #[inline]
pub fn expr(&self) -> Option<&Fields> { pub fn expr(&self) -> Option<&Fields> {

View file

@ -4,15 +4,45 @@ use crate::dbs::Statement;
use crate::dbs::Transaction; use crate::dbs::Transaction;
use crate::doc::Document; use crate::doc::Document;
use crate::err::Error; use crate::err::Error;
use crate::sql::permission::Permission;
impl<'a> Document<'a> { impl<'a> Document<'a> {
pub async fn allow( pub async fn allow(
&self, &self,
_ctx: &Runtime, ctx: &Runtime,
_opt: &Options, opt: &Options,
_txn: &Transaction, txn: &Transaction,
_stm: &Statement, stm: &Statement,
) -> Result<(), Error> { ) -> Result<(), Error> {
// Check permission clause
if opt.perms && opt.auth.perms() && self.id.is_some() {
// Get the table
let tb = self.tb(ctx, opt, txn).await?;
// Get the permission
let perms = if self.initial.is_none() {
&tb.permissions.create
} else if self.current.is_none() {
&tb.permissions.delete
} else if stm.is_select() {
&tb.permissions.select
} else {
&tb.permissions.update
};
// Match the permission
match perms {
Permission::None => return Err(Error::Ignore),
Permission::Full => return Ok(()),
Permission::Specific(e) => {
// Ensure permissions are disabled
let opt = &opt.perms(false);
// Process the PERMISSION clause
if !e.compute(ctx, opt, txn, Some(&self.current)).await?.is_truthy() {
return Err(Error::Ignore);
}
}
}
}
// Carry on
Ok(()) Ok(())
} }
} }

View file

@ -18,10 +18,10 @@ impl<'a> Document<'a> {
self.admit(ctx, opt, txn, stm).await?; self.admit(ctx, opt, txn, stm).await?;
// Check where clause // Check where clause
self.check(ctx, opt, txn, stm).await?; self.check(ctx, opt, txn, stm).await?;
// Check if allowed
self.allow(ctx, opt, txn, stm).await?;
// Erase document // Erase document
self.erase(ctx, opt, txn, stm).await?; self.erase(ctx, opt, txn, stm).await?;
// Check if allowed
self.allow(ctx, opt, txn, stm).await?;
// Purge index data // Purge index data
self.index(ctx, opt, txn, stm).await?; self.index(ctx, opt, txn, stm).await?;
// Purge record data // Purge record data

View file

@ -38,7 +38,7 @@ impl<'a> Document<'a> {
// Get the table for this document // Get the table for this document
pub async fn tb( pub async fn tb(
&self, &self,
ctx: &Runtime, _ctx: &Runtime,
opt: &Options, opt: &Options,
txn: &Transaction, txn: &Transaction,
) -> Result<DefineTableStatement, Error> { ) -> Result<DefineTableStatement, Error> {

View file

@ -153,7 +153,7 @@ pub enum Error {
}, },
#[error("You don't have permission to run the `{query}` query on the `{table}` table")] #[error("You don't have permission to run the `{query}` query on the `{table}` table")]
TablePermissionsError { TablePermissions {
query: String, query: String,
table: String, table: String,
}, },