Fix $value being NONE for DELETE events (#3869)

This commit is contained in:
Micha de Vries 2024-04-16 10:49:33 +02:00 committed by GitHub
parent ff45747c10
commit dc669b78e3
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 66 additions and 3 deletions

View file

@ -34,18 +34,23 @@ impl<'a> Document<'a> {
} else { } else {
Value::from("UPDATE") Value::from("UPDATE")
}; };
// Depending on type of event, how do we populate the document
let doc = match stm.is_delete() {
true => &self.initial,
false => &self.current,
};
// Configure the context // Configure the context
let mut ctx = Context::new(ctx); let mut ctx = Context::new(ctx);
ctx.add_value("event", met); ctx.add_value("event", met);
ctx.add_value("value", self.current.doc.deref()); ctx.add_value("value", doc.doc.deref());
ctx.add_value("after", self.current.doc.deref()); ctx.add_value("after", self.current.doc.deref());
ctx.add_value("before", self.initial.doc.deref()); ctx.add_value("before", self.initial.doc.deref());
// Process conditional clause // Process conditional clause
let val = ev.when.compute(&ctx, opt, txn, Some(&self.current)).await?; let val = ev.when.compute(&ctx, opt, txn, Some(doc)).await?;
// Execute event if value is truthy // Execute event if value is truthy
if val.is_truthy() { if val.is_truthy() {
for v in ev.then.iter() { for v in ev.then.iter() {
v.compute(&ctx, opt, txn, Some(&self.current)).await?; v.compute(&ctx, opt, txn, Some(doc)).await?;
} }
} }
} }

View file

@ -434,6 +434,64 @@ async fn define_statement_event_when_event() -> Result<(), Error> {
Ok(()) Ok(())
} }
#[tokio::test]
async fn define_statement_event_check_doc_always_populated() -> Result<(), Error> {
let sql = "
DEFINE EVENT test ON test WHEN true THEN {
LET $doc = $this;
CREATE type::thing('log', $event) SET this = $doc, value = $value, before = $before, after = $after;
};
CREATE test:1 SET num = 1;
UPDATE test:1 set num = 2;
DELETE test:1;
SELECT * FROM log;
";
let dbs = new_ds().await?;
let ses = Session::owner().with_ns("test").with_db("test");
let res = &mut dbs.execute(sql, &ses, None).await?;
assert_eq!(res.len(), 5);
//
let tmp = res.remove(0).result;
assert!(tmp.is_ok());
//
let tmp = res.remove(0).result;
assert!(tmp.is_ok());
//
let tmp = res.remove(0).result;
assert!(tmp.is_ok());
//
let tmp = res.remove(0).result;
assert!(tmp.is_ok());
//
let tmp = res.remove(0).result?;
let val = Value::parse(
r#"[
{
after: { id: test:1, num: 1 },
id: log:CREATE,
this: { id: test:1, num: 1 },
value: { id: test:1, num: 1 }
},
{
before: { id: test:1, num: 2 },
id: log:DELETE,
this: { id: test:1, num: 2 },
value: { id: test:1, num: 2 }
},
{
after: { id: test:1, num: 2 },
before: { id: test:1, num: 1 },
id: log:UPDATE,
this: { id: test:1, num: 2 },
value: { id: test:1, num: 2 }
}
]"#,
);
assert_eq!(tmp, val);
//
Ok(())
}
#[tokio::test] #[tokio::test]
async fn define_statement_event_when_logic() -> Result<(), Error> { async fn define_statement_event_when_logic() -> Result<(), Error> {
let sql = " let sql = "