From 57604cf24ce40a23de0e8d75fc366c24c9fe3aac Mon Sep 17 00:00:00 2001 From: Ryuta Kamizono Date: Mon, 11 Jan 2016 20:14:01 +0900 Subject: Avoid extra `show variables` in migration `initialize_schema_migrations_table` is called in every migrations. https://github.com/rails/rails/blob/v5.0.0.beta1/activerecord/lib/active_record/migration.rb#L1080 https://github.com/rails/rails/blob/v5.0.0.beta1/activerecord/lib/active_record/schema.rb#L51 This means that extra `show variables` is called regardless of the existence of `schema_migrations` table. This change is to avoid extra `show variables` if `schema_migrations` table exists. --- .../connection_adapters/abstract/schema_statements.rb | 6 +++++- .../connection_adapters/abstract_mysql_adapter.rb | 12 +++++------- activerecord/lib/active_record/internal_metadata.rb | 8 +++----- activerecord/lib/active_record/schema_migration.rb | 5 ++--- .../test/cases/adapters/mysql2/schema_migrations_test.rb | 5 ----- 5 files changed, 15 insertions(+), 21 deletions(-) diff --git a/activerecord/lib/active_record/connection_adapters/abstract/schema_statements.rb b/activerecord/lib/active_record/connection_adapters/abstract/schema_statements.rb index 8db7f9172f..cc245587c1 100644 --- a/activerecord/lib/active_record/connection_adapters/abstract/schema_statements.rb +++ b/activerecord/lib/active_record/connection_adapters/abstract/schema_statements.rb @@ -115,7 +115,7 @@ module ActiveRecord checks = [] checks << lambda { |c| c.name == column_name } checks << lambda { |c| c.type == type } if type - [:limit, :precision, :scale, :default, :null].each do |attr| + (migration_keys - [:name]).each do |attr| checks << lambda { |c| c.send(attr) == options[attr] } if options.key?(attr) end @@ -981,6 +981,10 @@ module ActiveRecord ActiveRecord::InternalMetadata.create_table end + def internal_string_options_for_primary_key # :nodoc: + { primary_key: true } + end + def assume_migrated_upto_version(version, migrations_paths) migrations_paths = Array(migrations_paths) version = version.to_i diff --git a/activerecord/lib/active_record/connection_adapters/abstract_mysql_adapter.rb b/activerecord/lib/active_record/connection_adapters/abstract_mysql_adapter.rb index 4dc7aa0c22..70d7956baa 100644 --- a/activerecord/lib/active_record/connection_adapters/abstract_mysql_adapter.rb +++ b/activerecord/lib/active_record/connection_adapters/abstract_mysql_adapter.rb @@ -67,14 +67,12 @@ module ActiveRecord end end - MAX_INDEX_LENGTH_FOR_CHARSETS_OF_4BYTES_MAXLEN = 191 CHARSETS_OF_4BYTES_MAXLEN = ['utf8mb4', 'utf16', 'utf16le', 'utf32'] - def initialize_schema_migrations_table - if CHARSETS_OF_4BYTES_MAXLEN.include?(charset) - ActiveRecord::SchemaMigration.create_table(MAX_INDEX_LENGTH_FOR_CHARSETS_OF_4BYTES_MAXLEN) - else - ActiveRecord::SchemaMigration.create_table - end + + def internal_string_options_for_primary_key # :nodoc: + super.tap { |options| + options[:collation] = collation.sub(/\A[^_]+/, 'utf8') if CHARSETS_OF_4BYTES_MAXLEN.include?(charset) + } end def version diff --git a/activerecord/lib/active_record/internal_metadata.rb b/activerecord/lib/active_record/internal_metadata.rb index 641b137851..cb4b1fc47c 100644 --- a/activerecord/lib/active_record/internal_metadata.rb +++ b/activerecord/lib/active_record/internal_metadata.rb @@ -5,10 +5,6 @@ module ActiveRecord # This class is used to create a table that keeps track of values and keys such # as which environment migrations were run in. class InternalMetadata < ActiveRecord::Base # :nodoc: - # Keys in mysql are limited to 191 characters, due to this no adapter can - # use a longer key - KEY_LIMIT = 191 - class << self def primary_key "key" @@ -33,8 +29,10 @@ module ActiveRecord # Creates an internal metadata table with columns +key+ and +value+ def create_table unless table_exists? + key_options = connection.internal_string_options_for_primary_key + connection.create_table(table_name, id: false) do |t| - t.string :key, primary_key: true, limit: KEY_LIMIT + t.string :key, key_options t.string :value t.timestamps end diff --git a/activerecord/lib/active_record/schema_migration.rb b/activerecord/lib/active_record/schema_migration.rb index a5b693c349..b6cb233e03 100644 --- a/activerecord/lib/active_record/schema_migration.rb +++ b/activerecord/lib/active_record/schema_migration.rb @@ -20,10 +20,9 @@ module ActiveRecord ActiveSupport::Deprecation.silence { connection.table_exists?(table_name) } end - def create_table(limit=nil) + def create_table unless table_exists? - version_options = { primary_key: true } - version_options[:limit] = limit if limit + version_options = connection.internal_string_options_for_primary_key connection.create_table(table_name, id: false) do |t| t.string :version, version_options diff --git a/activerecord/test/cases/adapters/mysql2/schema_migrations_test.rb b/activerecord/test/cases/adapters/mysql2/schema_migrations_test.rb index 9a9a4fed42..7c89fda582 100644 --- a/activerecord/test/cases/adapters/mysql2/schema_migrations_test.rb +++ b/activerecord/test/cases/adapters/mysql2/schema_migrations_test.rb @@ -33,11 +33,6 @@ class SchemaMigrationsTest < ActiveRecord::Mysql2TestCase end end - def test_key_limit_max_matches_max - assert_equal ActiveRecord::InternalMetadata::KEY_LIMIT ,ActiveRecord::ConnectionAdapters::Mysql2Adapter::MAX_INDEX_LENGTH_FOR_CHARSETS_OF_4BYTES_MAXLEN - end - - private def with_encoding_utf8mb4 -- cgit v1.2.3