Conversation
41c9aa8 to
ad367ed
Compare
Closed
77562dc to
2cf7319
Compare
Member
Author
|
Marking this as ready for review. |
rhatgadkar-goog
approved these changes
Mar 11, 2026
Collaborator
rhatgadkar-goog
left a comment
There was a problem hiding this comment.
Awesome job on implementing this!
086daa4 to
ec14345
Compare
Psycopg does not support providing a pre-connected socket in its connect API as there is no matching API in the underlying libpq C interface. To work around this limitation, this commit creates an in-memory proxy that copies data between a Unix domain socket and the secure SSL Socket created by the Connector. This approach works, but suffers from poor performance and makes the driver comparable to pg8000 (a pure Python implementation). The best solution would be for psycopg (and libpq) to expose a way to provide a socket creator function as we have in the other drivers. Until then, this is better than nothing. Fixes #377.
Member
Author
|
Just to double check the resource usage, I ran this script to compare with pg8000. I created one Connector and then repeatedly created a pool and read a 1000 records out of my target instance, looking at memory usage, file descriptors, and threads. import argparse
import os
import threading
import sqlalchemy
import time
import psutil
from google.cloud.alloydb.connector import Connector
parser = argparse.ArgumentParser()
parser.add_argument("--driver", choices=["pg8000", "psycopg"], default="psycopg")
args = parser.parse_args()
if args.driver == "pg8000":
import pg8000 # noqa: F401
else:
import psycopg # noqa: F401
_proc = psutil.Process(os.getpid())
DRIVER_URL = {
"pg8000": "postgresql+pg8000://",
"psycopg": "postgresql+psycopg://",
}
# helper function to return SQLAlchemy connection pool
def init_connection_pool(connector: Connector) -> sqlalchemy.engine.Engine:
# function used to generate database connection
def getconn():
conn = connector.connect(
"<INSTANCE_ID>",
args.driver,
user="postgres",
db="postgres",
ip_type="PUBLIC",
password="<PASSWORD>",
)
return conn
# create connection pool
pool = sqlalchemy.create_engine(
DRIVER_URL[args.driver],
creator=getconn,
)
return pool
print(f"Driver: {args.driver}")
print(f"Start Active threads: {threading.active_count()}")
print(f"Start FDs: {_proc.num_fds()}")
print(f"Start RSS: {_proc.memory_info().rss / 1024 / 1024:.1f} MB")
start_time = time.time()
with Connector() as connector:
for i in range(500):
engine = init_connection_pool(connector)
with engine.connect() as db_conn:
db_conn.execute(sqlalchemy.text("SELECT * from my_random_data")).fetchall()
engine.dispose()
if (i + 1) % 10 == 0:
print(f"i={i + 1} RSS: {_proc.memory_info().rss / 1024 / 1024:.1f} MB")
end_time = time.time()
elapsed_time = end_time - start_time
print(f"Elapsed time: {elapsed_time}")
print(f"Finish Active threads: {threading.active_count()}")
print(f"Finish FDs: {_proc.num_fds()}")
print(f"Finish RSS: {_proc.memory_info().rss / 1024 / 1024:.1f} MB")Observations:
So I think we're good to merge this. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Psycopg does not support providing a pre-connected socket in its
connect API as there is no matching API in the underlying libpq C
interface. To work around this limitation, this commit creates an
in-memory proxy that copies data between a Unix domain socket and the
secure SSL Socket created by the Connector.
This approach works, but suffers from poor performance and makes the
driver comparable to pg8000 (a pure Python implementation).
The best solution would be for psycopg (and libpq) to expose a way to
provide a socket creator function as we have in the other drivers. Until
then, this is better than nothing.
Fixes #377.