1
0
Fork 0
mirror of https://github.com/rails/rails.git synced 2022-11-09 12:12:34 -05:00

Merge pull request #40876 from fsateler/performance/type-map-initialize

postgres: Make the initial type map query less expensive
This commit is contained in:
Rafael França 2020-12-18 16:14:34 -05:00 committed by GitHub
commit 3cff5e7388
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 29 additions and 13 deletions

View file

@ -33,15 +33,27 @@ module ActiveRecord
composites.each { |row| register_composite_type(row) } composites.each { |row| register_composite_type(row) }
end end
def query_conditions_for_initial_load def query_conditions_for_known_type_names
known_type_names = @store.keys.map { |n| "'#{n}'" } known_type_names = @store.keys.map { |n| "'#{n}'" }
known_type_types = %w('r' 'e' 'd') <<~SQL % known_type_names.join(", ")
<<~SQL % [known_type_names.join(", "), known_type_types.join(", ")]
WHERE WHERE
t.typname IN (%s) t.typname IN (%s)
OR t.typtype IN (%s) SQL
OR t.typinput = 'array_in(cstring,oid,integer)'::regprocedure end
OR t.typelem != 0
def query_conditions_for_known_type_types
known_type_types = %w('r' 'e' 'd')
<<~SQL % known_type_types.join(", ")
WHERE
t.typtype IN (%s)
SQL
end
def query_conditions_for_array_types
known_type_oids = @store.keys.reject { |k| k.is_a?(String) }
<<~SQL % [known_type_oids.join(", ")]
WHERE
t.typelem IN (%s)
SQL SQL
end end

View file

@ -624,21 +624,25 @@ module ActiveRecord
def load_additional_types(oids = nil) def load_additional_types(oids = nil)
initializer = OID::TypeMapInitializer.new(type_map) initializer = OID::TypeMapInitializer.new(type_map)
load_types_queries(initializer, oids) do |query|
execute_and_clear(query, "SCHEMA", []) do |records|
initializer.run(records)
end
end
end
def load_types_queries(initializer, oids)
query = <<~SQL query = <<~SQL
SELECT t.oid, t.typname, t.typelem, t.typdelim, t.typinput, r.rngsubtype, t.typtype, t.typbasetype SELECT t.oid, t.typname, t.typelem, t.typdelim, t.typinput, r.rngsubtype, t.typtype, t.typbasetype
FROM pg_type as t FROM pg_type as t
LEFT JOIN pg_range as r ON oid = rngtypid LEFT JOIN pg_range as r ON oid = rngtypid
SQL SQL
if oids if oids
query += "WHERE t.oid IN (%s)" % oids.join(", ") yield query + "WHERE t.oid IN (%s)" % oids.join(", ")
else else
query += initializer.query_conditions_for_initial_load yield query + initializer.query_conditions_for_known_type_names
end yield query + initializer.query_conditions_for_known_type_types
yield query + initializer.query_conditions_for_array_types
execute_and_clear(query, "SCHEMA", []) do |records|
initializer.run(records)
end end
end end