toasty_driver_integration_suite/tests/
batch_create_statements.rs1use crate::prelude::*;
2
3use toasty_core::{
4 driver::{operation::Transaction, Operation},
5 stmt::Statement,
6};
7
8#[driver_test(id(ID), requires(sql))]
10pub async fn batch_two_creates_same_model(t: &mut Test) -> Result<()> {
11 #[derive(Debug, toasty::Model)]
12 struct User {
13 #[key]
14 #[auto]
15 id: ID,
16 name: String,
17 }
18
19 let mut db = t.setup_db(models!(User)).await;
20
21 t.log().clear();
22 let (alice, bob): (User, User) =
23 toasty::batch((User::create().name("Alice"), User::create().name("Bob")))
24 .exec(&mut db)
25 .await?;
26
27 assert_eq!(alice.name, "Alice");
28 assert_eq!(bob.name, "Bob");
29
30 assert_struct!(
32 t.log().pop_op(),
33 Operation::Transaction(Transaction::Start {
34 isolation: None,
35 read_only: false
36 })
37 );
38 assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
39 stmt: Statement::Insert(_),
40 ..
41 })); assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
43 stmt: Statement::Insert(_),
44 ..
45 })); assert!(t.log().pop_op().is_transaction_commit());
47 assert!(t.log().is_empty());
48
49 let all: Vec<_> = User::filter_by_id(alice.id).exec(&mut db).await?;
51 assert_eq!(all.len(), 1);
52 let all: Vec<_> = User::filter_by_id(bob.id).exec(&mut db).await?;
53 assert_eq!(all.len(), 1);
54
55 Ok(())
56}
57
58#[driver_test(id(ID), requires(sql))]
60pub async fn batch_two_creates_different_models(t: &mut Test) -> Result<()> {
61 #[derive(Debug, toasty::Model)]
62 struct User {
63 #[key]
64 #[auto]
65 id: ID,
66 name: String,
67 }
68
69 #[derive(Debug, toasty::Model)]
70 struct Post {
71 #[key]
72 #[auto]
73 id: ID,
74 title: String,
75 }
76
77 let mut db = t.setup_db(models!(User, Post)).await;
78
79 t.log().clear();
80 let (user, post): (User, Post) = toasty::batch((
81 User::create().name("Alice"),
82 Post::create().title("Hello World"),
83 ))
84 .exec(&mut db)
85 .await?;
86
87 assert_eq!(user.name, "Alice");
88 assert_eq!(post.title, "Hello World");
89
90 assert_struct!(
92 t.log().pop_op(),
93 Operation::Transaction(Transaction::Start {
94 isolation: None,
95 read_only: false
96 })
97 );
98 assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
99 stmt: Statement::Insert(_),
100 ..
101 })); assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
103 stmt: Statement::Insert(_),
104 ..
105 })); assert!(t.log().pop_op().is_transaction_commit());
107 assert!(t.log().is_empty());
108
109 let found = User::get_by_id(&mut db, user.id).await?;
111 assert_eq!(found.name, "Alice");
112 let found = Post::get_by_id(&mut db, post.id).await?;
113 assert_eq!(found.title, "Hello World");
114
115 Ok(())
116}
117
118#[driver_test(id(ID), requires(sql))]
120pub async fn batch_query_then_create(t: &mut Test) -> Result<()> {
121 #[derive(Debug, toasty::Model)]
122 struct User {
123 #[key]
124 #[auto]
125 id: ID,
126 #[index]
127 name: String,
128 }
129
130 let mut db = t.setup_db(models!(User)).await;
131 User::create().name("Alice").exec(&mut db).await?;
132
133 t.log().clear();
134 let (existing, created): (Vec<User>, User) =
135 toasty::batch((User::filter_by_name("Alice"), User::create().name("Bob")))
136 .exec(&mut db)
137 .await?;
138
139 assert_struct!(existing, [_ { name: "Alice" }]);
140 assert_eq!(created.name, "Bob");
141
142 assert_struct!(
144 t.log().pop_op(),
145 Operation::Transaction(Transaction::Start {
146 isolation: None,
147 read_only: false
148 })
149 );
150 assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
151 stmt: Statement::Query(_),
152 ..
153 })); assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
155 stmt: Statement::Insert(_),
156 ..
157 })); assert!(t.log().pop_op().is_transaction_commit());
159 assert!(t.log().is_empty());
160
161 Ok(())
162}
163
164#[driver_test(id(ID), requires(sql))]
166pub async fn batch_create_then_query(t: &mut Test) -> Result<()> {
167 #[derive(Debug, toasty::Model)]
168 struct User {
169 #[key]
170 #[auto]
171 id: ID,
172 #[index]
173 name: String,
174 }
175
176 let mut db = t.setup_db(models!(User)).await;
177 User::create().name("Alice").exec(&mut db).await?;
178
179 t.log().clear();
180 let (created, existing): (User, Vec<User>) =
181 toasty::batch((User::create().name("Bob"), User::filter_by_name("Alice")))
182 .exec(&mut db)
183 .await?;
184
185 assert_eq!(created.name, "Bob");
186 assert_struct!(existing, [_ { name: "Alice" }]);
187
188 assert_struct!(
190 t.log().pop_op(),
191 Operation::Transaction(Transaction::Start {
192 isolation: None,
193 read_only: false
194 })
195 );
196 assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
197 stmt: Statement::Insert(_),
198 ..
199 })); assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
201 stmt: Statement::Query(_),
202 ..
203 })); assert!(t.log().pop_op().is_transaction_commit());
205 assert!(t.log().is_empty());
206
207 Ok(())
208}
209
210#[driver_test(id(ID), requires(sql))]
212pub async fn batch_create_query_create(t: &mut Test) -> Result<()> {
213 #[derive(Debug, toasty::Model)]
214 struct User {
215 #[key]
216 #[auto]
217 id: ID,
218 #[index]
219 name: String,
220 }
221
222 let mut db = t.setup_db(models!(User)).await;
223 User::create().name("Alice").exec(&mut db).await?;
224
225 t.log().clear();
226 let (bob, existing, carol): (User, Vec<User>, User) = toasty::batch((
227 User::create().name("Bob"),
228 User::filter_by_name("Alice"),
229 User::create().name("Carol"),
230 ))
231 .exec(&mut db)
232 .await?;
233
234 assert_eq!(bob.name, "Bob");
235 assert_struct!(existing, [_ { name: "Alice" }]);
236 assert_eq!(carol.name, "Carol");
237
238 assert_struct!(
240 t.log().pop_op(),
241 Operation::Transaction(Transaction::Start {
242 isolation: None,
243 read_only: false
244 })
245 );
246 assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
247 stmt: Statement::Insert(_),
248 ..
249 })); assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
251 stmt: Statement::Query(_),
252 ..
253 })); assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
255 stmt: Statement::Insert(_),
256 ..
257 })); assert!(t.log().pop_op().is_transaction_commit());
259 assert!(t.log().is_empty());
260
261 Ok(())
262}
263
264#[driver_test(id(ID), requires(sql))]
266pub async fn batch_creates_from_array(t: &mut Test) -> Result<()> {
267 #[derive(Debug, toasty::Model)]
268 struct User {
269 #[key]
270 #[auto]
271 id: ID,
272 name: String,
273 }
274
275 let mut db = t.setup_db(models!(User)).await;
276
277 t.log().clear();
278 let users = toasty::batch([
279 User::create().name("Alice"),
280 User::create().name("Bob"),
281 User::create().name("Carol"),
282 ])
283 .exec(&mut db)
284 .await?;
285
286 assert_struct!(users, [{ name: "Alice" }, { name: "Bob" }, { name: "Carol" }]);
287
288 assert_struct!(
290 t.log().pop_op(),
291 Operation::Transaction(Transaction::Start {
292 isolation: None,
293 read_only: false
294 })
295 );
296 for _ in 0..3 {
297 assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
298 stmt: Statement::Insert(_),
299 ..
300 }));
301 }
302 assert!(t.log().pop_op().is_transaction_commit());
303 assert!(t.log().is_empty());
304
305 for user in &users {
307 let found = User::get_by_id(&mut db, user.id).await?;
308 assert_eq!(found.name, user.name);
309 }
310
311 Ok(())
312}
313
314#[driver_test(id(ID), requires(sql))]
316pub async fn batch_creates_from_vec(t: &mut Test) -> Result<()> {
317 #[derive(Debug, toasty::Model)]
318 struct User {
319 #[key]
320 #[auto]
321 id: ID,
322 name: String,
323 }
324
325 let mut db = t.setup_db(models!(User)).await;
326
327 let names = ["Alice", "Bob", "Carol"];
328 let builders: Vec<_> = names.iter().map(|n| User::create().name(*n)).collect();
329
330 t.log().clear();
331 let users = toasty::batch(builders).exec(&mut db).await?;
332
333 assert_struct!(users, [{ name: "Alice" }, { name: "Bob" }, { name: "Carol" }]);
334
335 assert_struct!(
337 t.log().pop_op(),
338 Operation::Transaction(Transaction::Start {
339 isolation: None,
340 read_only: false
341 })
342 );
343 for _ in 0..3 {
344 assert_struct!(t.log().pop_op(), Operation::QuerySql(_ {
345 stmt: Statement::Insert(_),
346 ..
347 }));
348 }
349 assert!(t.log().pop_op().is_transaction_commit());
350 assert!(t.log().is_empty());
351
352 for user in &users {
354 let found = User::get_by_id(&mut db, user.id).await?;
355 assert_eq!(found.name, user.name);
356 }
357
358 Ok(())
359}