Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Pass the connection to query transformers #47220

Merged
merged 5 commits into from Feb 2, 2023

Conversation

rafaelfranca
Copy link
Member

Sometimes we need to tag the queries with information that are in the database connection that is making the query.

Exposing the connection in the context parameter for the tagging procs we can read the information we need.

This also allow us to fix the default tagging for database information that were always using the ActiveRecord::Base connection, to use the right connection.

In the case the comment existed we would be calling this method twice
before.
@@ -1113,7 +1113,7 @@ def log(sql, name = "SQL", binds = [], type_casted_binds = [], statement_name =

def transform_query(sql)
ActiveRecord.query_transformers.each do |transformer|
sql = transformer.call(sql)
sql = transformer.call(sql, self)
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think those transformers were intended to be public API, so I'm not bothering with allowing transformers that accept only one parameter. But let me know if I got it work @byroot about the intention of this being public.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, not intended to be public, at least not for now. I'd see value is such API being public, but I'd wouldn't do it without putting some thoughts into it first.

attr_accessor :schema_cache

def connection_class; end
def checkin(_); end
def remove(_); end
def async_executor; end
def db_config
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This change sucks. It is only required because when checkind out a connection form the pool, we first create the object, check if the database version satisfies the requirements, and then we assign the pool to the connection.

When we are checking the database version, we are doing a query, so we try to annotate the query with the tags, but the pool isn't assigned yet, so pool.db_config would return an exception.

This is because the NullPool doesn't satisfy the ConnectionPool interface, which we should fix.

As the only queries that happen without a pool are very likely internal queries I'm retuning an object that respond to anything, without caring if that object have the same interface of the real configs.

This will avoid that this test mutates the global state of
ActiveRecord::QueryLogs.taggings and thus affect other tests.
Sometimes we need to tag the queries with information that are in the
database connection that is making the query, so let's add it to the
context.
Previous this tag would get the information only from ActiveRecord::Base
connection, which in a multi-database application would be wrong.

This get the information from the connection that is going to be used to
execute the query.

We also had to change the NullPool to make this work.

It is only required because when checking out a connection form the pool,
we first create the object, check if the database version satisfies the
requirements, and then we assign the pool to the connection.

When we are checking the database version, we are doing a query, so we
try to annotate the query with the tags, but the pool isn't assigned yet,
so `pool.db_config` would return an exception.

This is because the NullPool doesn't satisfy the ConnectionPool
interface, which we should fix.

As the only queries that happen without a pool are very likely internal
queries we are retuning an object that respond to anything, without
caring if that object have the same interface of the real configs.
Copy link
Member

@byroot byroot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense to me. You may want to transform the query based on connection settings (e.g. timeout) etc.

@rafaelfranca rafaelfranca merged commit caaafcd into rails:main Feb 2, 2023
@rafaelfranca rafaelfranca deleted the rm-connection-to-tag-logs branch February 2, 2023 15:24
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants