mirror of
https://github.com/rails/rails.git
synced 2022-11-09 12:12:34 -05:00
Change MySQL and Postgresql to use Bigint primary keys
This commit is contained in:
parent
575212a1ba
commit
b92ae61069
16 changed files with 74 additions and 75 deletions
1
.gitignore
vendored
1
.gitignore
vendored
|
@ -19,3 +19,4 @@ pkg
|
|||
/railties/doc
|
||||
/railties/tmp
|
||||
/guides/output
|
||||
/*/.byebug_history
|
|
@ -71,7 +71,7 @@ module ActiveRecord
|
|||
polymorphic: false,
|
||||
index: true,
|
||||
foreign_key: false,
|
||||
type: :integer,
|
||||
type: :bigint,
|
||||
**options
|
||||
)
|
||||
@name = name
|
||||
|
|
|
@ -56,7 +56,7 @@ module ActiveRecord
|
|||
private
|
||||
|
||||
def default_primary_key?(column)
|
||||
schema_type(column) == :integer
|
||||
schema_type(column) == :bigint
|
||||
end
|
||||
|
||||
def schema_type(column)
|
||||
|
|
|
@ -39,7 +39,7 @@ module ActiveRecord
|
|||
self.emulate_booleans = true
|
||||
|
||||
NATIVE_DATABASE_TYPES = {
|
||||
primary_key: "int auto_increment PRIMARY KEY",
|
||||
primary_key: "BIGINT(8) UNSIGNED DEFAULT NULL auto_increment PRIMARY KEY",
|
||||
string: { name: "varchar", limit: 255 },
|
||||
text: { name: "text", limit: 65535 },
|
||||
integer: { name: "int", limit: 4 },
|
||||
|
|
|
@ -3,7 +3,10 @@ module ActiveRecord
|
|||
module MySQL
|
||||
module ColumnMethods
|
||||
def primary_key(name, type = :primary_key, **options)
|
||||
options[:auto_increment] = true if type == :bigint && !options.key?(:default)
|
||||
if type == :primary_key && !options.key?(:default)
|
||||
options[:auto_increment] = true
|
||||
options[:limit] = 8
|
||||
end
|
||||
super
|
||||
end
|
||||
|
||||
|
|
|
@ -3,11 +3,9 @@ module ActiveRecord
|
|||
module MySQL
|
||||
module ColumnDumper
|
||||
def column_spec_for_primary_key(column)
|
||||
if column.bigint?
|
||||
spec = { id: :bigint.inspect }
|
||||
spec[:default] = schema_default(column) || "nil" unless column.auto_increment?
|
||||
else
|
||||
spec = super
|
||||
spec = super
|
||||
if column.type == :integer && !column.auto_increment?
|
||||
spec[:default] = schema_default(column) || "nil"
|
||||
end
|
||||
spec[:unsigned] = "true" if column.unsigned?
|
||||
spec
|
||||
|
|
|
@ -25,7 +25,7 @@ module ActiveRecord
|
|||
private
|
||||
|
||||
def default_primary_key?(column)
|
||||
schema_type(column) == :serial
|
||||
schema_type(column) == :bigserial
|
||||
end
|
||||
|
||||
def schema_type(column)
|
||||
|
|
|
@ -70,7 +70,7 @@ module ActiveRecord
|
|||
ADAPTER_NAME = "PostgreSQL".freeze
|
||||
|
||||
NATIVE_DATABASE_TYPES = {
|
||||
primary_key: "serial primary key",
|
||||
primary_key: "bigserial primary key",
|
||||
string: { name: "character varying" },
|
||||
text: { name: "text" },
|
||||
integer: { name: "integer" },
|
||||
|
|
|
@ -0,0 +1,13 @@
|
|||
module ActiveRecord
|
||||
module ConnectionAdapters
|
||||
module SQLite3
|
||||
module ColumnDumper
|
||||
private
|
||||
|
||||
def default_primary_key?(column)
|
||||
schema_type(column) == :integer
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
|
@ -4,6 +4,7 @@ require "active_record/connection_adapters/sqlite3/explain_pretty_printer"
|
|||
require "active_record/connection_adapters/sqlite3/quoting"
|
||||
require "active_record/connection_adapters/sqlite3/schema_creation"
|
||||
require "active_record/connection_adapters/sqlite3/schema_definitions"
|
||||
require "active_record/connection_adapters/sqlite3/schema_dumper"
|
||||
|
||||
gem "sqlite3", "~> 1.3.6"
|
||||
require "sqlite3"
|
||||
|
@ -53,6 +54,7 @@ module ActiveRecord
|
|||
ADAPTER_NAME = "SQLite".freeze
|
||||
|
||||
include SQLite3::Quoting
|
||||
include SQLite3::ColumnDumper
|
||||
|
||||
NATIVE_DATABASE_TYPES = {
|
||||
primary_key: "INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL",
|
||||
|
|
|
@ -101,7 +101,12 @@ module ActiveRecord
|
|||
|
||||
def test_primary_key_creates_primary_key_column
|
||||
with_change_table do |t|
|
||||
@connection.expect :add_column, nil, [:delete_me, :id, :primary_key, primary_key: true, first: true]
|
||||
if current_adapter?(:Mysql2Adapter)
|
||||
@connection.expect :add_column, nil, [:delete_me, :id, :primary_key, { first: true, auto_increment: true, limit: 8, primary_key: true }]
|
||||
else
|
||||
@connection.expect :add_column, nil, [:delete_me, :id, :primary_key, primary_key: true, first: true]
|
||||
end
|
||||
|
||||
t.primary_key :id, first: true
|
||||
end
|
||||
end
|
||||
|
|
|
@ -76,7 +76,7 @@ if ActiveRecord::Base.connection.supports_foreign_keys?
|
|||
end
|
||||
|
||||
def test_add_foreign_key_with_non_standard_primary_key
|
||||
with_example_table @connection, "space_shuttles", "pk integer PRIMARY KEY" do
|
||||
with_example_table @connection, "space_shuttles", "pk BIGINT PRIMARY KEY" do
|
||||
@connection.add_foreign_key(:astronauts, :space_shuttles,
|
||||
column: "rocket_id", primary_key: "pk", name: "custom_pk")
|
||||
|
||||
|
@ -229,7 +229,7 @@ if ActiveRecord::Base.connection.supports_foreign_keys?
|
|||
create_table("cities") { |t| }
|
||||
|
||||
create_table("houses") do |t|
|
||||
t.column :city_id, :integer
|
||||
t.column :city_id, :bigint
|
||||
end
|
||||
add_foreign_key :houses, :cities, column: "city_id"
|
||||
|
||||
|
@ -261,7 +261,7 @@ if ActiveRecord::Base.connection.supports_foreign_keys?
|
|||
create_table(:schools)
|
||||
|
||||
create_table(:classes) do |t|
|
||||
t.column :school_id, :integer
|
||||
t.column :school_id, :bigint
|
||||
end
|
||||
add_foreign_key :classes, :schools
|
||||
end
|
||||
|
|
|
@ -42,7 +42,7 @@ if ActiveRecord::Base.connection.supports_foreign_keys?
|
|||
|
||||
test "options hash can be passed" do
|
||||
@connection.change_table :testing_parents do |t|
|
||||
t.integer :other_id
|
||||
t.bigint :other_id
|
||||
t.index :other_id, unique: true
|
||||
end
|
||||
@connection.create_table :testings do |t|
|
||||
|
@ -92,7 +92,7 @@ if ActiveRecord::Base.connection.supports_foreign_keys?
|
|||
|
||||
test "foreign keys accept options when changing the table" do
|
||||
@connection.change_table :testing_parents do |t|
|
||||
t.integer :other_id
|
||||
t.bigint :other_id
|
||||
t.index :other_id, unique: true
|
||||
end
|
||||
@connection.create_table :testings
|
||||
|
@ -177,8 +177,8 @@ if ActiveRecord::Base.connection.supports_foreign_keys?
|
|||
|
||||
test "multiple foreign keys can be added to the same table" do
|
||||
@connection.create_table :testings do |t|
|
||||
t.integer :col_1
|
||||
t.integer :col_2
|
||||
t.bigint :col_1
|
||||
t.bigint :col_2
|
||||
|
||||
t.foreign_key :testing_parents, column: :col_1
|
||||
t.foreign_key :testing_parents, column: :col_2
|
||||
|
|
|
@ -316,85 +316,62 @@ class CompositePrimaryKeyTest < ActiveRecord::TestCase
|
|||
end
|
||||
|
||||
if current_adapter?(:Mysql2Adapter)
|
||||
class PrimaryKeyBigintNilDefaultTest < ActiveRecord::TestCase
|
||||
class PrimaryKeyIntegerNilDefaultTest < ActiveRecord::TestCase
|
||||
include SchemaDumpingHelper
|
||||
|
||||
self.use_transactional_tests = false
|
||||
|
||||
def setup
|
||||
@connection = ActiveRecord::Base.connection
|
||||
@connection.create_table(:bigint_defaults, id: :bigint, default: nil, force: true)
|
||||
@connection.create_table(:int_defaults, id: :integer, default: nil, force: true)
|
||||
end
|
||||
|
||||
def teardown
|
||||
@connection.drop_table :bigint_defaults, if_exists: true
|
||||
@connection.drop_table :int_defaults, if_exists: true
|
||||
end
|
||||
|
||||
test "primary key with bigint allows default override via nil" do
|
||||
column = @connection.columns(:bigint_defaults).find { |c| c.name == "id" }
|
||||
assert column.bigint?
|
||||
test "primary key with integer allows default override via nil" do
|
||||
column = @connection.columns(:int_defaults).find { |c| c.name == "id" }
|
||||
assert_equal :integer, column.type
|
||||
assert_not column.auto_increment?
|
||||
end
|
||||
|
||||
test "schema dump primary key with bigint default nil" do
|
||||
schema = dump_table_schema "bigint_defaults"
|
||||
assert_match %r{create_table "bigint_defaults", id: :bigint, default: nil}, schema
|
||||
test "schema dump primary key with int default nil" do
|
||||
schema = dump_table_schema "int_defaults"
|
||||
assert_match %r{create_table "int_defaults", id: :integer, default: nil}, schema
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if current_adapter?(:PostgreSQLAdapter, :Mysql2Adapter)
|
||||
class PrimaryKeyBigSerialTest < ActiveRecord::TestCase
|
||||
include SchemaDumpingHelper
|
||||
class PrimaryKeyIntegerTest < ActiveRecord::TestCase
|
||||
include SchemaDumpingHelper
|
||||
|
||||
self.use_transactional_tests = false
|
||||
self.use_transactional_tests = false
|
||||
|
||||
class Widget < ActiveRecord::Base
|
||||
end
|
||||
class Widget < ActiveRecord::Base
|
||||
end
|
||||
|
||||
setup do
|
||||
@connection = ActiveRecord::Base.connection
|
||||
if current_adapter?(:PostgreSQLAdapter)
|
||||
@connection.create_table(:widgets, id: :bigserial, force: true)
|
||||
else
|
||||
@connection.create_table(:widgets, id: :bigint, force: true)
|
||||
end
|
||||
end
|
||||
setup do
|
||||
@connection = ActiveRecord::Base.connection
|
||||
@connection.create_table(:widgets, force: true)
|
||||
end
|
||||
|
||||
teardown do
|
||||
@connection.drop_table :widgets, if_exists: true
|
||||
Widget.reset_column_information
|
||||
end
|
||||
teardown do
|
||||
@connection.drop_table :widgets, if_exists: true
|
||||
Widget.reset_column_information
|
||||
end
|
||||
|
||||
test "primary key column type with bigserial" do
|
||||
column_type = Widget.type_for_attribute(Widget.primary_key)
|
||||
assert_equal :integer, column_type.type
|
||||
test "primary key column type" do
|
||||
column_type = Widget.type_for_attribute(Widget.primary_key)
|
||||
assert_equal :integer, column_type.type
|
||||
|
||||
if current_adapter?(:PostgreSQLAdapter, :Mysql2Adapter)
|
||||
assert_equal 8, column_type.limit
|
||||
end
|
||||
|
||||
test "primary key with bigserial are automatically numbered" do
|
||||
widget = Widget.create!
|
||||
assert_not_nil widget.id
|
||||
end
|
||||
|
||||
test "schema dump primary key with bigserial" do
|
||||
schema = dump_table_schema "widgets"
|
||||
if current_adapter?(:PostgreSQLAdapter)
|
||||
assert_match %r{create_table "widgets", id: :bigserial, force: :cascade}, schema
|
||||
else
|
||||
assert_match %r{create_table "widgets", id: :bigint, force: :cascade}, schema
|
||||
end
|
||||
end
|
||||
|
||||
if current_adapter?(:Mysql2Adapter)
|
||||
test "primary key column type with options" do
|
||||
@connection.create_table(:widgets, id: :primary_key, limit: 8, unsigned: true, force: true)
|
||||
column = @connection.columns(:widgets).find { |c| c.name == "id" }
|
||||
assert column.auto_increment?
|
||||
assert_equal :integer, column.type
|
||||
assert_equal 8, column.limit
|
||||
assert column.unsigned?
|
||||
end
|
||||
column = @connection.columns(:widgets).find { |c| c.name == "id" }
|
||||
assert column.auto_increment?
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -346,7 +346,7 @@ class SchemaDumperTest < ActiveRecord::TestCase
|
|||
|
||||
create_table("dogs") do |t|
|
||||
t.column :name, :string
|
||||
t.column :owner_id, :integer
|
||||
t.column :owner_id, :bigint
|
||||
t.index [:name]
|
||||
t.foreign_key :dog_owners, column: "owner_id" if supports_foreign_keys?
|
||||
end
|
||||
|
|
|
@ -54,7 +54,7 @@ ActiveRecord::Schema.define do
|
|||
|
||||
create_table :authors, force: true do |t|
|
||||
t.string :name, null: false
|
||||
t.integer :author_address_id
|
||||
t.bigint :author_address_id
|
||||
t.integer :author_address_extra_id
|
||||
t.string :organization_id
|
||||
t.string :owned_essay_id
|
||||
|
@ -303,7 +303,7 @@ ActiveRecord::Schema.define do
|
|||
end
|
||||
|
||||
create_table :engines, force: true do |t|
|
||||
t.integer :car_id
|
||||
t.bigint :car_id
|
||||
end
|
||||
|
||||
create_table :entrants, force: true do |t|
|
||||
|
@ -1004,7 +1004,7 @@ ActiveRecord::Schema.define do
|
|||
if supports_foreign_keys?
|
||||
# fk_test_has_fk should be before fk_test_has_pk
|
||||
create_table :fk_test_has_fk, force: true do |t|
|
||||
t.integer :fk_id, null: false
|
||||
t.bigint :fk_id, null: false
|
||||
end
|
||||
|
||||
create_table :fk_test_has_pk, force: true, primary_key: "pk_id" do |t|
|
||||
|
|
Loading…
Reference in a new issue