surrealdb_sql/statements/
update.rs1use crate::ctx::Context;
2use crate::dbs::{Iterator, Options, Statement, Transaction};
3use crate::doc::CursorDoc;
4use crate::err::Error;
5use crate::{Cond, Data, Output, Timeout, Value, Values};
6use derive::Store;
7use revision::revisioned;
8use serde::{Deserialize, Serialize};
9use std::fmt;
10
11#[derive(Clone, Debug, Default, Eq, PartialEq, PartialOrd, Serialize, Deserialize, Store, Hash)]
12#[revisioned(revision = 2)]
13pub struct UpdateStatement {
14 #[revision(start = 2)]
15 pub only: bool,
16 pub what: Values,
17 pub data: Option<Data>,
18 pub cond: Option<Cond>,
19 pub output: Option<Output>,
20 pub timeout: Option<Timeout>,
21 pub parallel: bool,
22}
23
24impl UpdateStatement {
25 pub(crate) fn writeable(&self) -> bool {
27 true
28 }
29 pub(crate) async fn compute(
31 &self,
32 ctx: &Context<'_>,
33 opt: &Options,
34 txn: &Transaction,
35 doc: Option<&CursorDoc<'_>>,
36 ) -> Result<Value, Error> {
37 opt.valid_for_db()?;
39 let mut i = Iterator::new();
41 let stm = Statement::from(self);
43 let opt = &opt.new_with_futures(false).with_projections(false);
45 for w in self.what.0.iter() {
47 let v = w.compute(ctx, opt, txn, doc).await?;
48 i.prepare(ctx, opt, txn, &stm, v).await.map_err(|e| match e {
49 Error::InvalidStatementTarget {
50 value: v,
51 } => Error::UpdateStatement {
52 value: v,
53 },
54 e => e,
55 })?;
56 }
57 match i.output(ctx, opt, txn, &stm).await? {
59 Value::Array(mut a) if self.only => match a.len() {
61 1 => Ok(a.remove(0)),
63 _ => Err(Error::SingleOnlyOutput),
65 },
66 v => Ok(v),
68 }
69 }
70}
71
72impl fmt::Display for UpdateStatement {
73 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
74 write!(f, "UPDATE")?;
75 if self.only {
76 f.write_str(" ONLY")?
77 }
78 write!(f, " {}", self.what)?;
79 if let Some(ref v) = self.data {
80 write!(f, " {v}")?
81 }
82 if let Some(ref v) = self.cond {
83 write!(f, " {v}")?
84 }
85 if let Some(ref v) = self.output {
86 write!(f, " {v}")?
87 }
88 if let Some(ref v) = self.timeout {
89 write!(f, " {v}")?
90 }
91 if self.parallel {
92 f.write_str(" PARALLEL")?
93 }
94 Ok(())
95 }
96}