Class: ActiveRecord::ConnectionAdapters::MysqlAdapter

Inherits:
AbstractAdapter show all
Defined in:
lib/connection_adapters/mysql_adapter.rb

Overview

The purpose of this extension to MysqlAdapter is to exploit the referential constraints offered in MySQL >=5.0, and to make the table and column metadata stored in MySQL available to ActiveRecord objects

Currently, CHECK constraints are not supported in MySQL 5.x. Although the syntax for creating CHECK constraints is supported, they are ignored by MySQL

Instance Method Summary collapse

Instance Method Details

#columns(table_name, name = nil) ⇒ Object

The “EXTRA” column is discarded in the standard Rails implementation of MysqlAdapter.columns. ActiveRecord can use this column to generate validations



73
74
75
76
77
78
# File 'lib/connection_adapters/mysql_adapter.rb', line 73

def columns(table_name, name = nil)#:nodoc:
  sql = "SHOW FIELDS FROM #{table_name}"
  columns = []
  execute(sql, name).each { |field| columns << MysqlColumn.new(field[0], field[4], field[1], field[2] == "YES", field[5])}
  columns
end

#constraints(table_name, name = nil) ⇒ Object

Retrieve each DB constraint from the information_schema database that is either a constraint on table_name or references table_name (eg. FK into table_name)

Save a boolean value on each constraint indicating whether it is part of a composite constraint or not. This allows us to encapsulate is_composite? logic on the constraint object itself, rather than depending on access to the complete set of constraints for the table at a later time



86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
# File 'lib/connection_adapters/mysql_adapter.rb', line 86

def constraints(table_name, name = nil)#:nodoc:
  constraints = []
  sql = "select KCU.constraint_name, KCU.table_schema, KCU.table_name, KCU.column_name, TC.constraint_type, KCU.referenced_table_name, KCU.referenced_column_name from \
    ((select constraint_name, constraint_type, table_name from information_schema.table_constraints where table_schema='#{schema}' and table_name='#{table_name}') as TC right join \
    (select * from information_schema.key_column_usage where table_schema='#{schema}' and (table_name='#{table_name}' or referenced_table_name='#{table_name}')) as KCU on \
    (TC.constraint_name=KCU.constraint_name AND TC.table_name=KCU.table_name))"
  results = execute(sql, name)
  constraint_name_hash = {}
  results.each do |row| 
    constraints << MysqlConstraint.new(row[0], row[1], row[2], row[3], row[4], row[5], row[6])
    comparable_constraint_name = row[0].upcase + row[2].upcase
    constraint_name_count = constraint_name_hash[comparable_constraint_name]
    constraint_name_count ? 
      constraint_name_hash[comparable_constraint_name] = constraint_name_count + 1 :
      constraint_name_hash[comparable_constraint_name] = 1
  end
  
  constraints.each do | constraint|
    constraint.member_of_composite=(constraint_name_hash[constraint.constraint_name.upcase + constraint.table_name.upcase] > 1)
  end
  constraints
end

#schemaObject

FIXME filter SQL queries on information_schema by schema name in case a table

with the same name exists in > 1 schema (i.e. test vs. dev schema)


67
68
69
# File 'lib/connection_adapters/mysql_adapter.rb', line 67

def schema
  @connection_options[3]
end