diff options
Diffstat (limited to 'activerecord/lib/active_record/connection_adapters/postgresql/schema_statements.rb')
-rw-r--r-- | activerecord/lib/active_record/connection_adapters/postgresql/schema_statements.rb | 63 |
1 files changed, 35 insertions, 28 deletions
diff --git a/activerecord/lib/active_record/connection_adapters/postgresql/schema_statements.rb b/activerecord/lib/active_record/connection_adapters/postgresql/schema_statements.rb index 168180cfd3..686671b007 100644 --- a/activerecord/lib/active_record/connection_adapters/postgresql/schema_statements.rb +++ b/activerecord/lib/active_record/connection_adapters/postgresql/schema_statements.rb @@ -8,6 +8,13 @@ module ActiveRecord o.sql_type = type_to_sql(o.type, o.limit, o.precision, o.scale, o.array) super end + + def add_column_options!(sql, options) + if options[:collation] + sql << " COLLATE \"#{options[:collation]}\"" + end + super + end end module SchemaStatements @@ -63,7 +70,7 @@ module ActiveRecord # Returns the list of all tables in the schema search path or a specified schema. def tables(name = nil) - query(<<-SQL, 'SCHEMA').map { |row| row[0] } + select_values(<<-SQL, 'SCHEMA') SELECT tablename FROM pg_tables WHERE schemaname = ANY (current_schemas(false)) @@ -77,7 +84,7 @@ module ActiveRecord name = Utils.extract_schema_qualified_name(name.to_s) return false unless name.identifier - exec_query(<<-SQL, 'SCHEMA').rows.first[0].to_i > 0 + select_value(<<-SQL, 'SCHEMA').to_i > 0 SELECT COUNT(*) FROM pg_class c LEFT JOIN pg_namespace n ON n.oid = c.relnamespace @@ -93,15 +100,16 @@ module ActiveRecord # Returns true if schema exists. def schema_exists?(name) - exec_query(<<-SQL, 'SCHEMA').rows.first[0].to_i > 0 + select_value(<<-SQL, 'SCHEMA').to_i > 0 SELECT COUNT(*) FROM pg_namespace WHERE nspname = '#{name}' SQL end + # Verifies existence of an index with a given name. def index_name_exists?(table_name, index_name, default) - exec_query(<<-SQL, 'SCHEMA').rows.first[0].to_i > 0 + select_value(<<-SQL, 'SCHEMA').to_i > 0 SELECT COUNT(*) FROM pg_class t INNER JOIN pg_index d ON t.oid = d.indrelid @@ -158,33 +166,33 @@ module ActiveRecord # Returns the list of all column definitions for a table. def columns(table_name) # Limit, precision, and scale are all handled by the superclass. - column_definitions(table_name).map do |column_name, type, default, notnull, oid, fmod| + column_definitions(table_name).map do |column_name, type, default, notnull, oid, fmod, collation| oid = oid.to_i fmod = fmod.to_i type_metadata = fetch_type_metadata(column_name, type, oid, fmod) default_value = extract_value_from_default(default) default_function = extract_default_function(default_value, default) - new_column(column_name, default_value, type_metadata, !notnull, default_function) + new_column(column_name, default_value, type_metadata, !notnull, default_function, collation) end end - def new_column(name, default, sql_type_metadata = nil, null = true, default_function = nil) # :nodoc: - PostgreSQLColumn.new(name, default, sql_type_metadata, null, default_function) + def new_column(name, default, sql_type_metadata = nil, null = true, default_function = nil, collation = nil) # :nodoc: + PostgreSQLColumn.new(name, default, sql_type_metadata, null, default_function, collation) end # Returns the current database name. def current_database - query('select current_database()', 'SCHEMA')[0][0] + select_value('select current_database()', 'SCHEMA') end # Returns the current schema name. def current_schema - query('SELECT current_schema', 'SCHEMA')[0][0] + select_value('SELECT current_schema', 'SCHEMA') end # Returns the current database encoding format. def encoding - query(<<-end_sql, 'SCHEMA')[0][0] + select_value(<<-end_sql, 'SCHEMA') SELECT pg_encoding_to_char(pg_database.encoding) FROM pg_database WHERE pg_database.datname LIKE '#{current_database}' end_sql @@ -192,21 +200,21 @@ module ActiveRecord # Returns the current database collation. def collation - query(<<-end_sql, 'SCHEMA')[0][0] + select_value(<<-end_sql, 'SCHEMA') SELECT pg_database.datcollate FROM pg_database WHERE pg_database.datname LIKE '#{current_database}' end_sql end # Returns the current database ctype. def ctype - query(<<-end_sql, 'SCHEMA')[0][0] + select_value(<<-end_sql, 'SCHEMA') SELECT pg_database.datctype FROM pg_database WHERE pg_database.datname LIKE '#{current_database}' end_sql end # Returns an array of schema names. def schema_names - query(<<-SQL, 'SCHEMA').flatten + select_values(<<-SQL, 'SCHEMA') SELECT nspname FROM pg_namespace WHERE nspname !~ '^pg_.*' @@ -239,12 +247,12 @@ module ActiveRecord # Returns the active schema search path. def schema_search_path - @schema_search_path ||= query('SHOW search_path', 'SCHEMA')[0][0] + @schema_search_path ||= select_value('SHOW search_path', 'SCHEMA') end # Returns the current client message level. def client_min_messages - query('SHOW client_min_messages', 'SCHEMA')[0][0] + select_value('SHOW client_min_messages', 'SCHEMA') end # Set the client message level. @@ -262,10 +270,7 @@ module ActiveRecord end def serial_sequence(table, column) - result = exec_query(<<-eosql, 'SCHEMA') - SELECT pg_get_serial_sequence('#{table}', '#{column}') - eosql - result.rows.first.first + select_value("SELECT pg_get_serial_sequence('#{table}', '#{column}')", 'SCHEMA') end # Sets the sequence of a table's primary key to the specified value. @@ -276,9 +281,7 @@ module ActiveRecord if sequence quoted_sequence = quote_table_name(sequence) - select_value <<-end_sql, 'SCHEMA' - SELECT setval('#{quoted_sequence}', #{value}) - end_sql + select_value("SELECT setval('#{quoted_sequence}', #{value})", 'SCHEMA') else @logger.warn "#{table} has primary key #{pk} with no default sequence" if @logger end @@ -301,7 +304,7 @@ module ActiveRecord if pk && sequence quoted_sequence = quote_table_name(sequence) - select_value <<-end_sql, 'SCHEMA' + select_value(<<-end_sql, 'SCHEMA') SELECT setval('#{quoted_sequence}', (SELECT COALESCE(MAX(#{quote_column_name pk})+(SELECT increment_by FROM #{quoted_sequence}), (SELECT min_value FROM #{quoted_sequence})) FROM #{quote_table_name(table)}), false) end_sql end @@ -363,7 +366,7 @@ module ActiveRecord # Returns just a table's primary key def primary_key(table) - pks = exec_query(<<-end_sql, 'SCHEMA').rows + pks = query(<<-end_sql, 'SCHEMA') SELECT attr.attname FROM pg_attribute attr INNER JOIN pg_constraint cons ON attr.attrelid = cons.conrelid AND attr.attnum = any(cons.conkey) @@ -402,13 +405,15 @@ module ActiveRecord super end - # Changes the column of a table. - def change_column(table_name, column_name, type, options = {}) + def change_column(table_name, column_name, type, options = {}) #:nodoc: clear_cache! quoted_table_name = quote_table_name(table_name) quoted_column_name = quote_column_name(column_name) sql_type = type_to_sql(type, options[:limit], options[:precision], options[:scale], options[:array]) sql = "ALTER TABLE #{quoted_table_name} ALTER COLUMN #{quoted_column_name} TYPE #{sql_type}" + if options[:collation] + sql << " COLLATE \"#{options[:collation]}\"" + end if options[:using] sql << " USING #{options[:using]}" elsif options[:cast_as] @@ -437,7 +442,7 @@ module ActiveRecord end end - def change_column_null(table_name, column_name, null, default = nil) + def change_column_null(table_name, column_name, null, default = nil) #:nodoc: clear_cache! unless null || default.nil? column = column_for(table_name, column_name) @@ -462,6 +467,8 @@ module ActiveRecord execute "DROP INDEX #{quote_table_name(index_name)}" end + # Renames an index of a table. Raises error if length of new + # index name is greater than allowed limit. def rename_index(table_name, old_name, new_name) validate_index_length!(table_name, new_name) |