pub struct PgPool { /* private fields */ }Implementations§
Source§impl PgPool
impl PgPool
Sourcepub async fn connect(dsn: &str, max_size: usize) -> Result<Self>
pub async fn connect(dsn: &str, max_size: usize) -> Result<Self>
Connects using a postgresql:// DSN, matching the DSN Python’s
DatabaseConfig/_build_dsn already produces today. No TLS support
yet — no SSL/TLS surface exists anywhere in the project currently
(confirmed by a full-repo grep during planning), so this isn’t a
regression; it’s simply not needed until it is.
Unlike deadpool_postgres::Pool::builder(..).build() on its own —
which only validates the DSN and is otherwise lazy, deferring the
first real connection attempt to whenever a caller first acquires
one — this eagerly acquires and immediately releases one connection
before returning, so a bad host/port/database/credentials fails
right here. That eager-connect
behavior, which the caller (Client.ensure_connected) depends on to
raise ConnectionFailedError/ConnectionTimeoutError immediately
rather than silently deferring the failure to the first query.
Sourcepub fn types(&self) -> &ExtensionOids
pub fn types(&self) -> &ExtensionOids
The type OIDs discovered for this database when the pool connected.
Pass this to query_typed/query_composite rather than
ExtensionOids::default() — without it, a vector, enum, or domain
column has no decoder.
Sourcepub async fn refresh_types(&mut self) -> Result<()>
pub async fn refresh_types(&mut self) -> Result<()>
Re-runs type discovery. Needed after a migration creates an enum, domain, or extension type, since the registry is a connect-time snapshot and a pool normally outlives a migration.
Sourcepub fn clear_statement_caches(&self)
pub fn clear_statement_caches(&self)
Drops every pooled connection’s prepared-statement cache.
Must be called after any DDL that could change a statement’s result
type or parameter types — refresh_types already does, so migration
paths get this for free. Cheap: it only empties the cache maps, it
does not touch the connections.
Sourcepub fn set_name(&mut self, name: impl Into<String>)
pub fn set_name(&mut self, name: impl Into<String>)
Labels this pool in observability output — see PoolWaitObserver.
Sourcepub fn status(&self) -> PoolStatus
pub fn status(&self) -> PoolStatus
Current connection accounting — for the Prometheus gauge sampler
(pylon-py’s record_pool_metrics), not used on any query path.
Sourcepub async fn query_raw(&self, sql: &str) -> Result<Vec<Row>>
pub async fn query_raw(&self, sql: &str) -> Result<Vec<Row>>
Executes sql with no parameters and returns the raw rows.
Composite/record decoding is a later phase — this only proves the
pool can connect and round-trip a query end to end.
Sourcepub async fn query_composite(
&self,
sql: &str,
ext: &ExtensionOids,
) -> Result<Vec<DecodedValue>>
pub async fn query_composite( &self, sql: &str, ext: &ExtensionOids, ) -> Result<Vec<DecodedValue>>
Runs sql (expected to produce exactly one column, matching
pylon-core’s SELECT (...) AS result emission) and decodes that
column of every row via wire::decode_value, using its actual
declared Postgres type (not assumed to be record — a bare scalar
result column decodes just as well through the same path).
Sourcepub async fn query_typed(
&self,
sql: &str,
params: &[DecodedValue],
ext: &ExtensionOids,
) -> Result<Vec<DecodedValue>>
pub async fn query_typed( &self, sql: &str, params: &[DecodedValue], ext: &ExtensionOids, ) -> Result<Vec<DecodedValue>>
Runs sql with bound params, matched positionally to $1, $2, ...
— the same convention pylon-core’s param_names already assumes.
No caller-supplied parameter types: prepare asks Postgres itself
to analyze the SQL and report each placeholder’s expected Type
(Statement::params()), which drives wire::encode_value’s
encoding directly. Decodes the single result column exactly like
query_composite.
Sourcepub async fn query_typed_named(
&self,
sql: &str,
params: &[DecodedValue],
ext: &ExtensionOids,
) -> Result<Vec<DecodedValue>>
pub async fn query_typed_named( &self, sql: &str, params: &[DecodedValue], ext: &ExtensionOids, ) -> Result<Vec<DecodedValue>>
Like query_typed, but decodes every column of every row by name
instead of assuming a single (...) AS result column — for
hand-written admin SQL (CLI commands, not pylon-core-emitted
query bodies) that reads named columns directly.
Sourcepub async fn query_typed_with_globals(
&self,
sql: &str,
params: &[DecodedValue],
ext: &ExtensionOids,
globals: &str,
) -> Result<Vec<DecodedValue>>
pub async fn query_typed_with_globals( &self, sql: &str, params: &[DecodedValue], ext: &ExtensionOids, globals: &str, ) -> Result<Vec<DecodedValue>>
query_typed, with the session globals database triggers read
(pylon.globals) set first on the same connection. Each mutating
statement sets them anew, so a pooled connection never hands one
statement’s globals to the next.
Sourcepub async fn execute_typed_with_globals(
&self,
sql: &str,
params: &[DecodedValue],
globals: &str,
) -> Result<u64>
pub async fn execute_typed_with_globals( &self, sql: &str, params: &[DecodedValue], globals: &str, ) -> Result<u64>
execute_typed, with pylon.globals set — see query_typed_with_globals.
Sourcepub async fn execute_typed(
&self,
sql: &str,
params: &[DecodedValue],
) -> Result<u64>
pub async fn execute_typed( &self, sql: &str, params: &[DecodedValue], ) -> Result<u64>
Runs sql with bound params (same convention as query_typed)
and discards the result, returning the number of rows affected —
for INSERT/UPDATE/DELETE where the caller has no RETURNING
clause to decode.
Sourcepub async fn query_explain(
&self,
sql: &str,
params: &[DecodedValue],
) -> Result<String>
pub async fn query_explain( &self, sql: &str, params: &[DecodedValue], ) -> Result<String>
Runs EXPLAIN (ANALYZE, FORMAT JSON, VERBOSE) sql with bound
params and returns the raw JSON output text verbatim — for
analyze <query> (see pylon_core::analyze), which parses this text
itself to correlate plan nodes back to the query’s own shape.
Actually runs the query (ANALYZE), same as Postgres’s own
EXPLAIN ANALYZE, not just its planner estimate.
Sourcepub async fn begin(&self, isolation: &str) -> Result<PgTransaction>
pub async fn begin(&self, isolation: &str) -> Result<PgTransaction>
Acquires one pooled connection and starts an explicit transaction at
the given isolation level ("read_uncommitted", "read_committed",
"repeatable_read", or "serializable" — matching
AsyncTransaction’s existing accepted values in client.py, itself
the four standard SQL isolation levels). The returned
PgTransaction owns the connection until commit/rollback
consumes it.
Sourcepub async fn begin_default(&self) -> Result<PgTransaction>
pub async fn begin_default(&self) -> Result<PgTransaction>
Starts a transaction with no explicit isolation level — whatever
Postgres’s own session/database default is applies. Used by
migration execution, which (unlike begin) never needs a specific
isolation level — this matches a plain conn.transaction()
(no isolation= kwarg) that the old Python migration executor used.
Sourcepub async fn batch_execute(&self, sql: &str) -> Result<()>
pub async fn batch_execute(&self, sql: &str) -> Result<()>
Runs sql via the simple query protocol — no bind parameters, but
(unlike query_typed/execute_typed, which prepare via the extended
protocol and so accept exactly one statement) able to run several
;-separated statements in one call. Matches
Connection.execute(sql) called with no arguments, which migration
DDL steps rely on (a step’s body is whatever raw SQL text sits
between -- pylon:step markers, often more than one statement).
Sourcepub async fn connection(&self) -> Result<PgConnection>
pub async fn connection(&self) -> Result<PgConnection>
Checks out one pooled connection and hands back a handle the caller
holds across several calls, with no transaction started — for
state that’s scoped to a single session rather than a single
statement or transaction, the way Postgres advisory locks
(pg_advisory_lock/pg_advisory_unlock) are: they’re released by
an explicit unlock (or the session ending), not by a transaction
boundary, so acquiring and releasing one has to happen on the same
held connection — calling PgPool::batch_execute twice wouldn’t
work, since each call may checkout a different pooled connection.
Trait Implementations§
Auto Trait Implementations§
impl !RefUnwindSafe for PgPool
impl !UnwindSafe for PgPool
impl Freeze for PgPool
impl Send for PgPool
impl Sync for PgPool
impl Unpin for PgPool
impl UnsafeUnpin for PgPool
Blanket Implementations§
Source§impl<T> ArchivePointee for T
impl<T> ArchivePointee for T
Source§type ArchivedMetadata = ()
type ArchivedMetadata = ()
Source§fn pointer_metadata(
_: &<T as ArchivePointee>::ArchivedMetadata,
) -> <T as Pointee>::Metadata
fn pointer_metadata( _: &<T as ArchivePointee>::ArchivedMetadata, ) -> <T as Pointee>::Metadata
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
Source§fn in_current_span(self) -> Instrumented<Self> ⓘ
fn in_current_span(self) -> Instrumented<Self> ⓘ
Source§impl<T> LayoutRaw for T
impl<T> LayoutRaw for T
Source§fn layout_raw(_: <T as Pointee>::Metadata) -> Result<Layout, LayoutError>
fn layout_raw(_: <T as Pointee>::Metadata) -> Result<Layout, LayoutError>
Source§impl<T, N1, N2> Niching<NichedOption<T, N1>> for N2
impl<T, N1, N2> Niching<NichedOption<T, N1>> for N2
Source§unsafe fn is_niched(niched: *const NichedOption<T, N1>) -> bool
unsafe fn is_niched(niched: *const NichedOption<T, N1>) -> bool
Source§fn resolve_niched(out: Place<NichedOption<T, N1>>)
fn resolve_niched(out: Place<NichedOption<T, N1>>)
out indicating that a T is niched.