Skip to main content

eventuary_postgres/
database.rs

1use sqlx::PgPool;
2use sqlx::postgres::PgPoolOptions;
3
4use eventuary_core::{Error, Result};
5
6#[derive(Clone, Copy, Debug, Eq, PartialEq)]
7pub struct PgDatabaseConfig {
8    pub max_connections: u32,
9}
10
11impl Default for PgDatabaseConfig {
12    fn default() -> Self {
13        Self {
14            max_connections: 20,
15        }
16    }
17}
18
19pub type PgConnectOptions = PgDatabaseConfig;
20
21pub struct PgDatabase {
22    pool: PgPool,
23    config: PgDatabaseConfig,
24}
25
26impl PgDatabase {
27    pub async fn connect(url: &str) -> Result<Self> {
28        Self::connect_with_config(url, PgDatabaseConfig::default()).await
29    }
30
31    pub async fn connect_with(url: &str, options: PgConnectOptions) -> Result<Self> {
32        Self::connect_with_config(url, options).await
33    }
34
35    pub async fn connect_with_config(url: &str, config: PgDatabaseConfig) -> Result<Self> {
36        let pool = PgPoolOptions::new()
37            .max_connections(config.max_connections)
38            .connect(url)
39            .await
40            .map_err(|e| Error::Store(e.to_string()))?;
41        Ok(Self { pool, config })
42    }
43
44    pub fn with_pool(pool: PgPool) -> Self {
45        Self::with_pool_and_config(pool, PgDatabaseConfig::default())
46    }
47
48    pub fn with_pool_and_config(pool: PgPool, config: PgDatabaseConfig) -> Self {
49        Self { pool, config }
50    }
51
52    pub fn pool(&self) -> PgPool {
53        self.pool.clone()
54    }
55
56    pub fn config(&self) -> &PgDatabaseConfig {
57        &self.config
58    }
59}
60
61#[cfg(test)]
62mod tests {
63    use super::*;
64
65    #[test]
66    fn default_config_uses_twenty_connections() {
67        assert_eq!(PgDatabaseConfig::default().max_connections, 20);
68    }
69
70    #[test]
71    fn connect_options_aliases_database_config() {
72        let options = PgConnectOptions { max_connections: 7 };
73        assert_eq!(options.max_connections, 7);
74    }
75}