Skip to main content

toasty_driver_integration_suite/tests/
infra_connection_per_clone.rs

1use crate::prelude::*;
2
3#[driver_test(id(ID), scenario(crate::scenarios::two_models))]
4pub async fn db_does_not_hold_connection(t: &mut Test) -> Result<()> {
5    if !t.capability().test_connection_pool {
6        return Ok(());
7    }
8
9    let mut db = setup(t).await;
10
11    // Db is stateless — after setup_db, the connection used for push_schema has
12    // been returned to the pool, so it should be available.
13    let status = db.pool().status();
14    assert_eq!(
15        status.size, 1,
16        "setup_db should have created one connection"
17    );
18    assert_eq!(
19        status.available, 1,
20        "connection should be back in the pool (Db is stateless)"
21    );
22
23    // Execute an operation — it acquires a connection, runs, and returns it.
24    User::create().name("dummy").exec(&mut db).await?;
25
26    let status = db.pool().status();
27    assert_eq!(
28        status.available, 1,
29        "connection should be returned after operation"
30    );
31
32    // Clone the handle — both share the same pool.
33    let mut db2 = db.clone();
34    User::create().name("dummy").exec(&mut db2).await?;
35
36    let status = db.pool().status();
37    assert_eq!(
38        status.available, status.size,
39        "all connections should be available after operations"
40    );
41
42    // The original handle still works fine.
43    let user = User::create().name("dummy").exec(&mut db).await?;
44    let found = User::filter_by_id(user.id).exec(&mut db).await?;
45    assert_eq!(found.len(), 1);
46
47    Ok(())
48}
49
50#[driver_test(id(ID), scenario(crate::scenarios::two_models))]
51pub async fn dedicated_connection_holds_pool_slot(t: &mut Test) -> Result<()> {
52    if !t.capability().test_connection_pool {
53        return Ok(());
54    }
55
56    let db = setup(t).await;
57
58    // All connections available since Db is stateless.
59    let status = db.pool().status();
60    assert_eq!(status.available, status.size);
61
62    // Acquire a dedicated connection — it should be held from the pool.
63    let mut conn = db.connection().await?;
64
65    let status = db.pool().status();
66    assert_eq!(
67        status.available,
68        status.size - 1,
69        "dedicated connection should be held from the pool"
70    );
71
72    // Use the connection.
73    User::create().name("dummy").exec(&mut conn).await?;
74
75    // Connection is still held.
76    let status = db.pool().status();
77    assert_eq!(
78        status.available,
79        status.size - 1,
80        "connection should still be held after operation"
81    );
82
83    // Drop the connection — it should return to the pool.
84    drop(conn);
85
86    // The background task needs a moment to notice the channel closed and exit.
87    tokio::task::yield_now().await;
88
89    let status = db.pool().status();
90    assert_eq!(
91        status.available, status.size,
92        "connection should be returned after drop"
93    );
94
95    Ok(())
96}
97
98#[driver_test(id(ID), scenario(crate::scenarios::two_models))]
99pub async fn write_visible_on_same_handle(t: &mut Test) -> Result<()> {
100    let mut db = setup(t).await;
101
102    // Write and immediately read on the same handle — must see the write.
103    let created = User::create().name("hello").exec(&mut db).await?;
104    let found = User::filter_by_id(created.id).get(&mut db).await?;
105    assert_eq!(found.name, "hello");
106
107    Ok(())
108}